diff --git a/Allwclean b/Allwclean new file mode 100755 index 0000000000000000000000000000000000000000..be272495544444aae17ea79fca0585386105b114 --- /dev/null +++ b/Allwclean @@ -0,0 +1,9 @@ +#!/bin/sh +# Compile mesh library +wclean libso meshLibrary + +# Compile executables +wclean all executables + +# Compile utilities +wclean all utilities diff --git a/Allwmake b/Allwmake index 968c8a20af0f61432909a7460a23e1b749ea8381..d7667758074e76b5c88f7186e1534640ac90bb6f 100755 --- a/Allwmake +++ b/Allwmake @@ -1,15 +1,9 @@ #!/bin/sh # Compile mesh library -cd meshLibrary -wmake libso -cd .. +wmake libso meshLibrary -# Compile cartesianMesh -#cd executables/cartesianMesh -#wmake -#cd ../.. +# Compile executables +wmake all executables -# Compile dualMesh -#cd executables/dualMesh -#wmake -#cd ../.. +# Compile utilities +wmake all utilities diff --git a/GUI/GTK/generalPage/generalpage.glade b/GUI/GTK/generalPage/generalpage.glade deleted file mode 100644 index 070e41ff40c8fe5c050517757cfaf7abc69fa057..0000000000000000000000000000000000000000 --- a/GUI/GTK/generalPage/generalpage.glade +++ /dev/null @@ -1,470 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-interface SYSTEM "http://glade.gnome.org/glade-2.0.dtd"> - -<glade-interface> - -<widget class="GtkWindow" id="window_generalPage"> - <property name="visible">True</property> - <property name="title" translatable="yes">General settings</property> - <property name="type">GTK_WINDOW_TOPLEVEL</property> - <property name="window_position">GTK_WIN_POS_NONE</property> - <property name="modal">False</property> - <property name="resizable">True</property> - <property name="destroy_with_parent">False</property> - <property name="decorated">True</property> - <property name="skip_taskbar_hint">False</property> - <property name="skip_pager_hint">False</property> - <property name="type_hint">GDK_WINDOW_TYPE_HINT_NORMAL</property> - <property name="gravity">GDK_GRAVITY_NORTH_WEST</property> - <property name="focus_on_map">True</property> - <property name="urgency_hint">False</property> - - <child> - <widget class="GtkAlignment" id="alignment1"> - <property name="border_width">5</property> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">1</property> - <property name="yscale">1</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">0</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkVBox" id="vbox1"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkHBox" id="hbox1"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkLabel" id="label_surfaceFile"> - <property name="visible">True</property> - <property name="label" translatable="yes">Surface file</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkAlignment" id="alignment4"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">1</property> - <property name="yscale">1</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">96</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkEntry" id="entry_surfaceFile"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="editable">True</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char">●</property> - <property name="activates_default">False</property> - <signal name="editing_done" handler="on_entry_surfaceFile_editing_done" last_modification_time="Thu, 18 Oct 2007 20:17:37 GMT"/> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkButton" id="button1"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - - <child> - <widget class="GtkImage" id="image1"> - <property name="visible">True</property> - <property name="stock">gtk-open</property> - <property name="icon_size">4</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkHBox" id="hbox2"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkLabel" id="label_maxCellSize"> - <property name="visible">True</property> - <property name="label" translatable="yes">Max cell size [m]</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkAlignment" id="alignment3"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">1</property> - <property name="yscale">1</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">54</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkEntry" id="entry_maxCellSize"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="editable">True</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char">●</property> - <property name="activates_default">False</property> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkCheckButton" id="checkbutton_boundaryCellSize"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="label" translatable="yes">Use different size for boundary cells</property> - <property name="use_underline">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - <property name="active">False</property> - <property name="inconsistent">False</property> - <property name="draw_indicator">True</property> - <signal name="activate" handler="on_checkbutton_boundaryCellSize_activate" object="meshGui_" last_modification_time="Wed, 17 Oct 2007 18:54:38 GMT"/> - <signal name="clicked" handler="on_checkbutton_boundaryCellSize_clicked" object="meshGui_" last_modification_time="Wed, 17 Oct 2007 18:54:56 GMT"/> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkHBox" id="hbox3"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkLabel" id="label_boundaryCellSize"> - <property name="visible">True</property> - <property name="label" translatable="yes">Boundary cell size [m]</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkAlignment" id="alignment2"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">1</property> - <property name="yscale">1</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">10</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkEntry" id="entry_boundaryCellSize"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="editable">True</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char">●</property> - <property name="activates_default">False</property> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkHSeparator" id="hseparator2"> - <property name="visible">True</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkVBox" id="vbox2"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkCheckButton" id="checkbutton_automaticRefinement"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="label" translatable="yes">Use automatic refinement</property> - <property name="use_underline">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - <property name="active">False</property> - <property name="inconsistent">False</property> - <property name="draw_indicator">True</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkHBox" id="hbox4"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkLabel" id="label_minCellSize"> - <property name="visible">True</property> - <property name="label" translatable="yes">Min cell size [m]</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkAlignment" id="alignment5"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">1</property> - <property name="yscale">1</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">61</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkEntry" id="entry_minCellSize"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="editable">True</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char">●</property> - <property name="activates_default">False</property> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkHSeparator" id="hseparator1"> - <property name="visible">True</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkCheckButton" id="checkbutton_keepCellsIntersectingBoundary"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="label" translatable="yes">Keep octree boxes intersecting the boundary</property> - <property name="use_underline">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - <property name="active">False</property> - <property name="inconsistent">False</property> - <property name="draw_indicator">True</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkCheckButton" id="checkbutton_checkForGluedMesh"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="label" translatable="yes">Remove invalid mesh connections</property> - <property name="use_underline">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - <property name="active">False</property> - <property name="inconsistent">False</property> - <property name="draw_indicator">True</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - </widget> - </child> - </widget> - </child> -</widget> - -</glade-interface> diff --git a/GUI/GTK/generalPage/generalpage.gladep b/GUI/GTK/generalPage/generalpage.gladep deleted file mode 100644 index cb81d53211bbcaba42a2da3257cd024fa08f8208..0000000000000000000000000000000000000000 --- a/GUI/GTK/generalPage/generalpage.gladep +++ /dev/null @@ -1,8 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-project SYSTEM "http://glade.gnome.org/glade-project-2.0.dtd"> - -<glade-project> - <name>GeneralPage</name> - <program_name>generalpage</program_name> - <gnome_support>FALSE</gnome_support> -</glade-project> diff --git a/GUI/GTK/keepCellsIntersectingPatches/keepcellsintersectingpatches.glade b/GUI/GTK/keepCellsIntersectingPatches/keepcellsintersectingpatches.glade deleted file mode 100644 index 34abf26adc4172b312bbab6fb9ff215132172f5b..0000000000000000000000000000000000000000 --- a/GUI/GTK/keepCellsIntersectingPatches/keepcellsintersectingpatches.glade +++ /dev/null @@ -1,285 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-interface SYSTEM "http://glade.gnome.org/glade-2.0.dtd"> - -<glade-interface> - -<widget class="GtkWindow" id="window_keepCellsIntersectingPatches_window"> - <property name="visible">True</property> - <property name="title" translatable="yes">Select patches</property> - <property name="type">GTK_WINDOW_TOPLEVEL</property> - <property name="window_position">GTK_WIN_POS_NONE</property> - <property name="modal">False</property> - <property name="resizable">True</property> - <property name="destroy_with_parent">False</property> - <property name="decorated">True</property> - <property name="skip_taskbar_hint">False</property> - <property name="skip_pager_hint">False</property> - <property name="type_hint">GDK_WINDOW_TYPE_HINT_NORMAL</property> - <property name="gravity">GDK_GRAVITY_NORTH_WEST</property> - <property name="focus_on_map">True</property> - <property name="urgency_hint">False</property> - - <child> - <widget class="GtkTable" id="table1"> - <property name="visible">True</property> - <property name="n_rows">2</property> - <property name="n_columns">3</property> - <property name="homogeneous">False</property> - <property name="row_spacing">0</property> - <property name="column_spacing">0</property> - - <child> - <widget class="GtkLabel" id="label_keepCellsIntersectingPatches_availablePatches"> - <property name="visible">True</property> - <property name="label" translatable="yes">Available patches</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">1</property> - <property name="top_attach">0</property> - <property name="bottom_attach">1</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkComboBoxEntry" id="comboboxentry_keepCellsIntersectingPatches_availablePatches"> - <property name="visible">True</property> - <property name="add_tearoffs">False</property> - <property name="has_frame">True</property> - <property name="focus_on_click">True</property> - </widget> - <packing> - <property name="left_attach">1</property> - <property name="right_attach">2</property> - <property name="top_attach">0</property> - <property name="bottom_attach">1</property> - <property name="y_options">fill</property> - </packing> - </child> - - <child> - <widget class="GtkButton" id="button1"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - - <child> - <widget class="GtkAlignment" id="alignment1"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">0</property> - <property name="yscale">0</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">0</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkHBox" id="hbox1"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">2</property> - - <child> - <widget class="GtkImage" id="image1"> - <property name="visible">True</property> - <property name="stock">gtk-add</property> - <property name="icon_size">4</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="label3"> - <property name="visible">True</property> - <property name="label" translatable="yes">Add</property> - <property name="use_underline">True</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - </widget> - </child> - </widget> - </child> - </widget> - <packing> - <property name="left_attach">2</property> - <property name="right_attach">3</property> - <property name="top_attach">0</property> - <property name="bottom_attach">1</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="label_keepCellsIntersectingPatches_selectedPatches"> - <property name="visible">True</property> - <property name="label" translatable="yes">Selected patches</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">1</property> - <property name="top_attach">1</property> - <property name="bottom_attach">2</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkComboBoxEntry" id="comboboxentry_keepCellsIntersectingPatches_selectedPatches"> - <property name="visible">True</property> - <property name="add_tearoffs">False</property> - <property name="has_frame">True</property> - <property name="focus_on_click">True</property> - </widget> - <packing> - <property name="left_attach">1</property> - <property name="right_attach">2</property> - <property name="top_attach">1</property> - <property name="bottom_attach">2</property> - <property name="x_options">fill</property> - <property name="y_options">fill</property> - </packing> - </child> - - <child> - <widget class="GtkButton" id="button2"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - - <child> - <widget class="GtkAlignment" id="alignment2"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">0</property> - <property name="yscale">0</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">0</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkHBox" id="hbox2"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">2</property> - - <child> - <widget class="GtkImage" id="image2"> - <property name="visible">True</property> - <property name="stock">gtk-remove</property> - <property name="icon_size">4</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="label5"> - <property name="visible">True</property> - <property name="label" translatable="yes">Remove</property> - <property name="use_underline">True</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - </widget> - </child> - </widget> - </child> - </widget> - <packing> - <property name="left_attach">2</property> - <property name="right_attach">3</property> - <property name="top_attach">1</property> - <property name="bottom_attach">2</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - </widget> - </child> -</widget> - -</glade-interface> diff --git a/GUI/GTK/keepCellsIntersectingPatches/keepcellsintersectingpatches.gladep b/GUI/GTK/keepCellsIntersectingPatches/keepcellsintersectingpatches.gladep deleted file mode 100644 index 041b8543943f21dba275b2a07189f7146ba9657b..0000000000000000000000000000000000000000 --- a/GUI/GTK/keepCellsIntersectingPatches/keepcellsintersectingpatches.gladep +++ /dev/null @@ -1,8 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-project SYSTEM "http://glade.gnome.org/glade-project-2.0.dtd"> - -<glade-project> - <name>KeepCellsIntersectingPatches</name> - <program_name>keepcellsintersectingpatches</program_name> - <gnome_support>FALSE</gnome_support> -</glade-project> diff --git a/GUI/GTK/localRefinement/localrefinement.glade b/GUI/GTK/localRefinement/localrefinement.glade deleted file mode 100644 index 66c70ddbc2f2127da38310cef9cec80089d97cdb..0000000000000000000000000000000000000000 --- a/GUI/GTK/localRefinement/localrefinement.glade +++ /dev/null @@ -1,511 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-interface SYSTEM "http://glade.gnome.org/glade-2.0.dtd"> - -<glade-interface> - -<widget class="GtkWindow" id="window_localRefinement"> - <property name="visible">True</property> - <property name="title" translatable="yes">Local refinement</property> - <property name="type">GTK_WINDOW_TOPLEVEL</property> - <property name="window_position">GTK_WIN_POS_NONE</property> - <property name="modal">False</property> - <property name="resizable">True</property> - <property name="destroy_with_parent">False</property> - <property name="decorated">True</property> - <property name="skip_taskbar_hint">False</property> - <property name="skip_pager_hint">False</property> - <property name="type_hint">GDK_WINDOW_TYPE_HINT_NORMAL</property> - <property name="gravity">GDK_GRAVITY_NORTH_WEST</property> - <property name="focus_on_map">True</property> - <property name="urgency_hint">False</property> - - <child> - <widget class="GtkAlignment" id="alignment3"> - <property name="border_width">10</property> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">1</property> - <property name="yscale">1</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">0</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkVBox" id="vbox1"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkHBox" id="hbox1"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkLabel" id="label_localRefinement_availablePatches"> - <property name="visible">True</property> - <property name="label" translatable="yes">Available patches</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkComboBoxEntry" id="comboboxentry_localRefinement_availablePatches"> - <property name="visible">True</property> - <property name="add_tearoffs">False</property> - <property name="has_frame">True</property> - <property name="focus_on_click">True</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkButton" id="button_localRefinement_add"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - - <child> - <widget class="GtkAlignment" id="alignment1"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">0</property> - <property name="yscale">0</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">0</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkHBox" id="hbox3"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">2</property> - - <child> - <widget class="GtkImage" id="image1"> - <property name="visible">True</property> - <property name="stock">gtk-add</property> - <property name="icon_size">4</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="label2"> - <property name="visible">True</property> - <property name="label" translatable="yes">Add</property> - <property name="use_underline">True</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - </widget> - </child> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkAlignment" id="alignment4"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">1</property> - <property name="yscale">1</property> - <property name="top_padding">10</property> - <property name="bottom_padding">0</property> - <property name="left_padding">0</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkHBox" id="hbox4"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkVBox" id="vbox2"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkLabel" id="label_localRefinement_selectedPatches"> - <property name="visible">True</property> - <property name="label" translatable="yes">Selected patches</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <placeholder/> - </child> - - <child> - <placeholder/> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkScrolledWindow" id="scrolledwindow2"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="hscrollbar_policy">GTK_POLICY_ALWAYS</property> - <property name="vscrollbar_policy">GTK_POLICY_ALWAYS</property> - <property name="shadow_type">GTK_SHADOW_IN</property> - <property name="window_placement">GTK_CORNER_TOP_LEFT</property> - - <child> - <widget class="GtkTreeView" id="treeview3"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="headers_visible">True</property> - <property name="rules_hint">False</property> - <property name="reorderable">False</property> - <property name="enable_search">True</property> - <property name="fixed_height_mode">False</property> - <property name="hover_selection">False</property> - <property name="hover_expand">False</property> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - - <child> - <widget class="GtkVBox" id="vbox3"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkButton" id="button_localRefinement_remove"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - - <child> - <widget class="GtkAlignment" id="alignment5"> - <property name="visible">True</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xscale">0</property> - <property name="yscale">0</property> - <property name="top_padding">0</property> - <property name="bottom_padding">0</property> - <property name="left_padding">0</property> - <property name="right_padding">0</property> - - <child> - <widget class="GtkHBox" id="hbox5"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">2</property> - - <child> - <widget class="GtkImage" id="image2"> - <property name="visible">True</property> - <property name="stock">gtk-remove</property> - <property name="icon_size">4</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="label5"> - <property name="visible">True</property> - <property name="label" translatable="yes">Remove</property> - <property name="use_underline">True</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - </widget> - </child> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <placeholder/> - </child> - - <child> - <placeholder/> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - </child> - </widget> - </child> -</widget> - -<widget class="GtkWindow" id="window_localRefinement_selectPopup"> - <property name="visible">True</property> - <property name="title" translatable="yes">Set size for the selected patch</property> - <property name="type">GTK_WINDOW_TOPLEVEL</property> - <property name="window_position">GTK_WIN_POS_NONE</property> - <property name="modal">False</property> - <property name="resizable">True</property> - <property name="destroy_with_parent">False</property> - <property name="decorated">True</property> - <property name="skip_taskbar_hint">False</property> - <property name="skip_pager_hint">False</property> - <property name="type_hint">GDK_WINDOW_TYPE_HINT_NORMAL</property> - <property name="gravity">GDK_GRAVITY_NORTH_WEST</property> - <property name="focus_on_map">True</property> - <property name="urgency_hint">False</property> - - <child> - <widget class="GtkTable" id="table1"> - <property name="visible">True</property> - <property name="n_rows">2</property> - <property name="n_columns">2</property> - <property name="homogeneous">False</property> - <property name="row_spacing">0</property> - <property name="column_spacing">0</property> - - <child> - <widget class="GtkLabel" id="label6"> - <property name="visible">True</property> - <property name="label" translatable="yes">Selected patch</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">1</property> - <property name="top_attach">0</property> - <property name="bottom_attach">1</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="label_localRefinement_cellSize"> - <property name="visible">True</property> - <property name="label" translatable="yes">Cell size [m]</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="left_attach">0</property> - <property name="right_attach">1</property> - <property name="top_attach">1</property> - <property name="bottom_attach">2</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkEntry" id="entry_localRefinement_cellSize"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="editable">True</property> - <property name="visibility">True</property> - <property name="max_length">0</property> - <property name="text" translatable="yes"></property> - <property name="has_frame">True</property> - <property name="invisible_char">●</property> - <property name="activates_default">False</property> - </widget> - <packing> - <property name="left_attach">1</property> - <property name="right_attach">2</property> - <property name="top_attach">1</property> - <property name="bottom_attach">2</property> - <property name="y_options"></property> - </packing> - </child> - - <child> - <widget class="GtkLabel" id="label_localRefinement_selected"> - <property name="visible">True</property> - <property name="label" translatable="yes"></property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="left_attach">1</property> - <property name="right_attach">2</property> - <property name="top_attach">0</property> - <property name="bottom_attach">1</property> - <property name="x_options">fill</property> - <property name="y_options"></property> - </packing> - </child> - </widget> - </child> -</widget> - -</glade-interface> diff --git a/GUI/GTK/localRefinement/localrefinement.gladep b/GUI/GTK/localRefinement/localrefinement.gladep deleted file mode 100644 index 3fff85816bbd641dc2e5d4568cbb4a22ce0a14ac..0000000000000000000000000000000000000000 --- a/GUI/GTK/localRefinement/localrefinement.gladep +++ /dev/null @@ -1,8 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-project SYSTEM "http://glade.gnome.org/glade-project-2.0.dtd"> - -<glade-project> - <name>LocalRefinement</name> - <program_name>localrefinement</program_name> - <gnome_support>FALSE</gnome_support> -</glade-project> diff --git a/GUI/GTK/localSettingsMainWindow/localsettingsmainwindow.glade b/GUI/GTK/localSettingsMainWindow/localsettingsmainwindow.glade deleted file mode 100644 index 8178135b61f039c9efc407502c5d4ff80ab975f9..0000000000000000000000000000000000000000 --- a/GUI/GTK/localSettingsMainWindow/localsettingsmainwindow.glade +++ /dev/null @@ -1,89 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-interface SYSTEM "http://glade.gnome.org/glade-2.0.dtd"> - -<glade-interface> - -<widget class="GtkWindow" id="window_localSettingsMainWindow"> - <property name="visible">True</property> - <property name="title" translatable="yes">Local settings</property> - <property name="type">GTK_WINDOW_TOPLEVEL</property> - <property name="window_position">GTK_WIN_POS_NONE</property> - <property name="modal">False</property> - <property name="resizable">True</property> - <property name="destroy_with_parent">False</property> - <property name="decorated">True</property> - <property name="skip_taskbar_hint">False</property> - <property name="skip_pager_hint">False</property> - <property name="type_hint">GDK_WINDOW_TYPE_HINT_NORMAL</property> - <property name="gravity">GDK_GRAVITY_NORTH_WEST</property> - <property name="focus_on_map">True</property> - <property name="urgency_hint">False</property> - - <child> - <widget class="GtkNotebook" id="notebook1"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="show_tabs">True</property> - <property name="show_border">True</property> - <property name="tab_pos">GTK_POS_TOP</property> - <property name="scrollable">False</property> - <property name="enable_popup">False</property> - - <child> - <placeholder/> - </child> - - <child> - <widget class="GtkLabel" id="label_localRefinement"> - <property name="visible">True</property> - <property name="label" translatable="yes">Local refinement</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="type">tab</property> - </packing> - </child> - - <child> - <placeholder/> - </child> - - <child> - <widget class="GtkLabel" id="label_keepBoxesIntersectingPatches"> - <property name="visible">True</property> - <property name="label" translatable="yes">Keep octree boxes intersecting patches</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="type">tab</property> - </packing> - </child> - </widget> - </child> -</widget> - -</glade-interface> diff --git a/GUI/GTK/localSettingsMainWindow/localsettingsmainwindow.gladep b/GUI/GTK/localSettingsMainWindow/localsettingsmainwindow.gladep deleted file mode 100644 index 93fa732339b95ce4a52777622f12e8604be76be8..0000000000000000000000000000000000000000 --- a/GUI/GTK/localSettingsMainWindow/localsettingsmainwindow.gladep +++ /dev/null @@ -1,8 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-project SYSTEM "http://glade.gnome.org/glade-project-2.0.dtd"> - -<glade-project> - <name>LocalSettingsMainWindow</name> - <program_name>localsettingsmainwindow</program_name> - <gnome_support>FALSE</gnome_support> -</glade-project> diff --git a/GUI/GTK/mainWindow/mainwindow.glade b/GUI/GTK/mainWindow/mainwindow.glade deleted file mode 100644 index 8600fad0ec8e1e0461445c7e38449e5d3952090f..0000000000000000000000000000000000000000 --- a/GUI/GTK/mainWindow/mainwindow.glade +++ /dev/null @@ -1,165 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-interface SYSTEM "http://glade.gnome.org/glade-2.0.dtd"> - -<glade-interface> - -<widget class="GtkWindow" id="window1"> - <property name="visible">True</property> - <property name="title" translatable="yes">window1</property> - <property name="type">GTK_WINDOW_POPUP</property> - <property name="window_position">GTK_WIN_POS_NONE</property> - <property name="modal">False</property> - <property name="resizable">True</property> - <property name="destroy_with_parent">False</property> - <property name="decorated">True</property> - <property name="skip_taskbar_hint">False</property> - <property name="skip_pager_hint">False</property> - <property name="type_hint">GDK_WINDOW_TYPE_HINT_NORMAL</property> - <property name="gravity">GDK_GRAVITY_NORTH_WEST</property> - <property name="focus_on_map">True</property> - <property name="urgency_hint">False</property> - - <child> - <widget class="GtkVBox" id="vbox1"> - <property name="visible">True</property> - <property name="homogeneous">False</property> - <property name="spacing">0</property> - - <child> - <widget class="GtkToolbar" id="toolbar1"> - <property name="visible">True</property> - <property name="orientation">GTK_ORIENTATION_HORIZONTAL</property> - <property name="toolbar_style">GTK_TOOLBAR_ICONS</property> - <property name="tooltips">True</property> - <property name="show_arrow">True</property> - - <child> - <widget class="GtkToolItem" id="toolitem1"> - <property name="visible">True</property> - <property name="visible_horizontal">True</property> - <property name="visible_vertical">True</property> - <property name="is_important">False</property> - - <child> - <widget class="GtkButton" id="button_mainWindow_save"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="label" translatable="yes">Save meshDict</property> - <property name="use_underline">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - </widget> - </child> - </widget> - <packing> - <property name="expand">False</property> - <property name="homogeneous">False</property> - </packing> - </child> - - <child> - <widget class="GtkToolItem" id="toolitem2"> - <property name="visible">True</property> - <property name="visible_horizontal">True</property> - <property name="visible_vertical">True</property> - <property name="is_important">False</property> - - <child> - <widget class="GtkButton" id="button_mainWindow_exit"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="label" translatable="yes">Exit</property> - <property name="use_underline">True</property> - <property name="relief">GTK_RELIEF_NORMAL</property> - <property name="focus_on_click">True</property> - </widget> - </child> - </widget> - <packing> - <property name="expand">False</property> - <property name="homogeneous">False</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">False</property> - <property name="fill">False</property> - </packing> - </child> - - <child> - <widget class="GtkNotebook" id="notebook1"> - <property name="visible">True</property> - <property name="can_focus">True</property> - <property name="show_tabs">True</property> - <property name="show_border">True</property> - <property name="tab_pos">GTK_POS_TOP</property> - <property name="scrollable">False</property> - <property name="enable_popup">False</property> - - <child> - <placeholder/> - </child> - - <child> - <widget class="GtkLabel" id="label_generalSettings"> - <property name="visible">True</property> - <property name="label" translatable="yes">General settings</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="type">tab</property> - </packing> - </child> - - <child> - <placeholder/> - </child> - - <child> - <widget class="GtkLabel" id="label_localSettings"> - <property name="visible">True</property> - <property name="label" translatable="yes">Local settings</property> - <property name="use_underline">False</property> - <property name="use_markup">False</property> - <property name="justify">GTK_JUSTIFY_LEFT</property> - <property name="wrap">False</property> - <property name="selectable">False</property> - <property name="xalign">0.5</property> - <property name="yalign">0.5</property> - <property name="xpad">0</property> - <property name="ypad">0</property> - <property name="ellipsize">PANGO_ELLIPSIZE_NONE</property> - <property name="width_chars">-1</property> - <property name="single_line_mode">False</property> - <property name="angle">0</property> - </widget> - <packing> - <property name="type">tab</property> - </packing> - </child> - </widget> - <packing> - <property name="padding">0</property> - <property name="expand">True</property> - <property name="fill">True</property> - </packing> - </child> - </widget> - </child> -</widget> - -</glade-interface> diff --git a/GUI/GTK/mainWindow/mainwindow.gladep b/GUI/GTK/mainWindow/mainwindow.gladep deleted file mode 100644 index b6434bff9530309ef35182b239e618ff21ff93fc..0000000000000000000000000000000000000000 --- a/GUI/GTK/mainWindow/mainwindow.gladep +++ /dev/null @@ -1,8 +0,0 @@ -<?xml version="1.0" standalone="no"?> <!--*- mode: xml -*--> -<!DOCTYPE glade-project SYSTEM "http://glade.gnome.org/glade-project-2.0.dtd"> - -<glade-project> - <name>MainWindow</name> - <program_name>mainwindow</program_name> - <gnome_support>FALSE</gnome_support> -</glade-project> diff --git a/GUI/Make/files b/GUI/Make/files deleted file mode 100644 index ec3d7c8d021cda34542d9787e40e22a4000548a4..0000000000000000000000000000000000000000 --- a/GUI/Make/files +++ /dev/null @@ -1,35 +0,0 @@ -meshGenGUI = meshGenGUI -meshGenGTK = meshGenGTK -meshGenQt = meshGenQt -GTKHelpers = meshGenGTK/helpers -meshGenFLTK = meshGenFLTK - -$(meshGenGUI)/meshGenGUI.C -$(meshGenGUI)/meshGenGUIGeneral.C -$(meshGenGUI)/meshGenGUIPatchRefinement.C -$(meshGenGUI)/meshGenGUIKeepCellsIntersectingPatches.C -$(meshGenGUI)/meshGenGUIBndLayers.C -$(meshGenGUI)/meshGenGUIObjectRefinement.C -//$(meshGenGUI)/meshGenGUISubsetRefinement.C -$(meshGenGUI)/meshGenGUIRenameBoundary.C - -$(meshGenGTK)/meshGenGTK.C -$(meshGenGTK)/meshGenGTKGeneralPage.C -$(meshGenGTK)/meshGenGTKLocalRefinement.C -$(meshGenGTK)/meshGenGTKLocalSettingsMainWindow.C -$(meshGenGTK)/meshGenGTKObjectRefinementMainWindow.C -$(meshGenGTK)/meshGenGTKMainWindow.C -$(meshGenGTK)/meshGenGTKKeepCellsIntersectingPatches.C -$(meshGenGTK)/meshGenGTKBndLayers.C -$(meshGenGTK)/meshGenGTKBoxRefinement.C -$(meshGenGTK)/meshGenGTKLineRefinement.C -$(meshGenGTK)/meshGenGTKConeRefinement.C -$(meshGenGTK)/meshGenGTKSphereRefinement.C -$(meshGenGTK)/meshGenGTKRenameBoundary.C - -$(meshGenQt)/meshGenQt.C -$(meshGenQt)/meshGenQt.moc.C -$(meshGenQt)/meshGenQtGeneralSettings.C -$(meshGenQt)/meshGenQtGeneralSettings.moc.C - -LIB = $(FOAM_LIBBIN)/libMeshGenerationGui diff --git a/GUI/Make/options b/GUI/Make/options deleted file mode 100644 index d053162e7301c74b4e5a35b671bc454a9979f692..0000000000000000000000000000000000000000 --- a/GUI/Make/options +++ /dev/null @@ -1,34 +0,0 @@ -EXE_INC = \ - -g -ggdb -DFULLDEBUG -O0 -Wno-old-style-cast \ - -I$(FOAM_USER_LIB)/meshGeneration/meshLibrary/lnInclude \ - -I$(FOAM_USER_LIB)/meshGeneration/GUI/lnInclude \ - -I$(FOAM_SRC)/triSurface/lnInclude \ - -I/usr/include/cairo \ - -I/usr/include/freetype2 \ - -I/usr/include/libpng12 \ - -I/opt/gnome/include/gtk-2.0 \ - -I/opt/gnome/lib64/gtk-2.0/include \ - -I/opt/gnome/include/atk-1.0 \ - -I/opt/gnome/include/pango-1.0 \ - -I/opt/gnome/include/glib-2.0 \ - -I/opt/gnome/lib64/glib-2.0/include \ - -I$(QTDIR)/include -I$(QTDIR)/include/QtCore -I$(QTDIR)/include/QtGui \ - -I$(QTDIR)/include/QtOpenGL - -MOC = $(QTDIR)/bin/moc - -EXE_LIBS = \ - -lMeshLibrary \ - -ltriSurface \ - -L/opt/gnome/lib64 \ - -lgtk-x11-2.0 \ - -lgdk-x11-2.0 \ - -latk-1.0 \ - -lgdk_pixbuf-2.0 \ - -lpangocairo-1.0 \ - -lpango-1.0 -lcairo -lgobject-2.0 -lgmodule-2.0 -ldl \ - -lglib-2.0 -lfreetype -lz -lfontconfig -lexpat -lglitz \ - -lm -lpng12 -lXrender -lX11 -lpthread -lXau -lXdmcp \ - -L/usr/local/lib -L/usr/X11R6/lib \ - -L$(QTDIR)/lib \ - -lGL -lGLU -lqt-mt diff --git a/GUI/meshGenGTK/helpers/gtkHelpers.C b/GUI/meshGenGTK/helpers/gtkHelpers.C deleted file mode 100644 index 0f76f15ed85c04cb1ad4d0d603ece24b97f021aa..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/helpers/gtkHelpers.C +++ /dev/null @@ -1,63 +0,0 @@ -/* - * DO NOT EDIT THIS FILE - it is generated by Glade. - */ - -#ifdef HAVE_CONFIG_H -# include <config.h> -#endif - -#include <sys/types.h> -#include <sys/stat.h> -#include <unistd.h> -#include <string.h> -#include <stdio.h> - -#include <gtk/gtk.h> - -#include <iostream> - -#include "gtkHelpers.H" - -GtkWidget* lookup_widget -( - GtkWidget* widget, - const gchar* widget_name -) -{ - GtkWidget *parent, *found_widget; - - for(;;) - { - if( GTK_IS_MENU(widget) ) - { - parent = gtk_menu_get_attach_widget(GTK_MENU(widget)); - std::cout << "Here!" << std::endl; - } - else - { - parent = widget->parent; - std::cout << "Parent " << parent << std::endl; - } - if( !parent ) - { - parent = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(widget), - "GladeParentKey" - ); - } - - if( parent == NULL ) - break; - widget = parent; - } - - std::cout << "Start " << widget << std::endl; - found_widget = (GtkWidget*)g_object_get_data(G_OBJECT(widget), widget_name); - - if( !found_widget ) - g_warning("Widget not found: %s", widget_name); - - return found_widget; -} diff --git a/GUI/meshGenGTK/helpers/gtkHelpers.H b/GUI/meshGenGTK/helpers/gtkHelpers.H deleted file mode 100644 index 98e6a1ca34e086bc227547a98ae37488eb12f488..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/helpers/gtkHelpers.H +++ /dev/null @@ -1,46 +0,0 @@ -/* - * DO NOT EDIT THIS FILE - it is generated by Glade. - */ - -#ifdef HAVE_CONFIG_H -# include <config.h> -#endif - -#include <gtk/gtk.h> - -/* - * Standard gettext macros. - */ -#ifdef ENABLE_NLS -# include <libintl.h> -# undef _ -# define _(String) dgettext (PACKAGE, String) -# define Q_(String) g_strip_context ((String), gettext (String)) -# ifdef gettext_noop -# define N_(String) gettext_noop (String) -# else -# define N_(String) (String) -# endif -#else -# define textdomain(String) (String) -# define gettext(String) (String) -# define dgettext(Domain,Message) (Message) -# define dcgettext(Domain,Message,Type) (Message) -# define bindtextdomain(Domain,Directory) (Domain) -# define _(String) (String) -# define Q_(String) g_strip_context ((String), (String)) -# define N_(String) (String) -#endif - - -/* - * Public Functions. - */ - -/* - * This function returns a widget in a component created by Glade. - * Call it with the toplevel widget in the component (i.e. a window/dialog), - * or alternatively any widget in the component, and the name of the widget - * you want returned. - */ -GtkWidget* lookup_widget(GtkWidget* widget, const gchar* widget_name); diff --git a/GUI/meshGenGTK/meshGenGTK.C b/GUI/meshGenGTK/meshGenGTK.C deleted file mode 100644 index 1ca337a51e69754bc0c2aa80ca40f2def1c57b59..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTK.C +++ /dev/null @@ -1,88 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "objectRegistry.H" -#include "Time.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from objectRegistry -meshGenGTK::meshGenGTK -( - label argc, char* argv[], const objectRegistry& reg -) -: - meshGui_(reg), - generalPageFramePtr_(NULL), - mainWindowPtr_(NULL), - localRefinementFramePtr_(NULL), - keepCellsIntersectingPatchesFramePtr_(NULL), - bndLayersFramePtr_(NULL), - localSettingsMainFramePtr_(NULL), - - boxRefinementFramePtr_(NULL), - lineRefinementFramePtr_(NULL), - coneRefinementFramePtr_(NULL), - sphereRefinementFramePtr_(NULL), - objectRefinementMainFramePtr_(NULL), - - renameBoundaryFramePtr_(NULL) -{ - gtk_init(&argc, &argv); - - createLocalSettingsMainWindowPage(); - createGeneralPage(); - createObjectRefinementMainWindowPage(); - createRenameBoundaryMainWindowPage(); - createMainWindowPage(); - - gtk_main(); -} - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -meshGenGTK::~meshGenGTK() -{ - meshGui_.writeDict(); - gtk_main_quit(); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTK.H b/GUI/meshGenGTK/meshGenGTK.H deleted file mode 100644 index 505108f73e8d64acc9c8eec5ba33aa8caed587f9..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTK.H +++ /dev/null @@ -1,140 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Class - meshGenGTK - -Description - Graphical user inteface using GTK - -SourceFiles - meshGenGTK.C - -\*---------------------------------------------------------------------------*/ - -#ifndef meshGenGTK_H -#define meshGenGTK_H - -#include "meshGenGUI.H" - -#include <gtk/gtk.h> - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -//- Forward declarations -class triSurface; - -static meshGenGUI* guiPtr(NULL); - -/*---------------------------------------------------------------------------*\ - Class meshGenGTK Declaration -\*---------------------------------------------------------------------------*/ - -class meshGenGTK -{ - // Private data - - //- mesh generation dictionary - meshGenGUI meshGui_; - - //- pages - GtkWidget* generalPageFramePtr_; - GtkWidget* mainWindowPtr_; - GtkWidget* localRefinementFramePtr_; - GtkWidget* keepCellsIntersectingPatchesFramePtr_; - GtkWidget* bndLayersFramePtr_; - GtkWidget* localSettingsMainFramePtr_; - - GtkWidget* boxRefinementFramePtr_; - GtkWidget* lineRefinementFramePtr_; - GtkWidget* coneRefinementFramePtr_; - GtkWidget* sphereRefinementFramePtr_; - GtkWidget* objectRefinementMainFramePtr_; - - GtkWidget* renameBoundaryFramePtr_; - -private: - - // Private member functions - //- create pages - void createGeneralPage(); - void createMainWindowPage(); - - //- pages for local features - void createLocalRefinementWindowPage(); - void createKeepCellsIntersectingPatchesWindowPage(); - void createBndLayersWindowPage(); - void createLocalSettingsMainWindowPage(); - - //- pages for object refinement - void createBoxRefinementWindowPage(); - void createLineRefinementWindowPage(); - void createConeRefinementWindowPage(); - void createSphereRefinementWindowPage(); - void createObjectRefinementMainWindowPage(); - - //- pages for boundary renaming - void createRenameBoundaryMainWindowPage(); - - //- Disallow default bitwise copy construct - meshGenGTK(const meshGenGTK&); - - //- Disallow default bitwise assignment - void operator=(const meshGenGTK&); - -public: - - // Constructors - - //- Construct from registry - meshGenGTK(label argc, char* argv[], const objectRegistry&); - - // Destructor - - ~meshGenGTK(); - - // Member Functions -}; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#define GLADE_HOOKUP_OBJECT(component,widget,name) \ - g_object_set_data_full(G_OBJECT(component), name, \ - gtk_widget_ref(widget), (GDestroyNotify)gtk_widget_unref) - -#define GLADE_HOOKUP_OBJECT_NO_REF(component,widget,name) \ - g_object_set_data(G_OBJECT(component), name, widget) - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKBndLayers.C b/GUI/meshGenGTK/meshGenGTKBndLayers.C deleted file mode 100644 index 44a383ea459aa0d252ba41824df71ec4ddc9ddeb..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKBndLayers.C +++ /dev/null @@ -1,421 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "triSurface.H" -#include "HashSet.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -//- callback functions - -extern "C" -{ - -static void updateBndLayers(GtkWidget* bndLayersFramePtr) -{ - GtkWidget* comboboxentry_bndLayers_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(bndLayersFramePtr), - "comboboxentry_bndLayers_availablePatches" - ); - GtkWidget* comboboxentry_bndLayers_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(bndLayersFramePtr), - "comboboxentry_bndLayers_selectedPatches" - ); - - //- update available patches - wordList alreadyUsed = guiPtr->keepBndLayersPatches(); - wordHashSet usedNames; - forAll(alreadyUsed, nameI) - usedNames.insert(alreadyUsed[nameI]); - - GList* avPatches = 0; - label nAvailable(0); - const triSurface& surf = guiPtr->surface(); - forAll(surf.patches(), patchI) - { - if( usedNames.found(surf.patches()[patchI].name()) ) - continue; - const char* name = surf.patches()[patchI].name().c_str(); - avPatches = g_list_append(avPatches, const_cast<char*>(name)); - ++nAvailable; - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_bndLayers_availablePatches - ), avPatches - ); - - if( nAvailable == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_bndLayers_availablePatches - )->entry - ), "" - ); - } - - //- update used patches - GList* selPatches = 0; - forAll(alreadyUsed, patchI) - { - const char* name = alreadyUsed[patchI].c_str(); - selPatches = g_list_append(selPatches, const_cast<char*>(name)); - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_bndLayers_selectedPatches - ), selPatches - ); - - if( alreadyUsed.size() == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_bndLayers_selectedPatches - )->entry - ), "" - ); - } - - g_list_free(avPatches); - g_list_free(selPatches); -} - -static void addBndLayersPatches(GtkWidget* widget, GtkWidget* bndLayersFramePtr) -{ - GtkWidget* comboboxentry_bndLayers_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(bndLayersFramePtr), - "comboboxentry_bndLayers_availablePatches" - ); - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_bndLayers_availablePatches - )->entry - ) - ); - - if( name == "" ) - return; - - guiPtr->addBndLayersPatches(name); - - updateBndLayers(bndLayersFramePtr); -} - -static void removeBndLayersPatches -( - GtkWidget* widget, - GtkWidget* bndLayersFramePtr -) -{ - GtkWidget* comboboxentry_bndLayers_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(bndLayersFramePtr), - "comboboxentry_bndLayers_selectedPatches" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_bndLayers_selectedPatches - )->entry - ) - ); - - if( name == "" ) - return; - - guiPtr->removeBndLayersPatches(name); - - updateBndLayers(bndLayersFramePtr); -} - -} - -void meshGenGTK::createBndLayersWindowPage() -{ - guiPtr = &meshGui_; - - bndLayersFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(2, 3, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(bndLayersFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set label for available patches - GtkWidget* label_bndLayers_availablePatches = - gtk_label_new("Available patches"); - gtk_widget_show(label_bndLayers_availablePatches); - gtk_table_attach - ( - GTK_TABLE(table1), - label_bndLayers_availablePatches, - 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions) (0), 0, 0 - ); - gtk_misc_set_alignment - ( - GTK_MISC(label_bndLayers_availablePatches), - 0, - 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the combo box for available patches - GtkWidget* comboboxentry_bndLayers_availablePatches = - gtk_combo_new(); - gtk_widget_show - ( - comboboxentry_bndLayers_availablePatches - ); - gtk_table_attach - ( - GTK_TABLE(table1), - comboboxentry_bndLayers_availablePatches, - 1, 2, 0, 1, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(GTK_FILL), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO(comboboxentry_bndLayers_availablePatches)->entry - ), - 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding patches - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 2, 3, 0, 1, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addBndLayersPatches), - bndLayersFramePtr_ - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set label for selected patches - GtkWidget* label_bndLayers_selectedPatches = - gtk_label_new("Selected patches"); - gtk_widget_show(label_bndLayers_selectedPatches); - gtk_table_attach - ( - GTK_TABLE(table1), - label_bndLayers_selectedPatches, - 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - gtk_misc_set_alignment - ( - GTK_MISC(label_bndLayers_selectedPatches), - 0, - 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the combo box for selected patches - GtkWidget* comboboxentry_bndLayers_selectedPatches = - gtk_combo_new(); - gtk_widget_show(comboboxentry_bndLayers_selectedPatches); - gtk_table_attach - ( - GTK_TABLE(table1), - comboboxentry_bndLayers_selectedPatches, - 1, 2, 1, 2, - (GtkAttachOptions) (GTK_FILL), (GtkAttachOptions) (GTK_FILL), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO(comboboxentry_bndLayers_selectedPatches)->entry - ), - 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing patches - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 2, 3, 1, 2, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removeBndLayersPatches), - bndLayersFramePtr_ - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - bndLayersFramePtr_, - bndLayersFramePtr_, - "Cell intersecting patches frame" - ); - GLADE_HOOKUP_OBJECT - ( - bndLayersFramePtr_, - comboboxentry_bndLayers_availablePatches, - "comboboxentry_bndLayers_availablePatches" - ); - GLADE_HOOKUP_OBJECT - ( - bndLayersFramePtr_, - button1, - "button1" - ); - GLADE_HOOKUP_OBJECT - ( - bndLayersFramePtr_, - label_bndLayers_selectedPatches, - "label_bndLayers_selectedPatches" - ); - GLADE_HOOKUP_OBJECT - ( - bndLayersFramePtr_, - comboboxentry_bndLayers_selectedPatches, - "comboboxentry_bndLayers_selectedPatches" - ); - GLADE_HOOKUP_OBJECT - ( - bndLayersFramePtr_, - button2, - "button2" - ); - - updateBndLayers(bndLayersFramePtr_); - - gtk_widget_show(bndLayersFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKBoxRefinement.C b/GUI/meshGenGTK/meshGenGTKBoxRefinement.C deleted file mode 100644 index e9ba591ee28c0e0c04745583748062c7bc01c3e0..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKBoxRefinement.C +++ /dev/null @@ -1,1047 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "boxRefinement.H" -#include "helperFunctions.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -//- callback functions - -extern "C" -{ - -static void showDataForBoxRefinement -( - GtkWidget* widget, - GtkWidget* boxRefinementFramePtr -) -{ - GtkWidget* comboboxentry_boxRefinement_createdBoxes = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "comboboxentry_boxRefinement_createdBoxes" - ); - GtkWidget* entry_boxRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCellSize" - ); - GtkWidget* entry_boxRefinement_selectedCentreX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCentreX" - ); - GtkWidget* entry_boxRefinement_selectedCentreY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCentreY" - ); - GtkWidget* entry_boxRefinement_selectedCentreZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCentreZ" - ); - GtkWidget* entry_boxRefinement_selectedLengthX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedLengthX" - ); - GtkWidget* entry_boxRefinement_selectedLengthY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedLengthY" - ); - GtkWidget* entry_boxRefinement_selectedLengthZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedLengthZ" - ); - - //- find the object in the dictionary - const word boxName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_boxRefinement_createdBoxes)->entry - ) - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - - forAll(refs, refI) - if( refs[refI].keyword() == boxName ) - { - const dictionary dict = refs[refI].dict(); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_boxRefinement_selectedCellSize), - help::scalarToText - ( - scalar(readScalar(dict.lookup("cellSize"))) - ).c_str() - ); - const vector centre(dict.lookup("centre")); - gtk_entry_set_text - ( - GTK_ENTRY(entry_boxRefinement_selectedCentreX), - help::scalarToText(centre.x()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_boxRefinement_selectedCentreY), - help::scalarToText(centre.y()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_boxRefinement_selectedCentreZ), - help::scalarToText(centre.z()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_boxRefinement_selectedLengthX), - help::scalarToText(readScalar(dict.lookup("lengthX"))).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_boxRefinement_selectedLengthY), - help::scalarToText(readScalar(dict.lookup("lengthY"))).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_boxRefinement_selectedLengthZ), - help::scalarToText(readScalar(dict.lookup("lengthZ"))).c_str() - ); - - return; - } - - gtk_entry_set_text(GTK_ENTRY(entry_boxRefinement_selectedCellSize), ""); - gtk_entry_set_text(GTK_ENTRY(entry_boxRefinement_selectedCentreX), ""); - gtk_entry_set_text(GTK_ENTRY(entry_boxRefinement_selectedCentreY), ""); - gtk_entry_set_text(GTK_ENTRY(entry_boxRefinement_selectedCentreZ), ""); - gtk_entry_set_text(GTK_ENTRY(entry_boxRefinement_selectedLengthX), ""); - gtk_entry_set_text(GTK_ENTRY(entry_boxRefinement_selectedLengthY), ""); - gtk_entry_set_text(GTK_ENTRY(entry_boxRefinement_selectedLengthZ), ""); -} - -static void resetValuesForSelectedBox -( - GtkWidget* widget, - GtkWidget* boxRefinementFramePtr -) -{ - GtkWidget* comboboxentry_boxRefinement_createdBoxes = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "comboboxentry_boxRefinement_createdBoxes" - ); - GtkWidget* entry_boxRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCellSize" - ); - GtkWidget* entry_boxRefinement_selectedCentreX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCentreX" - ); - GtkWidget* entry_boxRefinement_selectedCentreY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCentreY" - ); - GtkWidget* entry_boxRefinement_selectedCentreZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedCentreZ" - ); - GtkWidget* entry_boxRefinement_selectedLengthX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedLengthX" - ); - GtkWidget* entry_boxRefinement_selectedLengthY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedLengthY" - ); - GtkWidget* entry_boxRefinement_selectedLengthZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_selectedLengthZ" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_boxRefinement_createdBoxes - )->entry - ) - ); - - if( name == "" ) - return; - - const PtrList<entry> refs = guiPtr->objectRefinements(); - dictionary dict; - forAll(refs, refI) - if( refs[refI].keyword() == name ) - dict = refs[refI].dict(); - guiPtr->removeObjectRefinement(name); - if( widget == entry_boxRefinement_selectedCellSize ) - { - const word size = - gtk_entry_get_text(GTK_ENTRY(entry_boxRefinement_selectedCellSize)); - dict.remove("cellSize"); - dict.add("cellSize", help::textToScalar(size)); - } - else if( widget == entry_boxRefinement_selectedCentreX ) - { - point centre(dict.lookup("centre")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_boxRefinement_selectedCentreX)); - dict.remove("centre"); - centre.x() = help::textToScalar(c); - dict.add("centre", centre); - } - else if( widget == entry_boxRefinement_selectedCentreY ) - { - point centre(dict.lookup("centre")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_boxRefinement_selectedCentreY)); - dict.remove("centre"); - centre.y() = help::textToScalar(c); - dict.add("centre", centre); - } - else if( widget == entry_boxRefinement_selectedCentreZ ) - { - point centre(dict.lookup("centre")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_boxRefinement_selectedCentreZ)); - dict.remove("centre"); - centre.z() = help::textToScalar(c); - dict.add("centre", centre); - } - else if( widget == entry_boxRefinement_selectedLengthX ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_boxRefinement_selectedLengthX)); - dict.remove("lengthX"); - dict.add("lengthX", help::textToScalar(l)); - } - else if( widget == entry_boxRefinement_selectedLengthY ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_boxRefinement_selectedLengthY)); - dict.remove("lengthY"); - dict.add("lengthY", help::textToScalar(l)); - } - else if( widget == entry_boxRefinement_selectedLengthZ ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_boxRefinement_selectedLengthZ)); - dict.remove("lengthZ"); - dict.add("lengthZ", help::textToScalar(l)); - } - - boxRefinement br(name, dict); - guiPtr->addObjectRefinement(br); -} - -static void updateBoxRefinements(GtkWidget* boxRefinementFramePtr) -{ - GtkWidget* comboboxentry_boxRefinement_createdBoxes = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "comboboxentry_boxRefinement_createdBoxes" - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - label nBoxes(0); - GList* createdBoxes = 0; - forAll(refs, refI) - { - const word& key = refs[refI].keyword(); - const dictionary& dict = refs[refI].dict(); - const word type(dict.lookup("type")); - - if( type == "box" ) - { - ++nBoxes; - boxRefinement br(key, dict); - createdBoxes = - g_list_append - ( - createdBoxes, - const_cast<char*>(br.name().c_str()) - ); - } - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_boxRefinement_createdBoxes - ), createdBoxes - ); - - if( nBoxes == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_boxRefinement_createdBoxes)->entry - ), - "" - ); - } - - g_list_free(createdBoxes); - - showDataForBoxRefinement(NULL, boxRefinementFramePtr); -} - -static void addBoxRefinement -( - GtkWidget* button, - GtkWidget* boxRefinementFramePtr -) -{ - GtkWidget* name = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxName" - ); - GtkWidget* cellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_cellSize" - ); - GtkWidget* centreX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_centreX" - ); - GtkWidget* centreY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_centreY" - ); - GtkWidget* centreZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_centreZ" - ); - GtkWidget* lengthX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_lengthX" - ); - GtkWidget* lengthY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_lengthY" - ); - GtkWidget* lengthZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "entry_boxRefinement_lengthZ" - ); - - //- create all necessary settings - const word boxName = gtk_entry_get_text(GTK_ENTRY(name)); - gtk_entry_set_text(GTK_ENTRY(name), ""); - const scalar boxCellSize = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(cellSize))); - gtk_entry_set_text(GTK_ENTRY(cellSize), ""); - point centre; - centre.x() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(centreX))); - gtk_entry_set_text(GTK_ENTRY(centreX), ""); - centre.y() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(centreY))); - gtk_entry_set_text(GTK_ENTRY(centreY), ""); - centre.z() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(centreZ))); - gtk_entry_set_text(GTK_ENTRY(centreZ), ""); - const scalar boxLengthX = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(lengthX))); - gtk_entry_set_text(GTK_ENTRY(lengthX), ""); - const scalar boxLengthY = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(lengthY))); - gtk_entry_set_text(GTK_ENTRY(lengthY), ""); - const scalar boxLengthZ = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(lengthZ))); - gtk_entry_set_text(GTK_ENTRY(lengthZ), ""); - - boxRefinement box - ( - boxName, - boxCellSize, - centre, - boxLengthX, - boxLengthY, - boxLengthZ - ); - - guiPtr->addObjectRefinement(box); - - updateBoxRefinements(boxRefinementFramePtr); -} - -static void removeBoxRefinement -( - GtkWidget* button, - GtkWidget* boxRefinementFramePtr -) -{ - GtkWidget* createdBoxes = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(boxRefinementFramePtr), - "comboboxentry_boxRefinement_createdBoxes" - ); - - const word boxName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(createdBoxes)->entry - ) - ); - - guiPtr->removeObjectRefinement(boxName); - - updateBoxRefinements(boxRefinementFramePtr); -} - -} - -void meshGenGTK::createBoxRefinementWindowPage() -{ - guiPtr = &meshGui_; - - boxRefinementFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(5, 11, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(boxRefinementFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for box name - GtkWidget* label_boxName = gtk_label_new("Box name"); - gtk_widget_show(label_boxName); - gtk_table_attach(GTK_TABLE(table1), label_boxName, 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_boxName), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create an entry for box name - GtkWidget* entry_boxName = gtk_entry_new(); - gtk_widget_show(entry_boxName); - - gtk_table_attach(GTK_TABLE(table1), entry_boxName, 1, 4, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* label_boxRefinement_cellSize = gtk_label_new("Cell size [m]"); - gtk_widget_show(label_boxRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), label_boxRefinement_cellSize, - 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_boxRefinement_cellSize), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* entry_boxRefinement_cellSize = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_cellSize, - 1, 4, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - GtkWidget* label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for box centre - GtkWidget* label_boxRefinement_centre = gtk_label_new("Centre"); - gtk_widget_show(label_boxRefinement_centre); - gtk_table_attach(GTK_TABLE(table1), label_boxRefinement_centre, - 0, 1, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_boxRefinement_centre), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for box centre - GtkWidget* entry_boxRefinement_centreX = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_centreX); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_centreX, - 1, 2, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_centreY = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_centreY); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_centreY, - 2, 3, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_centreZ = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_centreZ); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_centreZ, - 3, 4, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for side lengths - GtkWidget* label_boxRefinement_lengths = gtk_label_new("Side lengths"); - gtk_widget_show(label_boxRefinement_lengths); - gtk_table_attach(GTK_TABLE(table1), label_boxRefinement_lengths, - 0, 1, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_boxRefinement_lengths), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for side lengths - GtkWidget* entry_boxRefinement_lengthX = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_lengthX); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_lengthX, - 1, 2, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_lengthY = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_lengthY); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_lengthY, - 2, 3, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_lengthZ = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_lengthZ); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_lengthZ, - 3, 4, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding boxes - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 4, 5, 0, 5, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addBoxRefinement), - boxRefinementFramePtr_ - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- horizontal separator - GtkWidget* hseparator0 = gtk_hseparator_new(); - gtk_widget_show(hseparator0); - gtk_table_attach(GTK_TABLE(table1), hseparator0, 0, 5, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for existing box objects - GtkWidget* label_boxRefinement_existing = gtk_label_new("Existing boxes"); - gtk_widget_show(label_boxRefinement_existing); - gtk_table_attach(GTK_TABLE(table1), label_boxRefinement_existing, - 0, 1, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- combobox for existing box objects - GtkWidget* comboboxentry_boxRefinement_createdBoxes = - gtk_combo_new(); - gtk_widget_show(comboboxentry_boxRefinement_createdBoxes); - gtk_table_attach(GTK_TABLE(table1),comboboxentry_boxRefinement_createdBoxes, - 1, 2, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO(comboboxentry_boxRefinement_createdBoxes)->entry - ), - 0 - ); - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* label_boxRefinement_selectedCellSize = - gtk_label_new("Cell size [m]"); - gtk_widget_show(label_boxRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), label_boxRefinement_selectedCellSize, - 0, 1, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_boxRefinement_selectedCellSize), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* entry_boxRefinement_selectedCellSize = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_selectedCellSize, - 1, 4, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for box centre - GtkWidget* label_boxRefinement_selectedCentre = gtk_label_new("Centre"); - gtk_widget_show(label_boxRefinement_selectedCentre); - gtk_table_attach(GTK_TABLE(table1), label_boxRefinement_selectedCentre, - 0, 1, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_boxRefinement_selectedCentre), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for selected box centre - GtkWidget* entry_boxRefinement_selectedCentreX = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_selectedCentreX); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_selectedCentreX, - 1, 2, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_selectedCentreY = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_selectedCentreY); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_selectedCentreY, - 2, 3, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_selectedCentreZ = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_selectedCentreZ); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_selectedCentreZ, - 3, 4, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for selected side lengths - GtkWidget* label_boxRefinement_selectedLengths = - gtk_label_new("Side lengths"); - gtk_widget_show(label_boxRefinement_selectedLengths); - gtk_table_attach(GTK_TABLE(table1), label_boxRefinement_selectedLengths, - 0, 1, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_boxRefinement_selectedLengths), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for side lengths - GtkWidget* entry_boxRefinement_selectedLengthX = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_selectedLengthX); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_selectedLengthX, - 1, 2, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_selectedLengthY = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_selectedLengthY); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_selectedLengthY, - 2, 3, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_boxRefinement_selectedLengthZ = gtk_entry_new(); - gtk_widget_show(entry_boxRefinement_selectedLengthZ); - gtk_table_attach(GTK_TABLE(table1), entry_boxRefinement_selectedLengthZ, - 3, 4, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing patches - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 4, 5, 6, 11, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removeBoxRefinement), - boxRefinementFramePtr_ - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - boxRefinementFramePtr_, - boxRefinementFramePtr_, - "boxRefinementFramePtr_"); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - table1, - "table1" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxName, - "entry_boxName" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_cellSize, - "entry_boxRefinement_cellSize" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_centreX, - "entry_boxRefinement_centreX" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_centreY, - "entry_boxRefinement_centreY" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_centreZ, - "entry_boxRefinement_centreZ" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_lengthX, - "entry_boxRefinement_lengthX" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_lengthY, - "entry_boxRefinement_lengthY" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_lengthZ, - "entry_boxRefinement_lengthZ" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - comboboxentry_boxRefinement_createdBoxes, - "comboboxentry_boxRefinement_createdBoxes" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_selectedCellSize, - "entry_boxRefinement_selectedCellSize" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_selectedCentreX, - "entry_boxRefinement_selectedCentreX" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_selectedCentreY, - "entry_boxRefinement_selectedCentreY" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_selectedCentreZ, - "entry_boxRefinement_selectedCentreZ" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_selectedLengthX, - "entry_boxRefinement_selectedLengthX" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_selectedLengthY, - "entry_boxRefinement_selectedLengthY" - ); - GLADE_HOOKUP_OBJECT - ( - boxRefinementFramePtr_, - entry_boxRefinement_selectedLengthZ, - "entry_boxRefinement_selectedLengthZ" - ); - - updateBoxRefinements(boxRefinementFramePtr_); - - g_signal_connect - ( - G_OBJECT - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_boxRefinement_createdBoxes)->entry - ) - ), - "changed", - G_CALLBACK(showDataForBoxRefinement), - boxRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_boxRefinement_selectedCellSize), - "changed", - G_CALLBACK(resetValuesForSelectedBox), - boxRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_boxRefinement_selectedCentreX), - "changed", - G_CALLBACK(resetValuesForSelectedBox), - boxRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_boxRefinement_selectedCentreY), - "changed", - G_CALLBACK(resetValuesForSelectedBox), - boxRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_boxRefinement_selectedCentreZ), - "changed", - G_CALLBACK(resetValuesForSelectedBox), - boxRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_boxRefinement_selectedLengthX), - "changed", - G_CALLBACK(resetValuesForSelectedBox), - boxRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_boxRefinement_selectedLengthY), - "changed", - G_CALLBACK(resetValuesForSelectedBox), - boxRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_boxRefinement_selectedLengthZ), - "changed", - G_CALLBACK(resetValuesForSelectedBox), - boxRefinementFramePtr_ - ); - - gtk_widget_show(boxRefinementFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKConeRefinement.C b/GUI/meshGenGTK/meshGenGTKConeRefinement.C deleted file mode 100644 index 43b978e83eadba3fd8e2f7d167cb761bee0c241c..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKConeRefinement.C +++ /dev/null @@ -1,1244 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "coneRefinement.H" -#include "helperFunctions.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -//- callback functions - -extern "C" -{ - -static void showDataForConeRefinement -( - GtkWidget* widget, - GtkWidget* coneRefinementFramePtr -) -{ - GtkWidget* comboboxentry_coneRefinement_createdCones = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "comboboxentry_coneRefinement_createdCones" - ); - GtkWidget* entry_coneRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedCellSize" - ); - GtkWidget* entry_coneRefinement_selectedP0X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP0X" - ); - GtkWidget* entry_coneRefinement_selectedP0Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP0Y" - ); - GtkWidget* entry_coneRefinement_selectedP0Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP0Z" - ); - GtkWidget* entry_coneRefinement_selectedRadius0 = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedRadius0" - ); - GtkWidget* entry_coneRefinement_selectedP1X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP1X" - ); - GtkWidget* entry_coneRefinement_selectedP1Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP1Y" - ); - GtkWidget* entry_coneRefinement_selectedP1Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP1Z" - ); - GtkWidget* entry_coneRefinement_selectedRadius1 = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedRadius1" - ); - - //- find the object in the dictionary - const word coneName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_coneRefinement_createdCones)->entry - ) - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - - forAll(refs, refI) - if( refs[refI].keyword() == coneName ) - { - const dictionary dict = refs[refI].dict(); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedCellSize), - help::scalarToText - ( - scalar(readScalar(dict.lookup("cellSize"))) - ).c_str() - ); - const vector p0(dict.lookup("p0")); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedP0X), - help::scalarToText(p0.x()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedP0Y), - help::scalarToText(p0.y()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedP0Z), - help::scalarToText(p0.z()).c_str() - ); - const scalar r0(readScalar(dict.lookup("radius0"))); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedRadius0), - help::scalarToText(r0).c_str() - ); - - const vector p1(dict.lookup("p1")); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedP1X), - help::scalarToText(p1.x()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedP1Y), - help::scalarToText(p1.y()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedP1Z), - help::scalarToText(p1.z()).c_str() - ); - const scalar r1(readScalar(dict.lookup("radius1"))); - gtk_entry_set_text - ( - GTK_ENTRY(entry_coneRefinement_selectedRadius1), - help::scalarToText(r1).c_str() - ); - - return; - } - - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedCellSize), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedP0X), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedP0Y), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedP0Z), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedRadius0), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedP1X), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedP1Y), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedP1Z), ""); - gtk_entry_set_text(GTK_ENTRY(entry_coneRefinement_selectedRadius1), ""); -} - -static void resetValuesForSelectedCone -( - GtkWidget* widget, - GtkWidget* coneRefinementFramePtr -) -{ - GtkWidget* comboboxentry_coneRefinement_createdCones = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "comboboxentry_coneRefinement_createdCones" - ); - GtkWidget* entry_coneRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedCellSize" - ); - GtkWidget* entry_coneRefinement_selectedP0X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP0X" - ); - GtkWidget* entry_coneRefinement_selectedP0Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP0Y" - ); - GtkWidget* entry_coneRefinement_selectedP0Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP0Z" - ); - GtkWidget* entry_coneRefinement_selectedRadius0 = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedRadius0" - ); - GtkWidget* entry_coneRefinement_selectedP1X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP1X" - ); - GtkWidget* entry_coneRefinement_selectedP1Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP1Y" - ); - GtkWidget* entry_coneRefinement_selectedP1Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedP1Z" - ); - GtkWidget* entry_coneRefinement_selectedRadius1 = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_selectedRadius1" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_coneRefinement_createdCones - )->entry - ) - ); - - if( name == "" ) - return; - - const PtrList<entry> refs = guiPtr->objectRefinements(); - dictionary dict; - forAll(refs, refI) - if( refs[refI].keyword() == name ) - dict = refs[refI].dict(); - guiPtr->removeObjectRefinement(name); - if( widget == entry_coneRefinement_selectedCellSize ) - { - const word size = - gtk_entry_get_text(GTK_ENTRY(entry_coneRefinement_selectedCellSize)); - dict.remove("cellSize"); - dict.add("cellSize", help::textToScalar(size)); - } - else if( widget == entry_coneRefinement_selectedP0X ) - { - point p0(dict.lookup("p0")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_coneRefinement_selectedP0X)); - dict.remove("p0"); - p0.x() = help::textToScalar(c); - dict.add("p0", p0); - } - else if( widget == entry_coneRefinement_selectedP0Y ) - { - point p0(dict.lookup("p0")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_coneRefinement_selectedP0Y)); - dict.remove("p0"); - p0.y() = help::textToScalar(c); - dict.add("p0", p0); - } - else if( widget == entry_coneRefinement_selectedP0Z ) - { - point p0(dict.lookup("p0")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_coneRefinement_selectedP0Z)); - dict.remove("p0"); - p0.z() = help::textToScalar(c); - dict.add("p0", p0); - } - else if( widget == entry_coneRefinement_selectedRadius0 ) - { - scalar r0(readScalar(dict.lookup("radius0"))); - const word c = - gtk_entry_get_text - ( - GTK_ENTRY(entry_coneRefinement_selectedRadius0) - ); - dict.remove("radius0"); - r0 = help::textToScalar(c); - dict.add("radius0", r0); - } - else if( widget == entry_coneRefinement_selectedP1X ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_coneRefinement_selectedP1X)); - point p1(dict.lookup("p1")); - dict.remove("p1"); - p1.x() = help::textToScalar(l); - dict.add("p1", p1); - } - else if( widget == entry_coneRefinement_selectedP1Y ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_coneRefinement_selectedP1Y)); - point p1(dict.lookup("p1")); - dict.remove("p1"); - p1.y() = help::textToScalar(l); - dict.add("p1", p1); - } - else if( widget == entry_coneRefinement_selectedP1Z ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_coneRefinement_selectedP1Z)); - point p1(dict.lookup("p1")); - dict.remove("p1"); - p1.z() = help::textToScalar(l); - dict.add("p1", p1); - } - else if( widget == entry_coneRefinement_selectedRadius1 ) - { - scalar r1(readScalar(dict.lookup("radius1"))); - const word c = - gtk_entry_get_text - ( - GTK_ENTRY(entry_coneRefinement_selectedRadius1) - ); - dict.remove("radius1"); - r1 = help::textToScalar(c); - dict.add("radius1", r1); - } - - coneRefinement cr(name, dict); - guiPtr->addObjectRefinement(cr); -} - -static void updateConeRefinements(GtkWidget* coneRefinementFramePtr) -{ - GtkWidget* comboboxentry_coneRefinement_createdCones = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "comboboxentry_coneRefinement_createdCones" - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - label nCones(0); - GList* createdCones = 0; - forAll(refs, refI) - { - const word& key = refs[refI].keyword(); - const dictionary& dict = refs[refI].dict(); - const word type(dict.lookup("type")); - - if( type == "cone" ) - { - ++nCones; - coneRefinement cone(key, dict); - createdCones = - g_list_append - ( - createdCones, - const_cast<char*>(cone.name().c_str()) - ); - } - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_coneRefinement_createdCones - ), createdCones - ); - - if( nCones == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_coneRefinement_createdCones)->entry - ), - "" - ); - } - - g_list_free(createdCones); - - showDataForConeRefinement(NULL, coneRefinementFramePtr); -} - -static void addConeRefinement -( - GtkWidget* button, - GtkWidget* coneRefinementFramePtr -) -{ - GtkWidget* name = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneName" - ); - GtkWidget* cellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_cellSize" - ); - GtkWidget* p0X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_p0X" - ); - GtkWidget* p0Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_p0Y" - ); - GtkWidget* p0Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_p0Z" - ); - GtkWidget* r0 = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_radius0" - ); - GtkWidget* p1X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_p1X" - ); - GtkWidget* p1Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_p1Y" - ); - GtkWidget* p1Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_p1Z" - ); - GtkWidget* r1 = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "entry_coneRefinement_radius1" - ); - - //- create all necessary settings - const word coneName = gtk_entry_get_text(GTK_ENTRY(name)); - gtk_entry_set_text(GTK_ENTRY(name), ""); - const scalar coneCellSize = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(cellSize))); - gtk_entry_set_text(GTK_ENTRY(cellSize), ""); - point p0, p1; - scalar radius0, radius1; - p0.x() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p0X))); - gtk_entry_set_text(GTK_ENTRY(p0X), ""); - p0.y() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p0Y))); - gtk_entry_set_text(GTK_ENTRY(p0Y), ""); - p0.z() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p0Z))); - gtk_entry_set_text(GTK_ENTRY(p0Z), ""); - radius0 = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(r0))); - gtk_entry_set_text(GTK_ENTRY(r0), ""); - p1.x() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p1X))); - gtk_entry_set_text(GTK_ENTRY(p1X), ""); - p1.y() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p1Y))); - gtk_entry_set_text(GTK_ENTRY(p1Y), ""); - p1.z() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p1Z))); - gtk_entry_set_text(GTK_ENTRY(p1Z), ""); - radius1 = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(r1))); - gtk_entry_set_text(GTK_ENTRY(r1), ""); - - coneRefinement cone - ( - coneName, - coneCellSize, - p0, - radius0, - p1, - radius1 - ); - - guiPtr->addObjectRefinement(cone); - - updateConeRefinements(coneRefinementFramePtr); -} - -static void removeConeRefinement -( - GtkWidget* button, - GtkWidget* coneRefinementFramePtr -) -{ - GtkWidget* createdCones = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(coneRefinementFramePtr), - "comboboxentry_coneRefinement_createdCones" - ); - - const word coneName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(createdCones)->entry - ) - ); - - guiPtr->removeObjectRefinement(coneName); - - updateConeRefinements(coneRefinementFramePtr); -} - -} - -void meshGenGTK::createConeRefinementWindowPage() -{ - guiPtr = &meshGui_; - - coneRefinementFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(5, 15, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(coneRefinementFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for cone name - GtkWidget* label_coneName = gtk_label_new("Cone name"); - gtk_widget_show(label_coneName); - gtk_table_attach(GTK_TABLE(table1), label_coneName, 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_coneName), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create an entry for cone name - GtkWidget* entry_coneName = gtk_entry_new(); - gtk_widget_show(entry_coneName); - - gtk_table_attach(GTK_TABLE(table1), entry_coneName, 1, 4, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* label_coneRefinement_cellSize = gtk_label_new("Cell size [m]"); - gtk_widget_show(label_coneRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_cellSize, - 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_coneRefinement_cellSize), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* entry_coneRefinement_cellSize = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_cellSize, - 1, 4, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - GtkWidget* label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for p0 - GtkWidget* label_coneRefinement_p0 = gtk_label_new("Starting point"); - gtk_widget_show(label_coneRefinement_p0); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_p0, - 0, 1, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_coneRefinement_p0), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for p0 - GtkWidget* entry_coneRefinement_p0X = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_p0X); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_p0X, - 1, 2, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_p0Y = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_p0Y); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_p0Y, - 2, 3, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_p0Z = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_p0Z); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_p0Z, - 3, 4, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for p1 - GtkWidget* label_coneRefinement_p1 = gtk_label_new("End point"); - gtk_widget_show(label_coneRefinement_p1); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_p1, - 0, 1, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_coneRefinement_p1), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for p1 - GtkWidget* entry_coneRefinement_p1X = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_p1X); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_p1X, - 1, 2, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_p1Y = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_p1Y); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_p1Y, - 2, 3, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_p1Z = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_p1Z); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_p1Z, - 3, 4, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for radius0 - GtkWidget* label_coneRefinement_radius0 = - gtk_label_new("Starting radius [m]"); - gtk_widget_show(label_coneRefinement_radius0); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_radius0, - 0, 1, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_coneRefinement_radius0), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entry for radius0 - GtkWidget* entry_coneRefinement_radius0 = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_radius0); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_radius0, - 1, 4, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for radius1 - GtkWidget* label_coneRefinement_radius1 = gtk_label_new("End radius [m]"); - gtk_widget_show(label_coneRefinement_radius1); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_radius1, - 0, 1, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_coneRefinement_radius1), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entry for radius1 - GtkWidget* entry_coneRefinement_radius1 = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_radius1); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_radius1, - 1, 4, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding cones - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 4, 5, 0, 7, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addConeRefinement), - coneRefinementFramePtr_ - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- horizontal separator - GtkWidget* hseparator0 = gtk_hseparator_new(); - gtk_widget_show(hseparator0); - gtk_table_attach(GTK_TABLE(table1), hseparator0, 0, 5, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for existing cone objects - GtkWidget* label_coneRefinement_existing = gtk_label_new("Existing cones"); - gtk_widget_show(label_coneRefinement_existing); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_existing, - 0, 1, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- combobox for existing cone objects - GtkWidget* comboboxentry_coneRefinement_createdCones = - gtk_combo_new(); - gtk_widget_show(comboboxentry_coneRefinement_createdCones); - gtk_table_attach - ( - GTK_TABLE(table1),comboboxentry_coneRefinement_createdCones, - 1, 2, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO(comboboxentry_coneRefinement_createdCones)->entry - ), - 0 - ); - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* label_coneRefinement_selectedCellSize = - gtk_label_new("Cell size [m]"); - gtk_widget_show(label_coneRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_selectedCellSize, - 0, 1, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_coneRefinement_selectedCellSize), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* entry_coneRefinement_selectedCellSize = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedCellSize, - 1, 4, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for p0 - GtkWidget* label_coneRefinement_selectedP0 = - gtk_label_new("Starting point"); - gtk_widget_show(label_coneRefinement_selectedP0); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_selectedP0, - 0, 1, 11, 12, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_coneRefinement_selectedP0), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for selected p0 - GtkWidget* entry_coneRefinement_selectedP0X = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedP0X); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedP0X, - 1, 2, 11, 12, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_selectedP0Y = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedP0Y); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedP0Y, - 2, 3, 11, 12, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_selectedP0Z = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedP0Z); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedP0Z, - 3, 4, 11, 12, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for selected p1 - GtkWidget* label_coneRefinement_selectedP1 = - gtk_label_new("End point"); - gtk_widget_show(label_coneRefinement_selectedP1); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_selectedP1, - 0, 1, 12, 13, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_coneRefinement_selectedP1), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for p1 - GtkWidget* entry_coneRefinement_selectedP1X = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedP1X); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedP1X, - 1, 2, 12, 13, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_selectedP1Y = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedP1Y); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedP1Y, - 2, 3, 12, 13, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_coneRefinement_selectedP1Z = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedP1Z); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedP1Z, - 3, 4, 12, 13, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for selected radius0 - GtkWidget* label_coneRefinement_selectedRadius0 = - gtk_label_new("Starting radius [m]"); - gtk_widget_show(label_coneRefinement_selectedRadius0); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_selectedRadius0, - 0, 1, 13, 14, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_coneRefinement_selectedRadius0), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entry for selected radius0 - GtkWidget* entry_coneRefinement_selectedRadius0 = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedRadius0); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedRadius0, - 1, 4, 13, 14, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for radius1 - GtkWidget* label_coneRefinement_selectedRadius1 = - gtk_label_new("End radius [m]"); - gtk_widget_show(label_coneRefinement_selectedRadius1); - gtk_table_attach(GTK_TABLE(table1), label_coneRefinement_selectedRadius1, - 0, 1, 14, 15, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_coneRefinement_selectedRadius1), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entry for radius1 - GtkWidget* entry_coneRefinement_selectedRadius1 = gtk_entry_new(); - gtk_widget_show(entry_coneRefinement_selectedRadius1); - gtk_table_attach(GTK_TABLE(table1), entry_coneRefinement_selectedRadius1, - 1, 4, 14, 15, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing patches - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 4, 5, 8, 15, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removeConeRefinement), - coneRefinementFramePtr_ - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - coneRefinementFramePtr_, - coneRefinementFramePtr_, - "coneRefinementFramePtr_"); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - table1, - "table1" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneName, - "entry_coneName" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_cellSize, - "entry_coneRefinement_cellSize" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_p0X, - "entry_coneRefinement_p0X" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_p0Y, - "entry_coneRefinement_p0Y" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_radius0, - "entry_coneRefinement_radius0" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_radius1, - "entry_coneRefinement_radius1" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_p0Z, - "entry_coneRefinement_p0Z" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_p1X, - "entry_coneRefinement_p1X" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_p1Y, - "entry_coneRefinement_p1Y" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_p1Z, - "entry_coneRefinement_p1Z" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - comboboxentry_coneRefinement_createdCones, - "comboboxentry_coneRefinement_createdCones" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedCellSize, - "entry_coneRefinement_selectedCellSize" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedP0X, - "entry_coneRefinement_selectedP0X" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedP0Y, - "entry_coneRefinement_selectedP0Y" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedP0Z, - "entry_coneRefinement_selectedP0Z" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedRadius0, - "entry_coneRefinement_selectedRadius0" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedP1X, - "entry_coneRefinement_selectedP1X" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedP1Y, - "entry_coneRefinement_selectedP1Y" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedP1Z, - "entry_coneRefinement_selectedP1Z" - ); - GLADE_HOOKUP_OBJECT - ( - coneRefinementFramePtr_, - entry_coneRefinement_selectedRadius1, - "entry_coneRefinement_selectedRadius1" - ); - - updateConeRefinements(coneRefinementFramePtr_); - - g_signal_connect - ( - G_OBJECT - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_coneRefinement_createdCones)->entry - ) - ), - "changed", - G_CALLBACK(showDataForConeRefinement), - coneRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_coneRefinement_selectedCellSize), - "changed", - G_CALLBACK(resetValuesForSelectedCone), - coneRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_coneRefinement_selectedP0X), - "changed", - G_CALLBACK(resetValuesForSelectedCone), - coneRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_coneRefinement_selectedP0Y), - "changed", - G_CALLBACK(resetValuesForSelectedCone), - coneRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_coneRefinement_selectedP0Z), - "changed", - G_CALLBACK(resetValuesForSelectedCone), - coneRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_coneRefinement_selectedP1X), - "changed", - G_CALLBACK(resetValuesForSelectedCone), - coneRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_coneRefinement_selectedP1Y), - "changed", - G_CALLBACK(resetValuesForSelectedCone), - coneRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_coneRefinement_selectedP1Z), - "changed", - G_CALLBACK(resetValuesForSelectedCone), - coneRefinementFramePtr_ - ); - - gtk_widget_show(coneRefinementFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKGeneralPage.C b/GUI/meshGenGTK/meshGenGTKGeneralPage.C deleted file mode 100644 index 42be44f8e3ca3bcbeecf482ec843f73cd0391f55..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKGeneralPage.C +++ /dev/null @@ -1,559 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "helperFunctions.H" -#include "gtkHelpers.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -// callback functions - -extern "C" -{ - -static void useButtonCallback(GtkWidget* widget, gpointer data) -{ - if( (gchar*)data == "UseBndSize" ) - { - if( guiPtr->boundaryCellSizeEntryExist() ) - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 0); - guiPtr->removeBoundaryCellSize(); - } - else - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 1); - guiPtr->setBoundaryCellSize - ( - guiPtr->maxCellSize() - ); - } - } - else if( (gchar*)data == "UseAutoRef" ) - { - if( guiPtr->minCellSizeEntryExist() ) - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 0); - guiPtr->removeMinCellSize(); - } - else - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 1); - guiPtr->setMinCellSize(guiPtr->maxCellSize()); - } - } - else if( (gchar*)data == "UseKeepCellsIntersectingBoundary" ) - { - if( guiPtr->keepCellsIntersectingBoundaryEntryExist() ) - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 0); - guiPtr->removeKeepCellsIntersectingBoundary(); - - if( guiPtr->checkForGluedMeshEntryExist() ) - { - GtkWidget* checkButtonGluedMesh = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(widget), - "checkbutton_checkForGluedMesh" - ); - - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkButtonGluedMesh), - 0 - ); - guiPtr->removeCheckForGluedMesh(); - } - } - else - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 1); - guiPtr->setKeepCellsIntersectingBoundary(); - } - } - else if( (gchar*)(data) == "UseCheckForGluedMesh" ) - { - if( !guiPtr->keepCellsIntersectingBoundary() ) - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 0); - return; - } - - if( guiPtr->checkForGluedMeshEntryExist() ) - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 0); - guiPtr->removeCheckForGluedMesh(); - } - else - { - gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(widget), 1); - guiPtr->setCheckForGluedMesh(); - } - } -} - -static void enterSurfaceFile(GtkWidget* widget, GtkEntry* entry) -{ - const fileName file = gtk_entry_get_text(entry); - guiPtr->setSurfaceFileName(file); -} - -static void enterMaxCellSize(GtkWidget* widget, GtkEntry* entry) -{ - const word s = gtk_entry_get_text(GTK_ENTRY(widget)); - const scalar size = help::textToScalar(s); - guiPtr->setMaxCellSize(size); -} - -static void enterBndCellSize(GtkWidget* widget, GtkEntry* entry) -{ - if( !guiPtr->boundaryCellSizeEntryExist() ) - return; - const word s = gtk_entry_get_text(GTK_ENTRY(widget)); - const scalar size = help::textToScalar(s); - guiPtr->setBoundaryCellSize(size); -} - -static void enterMinCellSize(GtkWidget* widget, GtkEntry* entry) -{ - if( !guiPtr->minCellSizeEntryExist() ) - return; - const word s = gtk_entry_get_text(GTK_ENTRY(widget)); - const scalar size = help::textToScalar(s); - guiPtr->setMinCellSize(size); -} - -static void editableEntry(GtkWidget *checkbutton, GtkWidget *entry) -{ - gtk_editable_set_editable - ( - GTK_EDITABLE(entry), - GTK_TOGGLE_BUTTON(checkbutton)->active - ); - - if( !GTK_TOGGLE_BUTTON(checkbutton)->active ) - gtk_entry_set_text(GTK_ENTRY(entry), ""); -} - -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenGTK::createGeneralPage() -{ - guiPtr = &meshGui_; - - //- create a window for a general page - generalPageFramePtr_ = gtk_frame_new(NULL); - - GtkWidget* table1 = gtk_table_new (11, 5, FALSE); - gtk_widget_show(table1); - gtk_container_add(GTK_CONTAINER(generalPageFramePtr_), table1); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the surface file - GtkWidget* label_surfaceFile = gtk_label_new("Surface file"); - gtk_widget_show(label_surfaceFile); - gtk_table_attach(GTK_TABLE(table1), label_surfaceFile, 1, 2, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC (label_surfaceFile), 0, 0.5); - - GtkWidget* label_Space = gtk_label_new(""); - gtk_widget_show(label_Space); - gtk_table_attach(GTK_TABLE(table1), label_Space, 2, 3, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_widget_set_size_request(label_Space, 10, -1); - gtk_misc_set_alignment(GTK_MISC(label_Space), 0, 0.5); - - //- create entry box for the surface file - GtkWidget* entry_surfaceFile = gtk_entry_new(); - gtk_widget_show(entry_surfaceFile); - gtk_table_attach(GTK_TABLE(table1), entry_surfaceFile, 3, 4, 0, 1, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_surfaceFile), - meshGui_.surfaceFileName().c_str() - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_surfaceFile), - 1 - ); - - g_signal_connect(G_OBJECT(entry_surfaceFile), "changed", - G_CALLBACK(enterSurfaceFile), - (gpointer)entry_surfaceFile); - -/* GtkWidget* image1 = - gtk_image_new_from_stock("gtk-open", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_table_attach(GTK_TABLE (table1), image1, 4, 5, 0, 1, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(GTK_FILL), 0, 0); -*/ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- box for maxCellSize - GtkWidget* label_maxCellSize = gtk_label_new("Max cell size [m]"); - gtk_widget_show(label_maxCellSize); - gtk_table_attach(GTK_TABLE(table1), label_maxCellSize, 1, 2, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_maxCellSize), 0, 0.5); - - //- entry for maxCellSize - GtkWidget* entry_maxCellSize = gtk_entry_new(); - gtk_widget_show(entry_maxCellSize); - gtk_table_attach(GTK_TABLE(table1), entry_maxCellSize, 3, 5, 1, 2, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_maxCellSize), - help::scalarToText(meshGui_.maxCellSize()).c_str() - ); - - g_signal_connect - ( - G_OBJECT(entry_maxCellSize), "changed", - G_CALLBACK(enterMaxCellSize), - (gpointer)entry_maxCellSize - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- horizontal separator - GtkWidget* hseparator0 = gtk_hseparator_new(); - gtk_widget_show(hseparator0); - gtk_table_attach(GTK_TABLE(table1), hseparator0, 0, 5, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -//- boundary cell size - - //- checkbutton for boundaryCellSize - GtkWidget* checkbutton_boundaryCellSize = - gtk_check_button_new_with_mnemonic - ( - "Use different size for boundary cells" - ); - gtk_widget_show(checkbutton_boundaryCellSize); - gtk_table_attach(GTK_TABLE(table1), - checkbutton_boundaryCellSize, 0, 5, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 1, 0); - - - //- add callbacks for the button - if( meshGui_.boundaryCellSizeEntryExist() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_boundaryCellSize), - 1 - ); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_boundaryCellSize), - 0 - ); - } - - g_signal_connect - ( - gpointer(checkbutton_boundaryCellSize), - "clicked", - G_CALLBACK(useButtonCallback), - (gpointer)"UseBndSize" - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a box for boundary cell size - GtkWidget* label_boundaryCellSize = gtk_label_new("Boundary cell size [m]"); - gtk_widget_show(label_boundaryCellSize); - gtk_table_attach(GTK_TABLE(table1), label_boundaryCellSize, 1, 2, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_boundaryCellSize), 0, 0.5); - - GtkWidget* entry_boundaryCellSize = gtk_entry_new(); - gtk_widget_show(entry_boundaryCellSize); - gtk_table_attach(GTK_TABLE (table1), entry_boundaryCellSize, 3, 5, 4, 5, - (GtkAttachOptions) (GTK_EXPAND | GTK_FILL), - (GtkAttachOptions) (0), 1, 0); - gtk_entry_set_invisible_char (GTK_ENTRY (entry_boundaryCellSize), 9679); - - gtk_entry_set_visibility - ( - GTK_ENTRY(entry_boundaryCellSize), - meshGui_.boundaryCellSizeEntryExist() - ); - - if( meshGui_.boundaryCellSizeEntryExist() ) - { - gtk_entry_set_text - ( - GTK_ENTRY(entry_boundaryCellSize), - help::scalarToText(meshGui_.boundaryCellSize()).c_str() - ); - } - else - { - gtk_editable_set_editable(GTK_EDITABLE(entry_boundaryCellSize), 0); - } - - g_signal_connect - ( - G_OBJECT(checkbutton_boundaryCellSize), - "toggled", - G_CALLBACK(editableEntry), - (gpointer)entry_boundaryCellSize - ); - - g_signal_connect - ( - G_OBJECT(entry_boundaryCellSize), - "changed", - G_CALLBACK(enterBndCellSize), - (gpointer)entry_boundaryCellSize - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- horizontal separator - GtkWidget* hseparator1 = gtk_hseparator_new(); - gtk_widget_show(hseparator1); - gtk_table_attach(GTK_TABLE(table1), hseparator1, 0, 5, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a box for automatic refinement - - //- checkbox for automatic refinement - GtkWidget* checkbutton_automaticRefinement = - gtk_check_button_new_with_mnemonic("Use automatic refinement"); - gtk_widget_show(checkbutton_automaticRefinement); - gtk_table_attach(GTK_TABLE(table1), checkbutton_automaticRefinement, - 0, 5, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - if( meshGui_.minCellSizeEntryExist() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_automaticRefinement), 1 - ); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_automaticRefinement), 0 - ); - } - - g_signal_connect - ( - gpointer(checkbutton_automaticRefinement), - "clicked", - G_CALLBACK(useButtonCallback), - (gpointer)"UseAutoRef" - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a box for min cell size - GtkWidget* label_minCellSize = gtk_label_new("Min cell size [m]"); - gtk_widget_show(label_minCellSize); - gtk_table_attach(GTK_TABLE(table1), label_minCellSize, 1, 2, 7, 8, - (GtkAttachOptions) (GTK_FILL), - (GtkAttachOptions) (0), 0, 0); - gtk_misc_set_alignment (GTK_MISC (label_minCellSize), 0, 0.5); - - GtkWidget* entry_minCellSize = gtk_entry_new(); - gtk_widget_show(entry_minCellSize); - gtk_table_attach(GTK_TABLE (table1), entry_minCellSize, 3, 5, 7, 8, - (GtkAttachOptions) (GTK_EXPAND | GTK_FILL), - (GtkAttachOptions) (0), 1, 0); - - if( meshGui_.minCellSizeEntryExist() ) - { - gtk_entry_set_text - ( - GTK_ENTRY(entry_minCellSize), - help::scalarToText(meshGui_.minCellSize()).c_str() - ); - } - else - { - gtk_editable_set_editable(GTK_EDITABLE(entry_minCellSize), 0); - } - - g_signal_connect - ( - G_OBJECT(checkbutton_automaticRefinement), - "toggled", - G_CALLBACK(editableEntry), - (gpointer)entry_minCellSize - ); - - g_signal_connect - ( - G_OBJECT(entry_minCellSize), - "changed", - G_CALLBACK(enterMinCellSize), - (gpointer)entry_minCellSize - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- horizontal separator - GtkWidget* hseparator2 = gtk_hseparator_new(); - gtk_widget_show(hseparator2); - gtk_table_attach(GTK_TABLE(table1), hseparator2, 0, 5, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- activate keepCellsIntersectingBoundary option - GtkWidget* checkbutton_keepCellsIntersectingBoundary = - gtk_check_button_new_with_mnemonic - ( - "Keep octree boxes intersecting the boundary" - ); - gtk_widget_show(checkbutton_keepCellsIntersectingBoundary); - gtk_table_attach(GTK_TABLE(table1), - checkbutton_keepCellsIntersectingBoundary, - 0, 5, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - if( meshGui_.keepCellsIntersectingBoundaryEntryExist() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_keepCellsIntersectingBoundary) - ,1 - ); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_keepCellsIntersectingBoundary) - ,0 - ); - } - - g_signal_connect - ( - gpointer(checkbutton_keepCellsIntersectingBoundary), - "clicked", - G_CALLBACK(useButtonCallback), - (gpointer)"UseKeepCellsIntersectingBoundary" - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- activate checkForGluedMesh - GtkWidget* checkbutton_checkForGluedMesh = - gtk_check_button_new_with_mnemonic("Remove invalid mesh connections"); - gtk_widget_show(checkbutton_checkForGluedMesh); - gtk_table_attach(GTK_TABLE(table1), checkbutton_checkForGluedMesh, - 0, 5, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - if( !meshGui_.keepCellsIntersectingBoundary() ) - meshGui_.removeCheckForGluedMesh(); - - if( meshGui_.checkForGluedMesh() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_checkForGluedMesh), - 1 - ); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_checkForGluedMesh), - 0 - ); - } - - g_signal_connect - ( - gpointer(checkbutton_checkForGluedMesh), - "clicked", - G_CALLBACK(useButtonCallback), - (gpointer)"UseCheckForGluedMesh" - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - generalPageFramePtr_, - generalPageFramePtr_, - "window_generalPage_" - ); - GLADE_HOOKUP_OBJECT - ( - checkbutton_keepCellsIntersectingBoundary, - checkbutton_checkForGluedMesh, - "checkbutton_checkForGluedMesh" - ); - - gtk_widget_show(generalPageFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKKeepCellsIntersectingPatches.C b/GUI/meshGenGTK/meshGenGTKKeepCellsIntersectingPatches.C deleted file mode 100644 index d14adbc4017b4b7ba4b0284678453d7b2c11381c..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKKeepCellsIntersectingPatches.C +++ /dev/null @@ -1,414 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "triSurface.H" -#include "HashSet.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -//- callback functions - -extern "C" -{ - -static void updateKeepCellsIntersectingPatches -( - GtkWidget* keepCellsIntersectingPatchesFramePtr -) -{ - GtkWidget* comboboxentry_keepCellsIntersectingPatches_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(keepCellsIntersectingPatchesFramePtr), - "comboboxentry_keepCellsIntersectingPatches_availablePatches" - ); - GtkWidget* comboboxentry_keepCellsIntersectingPatches_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(keepCellsIntersectingPatchesFramePtr), - "comboboxentry_keepCellsIntersectingPatches_selectedPatches" - ); - //- update available patches - wordList alreadyUsed = guiPtr->keepCellsIntersectingPatches(); - wordHashSet usedNames; - forAll(alreadyUsed, nameI) - usedNames.insert(alreadyUsed[nameI]); - - GList* avPatches = 0; - label nAvailable(0); - const triSurface& surf = guiPtr->surface(); - forAll(surf.patches(), patchI) - { - if( usedNames.found(surf.patches()[patchI].name()) ) - continue; - const char* name = surf.patches()[patchI].name().c_str(); - avPatches = g_list_append(avPatches, const_cast<char*>(name)); - ++nAvailable; - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_availablePatches - ), avPatches - ); - - if( nAvailable == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_availablePatches - )->entry - ), "" - ); - } - - //- update used patches - GList* selPatches = 0; - forAll(alreadyUsed, patchI) - { - const char* name = alreadyUsed[patchI].c_str(); - selPatches = g_list_append(selPatches, const_cast<char*>(name)); - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_selectedPatches - ), selPatches - ); - - if( alreadyUsed.size() == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_selectedPatches - )->entry - ), "" - ); - } - - g_list_free(avPatches); - g_list_free(selPatches); -} - -static void addKeepCellsIntersectingPatches -( - GtkWidget* widget, - GtkWidget* keepCellsIntersectingPatchesFramePtr -) -{ - GtkWidget* comboboxentry_keepCellsIntersectingPatches_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(keepCellsIntersectingPatchesFramePtr), - "comboboxentry_keepCellsIntersectingPatches_availablePatches" - ); - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_availablePatches - )->entry - ) - ); - - if( name == "" ) - return; - - guiPtr->addKeepCellsIntersectingPatches(name); - - updateKeepCellsIntersectingPatches(keepCellsIntersectingPatchesFramePtr); -} - -static void removeKeepCellsIntersectingPatches -( - GtkWidget* widget, - GtkWidget* keepCellsIntersectingPatchesFramePtr -) -{ - GtkWidget* comboboxentry_keepCellsIntersectingPatches_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(keepCellsIntersectingPatchesFramePtr), - "comboboxentry_keepCellsIntersectingPatches_selectedPatches" - ); - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_selectedPatches - )->entry - ) - ); - - if( name == "" ) - return; - - guiPtr->removeKeepCellsIntersectingPatches(name); - - updateKeepCellsIntersectingPatches(keepCellsIntersectingPatchesFramePtr); -} - -} - -void meshGenGTK::createKeepCellsIntersectingPatchesWindowPage() -{ - guiPtr = &meshGui_; - - keepCellsIntersectingPatchesFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(2, 3, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(keepCellsIntersectingPatchesFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set label for available patches - GtkWidget* label_keepCellsIntersectingPatches_availablePatches = - gtk_label_new("Available patches"); - gtk_widget_show(label_keepCellsIntersectingPatches_availablePatches); - gtk_table_attach - ( - GTK_TABLE(table1), - label_keepCellsIntersectingPatches_availablePatches, - 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions) (0), 0, 0 - ); - gtk_misc_set_alignment - ( - GTK_MISC(label_keepCellsIntersectingPatches_availablePatches), - 0, - 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the combo box for available patches - GtkWidget* comboboxentry_keepCellsIntersectingPatches_availablePatches = - gtk_combo_new(); - gtk_widget_show - ( - comboboxentry_keepCellsIntersectingPatches_availablePatches - ); - gtk_table_attach - ( - GTK_TABLE(table1), - comboboxentry_keepCellsIntersectingPatches_availablePatches, - 1, 2, 0, 1, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(GTK_FILL), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_availablePatches - )->entry - ), - 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding patches - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 2, 3, 0, 1, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addKeepCellsIntersectingPatches), - keepCellsIntersectingPatchesFramePtr_ - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set label for selected patches - GtkWidget* label_keepCellsIntersectingPatches_selectedPatches = - gtk_label_new("Selected patches"); - gtk_widget_show(label_keepCellsIntersectingPatches_selectedPatches); - gtk_table_attach - ( - GTK_TABLE(table1), - label_keepCellsIntersectingPatches_selectedPatches, - 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - gtk_misc_set_alignment - ( - GTK_MISC(label_keepCellsIntersectingPatches_selectedPatches), - 0, - 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the combo box for selected patches - GtkWidget* comboboxentry_keepCellsIntersectingPatches_selectedPatches = - gtk_combo_new(); - gtk_widget_show(comboboxentry_keepCellsIntersectingPatches_selectedPatches); - gtk_table_attach - ( - GTK_TABLE(table1), - comboboxentry_keepCellsIntersectingPatches_selectedPatches, - 1, 2, 1, 2, - (GtkAttachOptions) (GTK_FILL), (GtkAttachOptions) (GTK_FILL), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO - ( - comboboxentry_keepCellsIntersectingPatches_selectedPatches - )->entry - ), - 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing patches - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 2, 3, 1, 2, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removeKeepCellsIntersectingPatches), - keepCellsIntersectingPatchesFramePtr_ - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - keepCellsIntersectingPatchesFramePtr_, - keepCellsIntersectingPatchesFramePtr_, - "Cell intersecting patches frame" - ); - GLADE_HOOKUP_OBJECT - ( - keepCellsIntersectingPatchesFramePtr_, - comboboxentry_keepCellsIntersectingPatches_availablePatches, - "comboboxentry_keepCellsIntersectingPatches_availablePatches" - ); - GLADE_HOOKUP_OBJECT - ( - keepCellsIntersectingPatchesFramePtr_, - comboboxentry_keepCellsIntersectingPatches_selectedPatches, - "comboboxentry_keepCellsIntersectingPatches_selectedPatches" - ); - - updateKeepCellsIntersectingPatches(keepCellsIntersectingPatchesFramePtr_); - - gtk_widget_show(keepCellsIntersectingPatchesFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKLineRefinement.C b/GUI/meshGenGTK/meshGenGTKLineRefinement.C deleted file mode 100644 index ee07cc2e8a68a30bf562f2cf4b747e92402f0399..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKLineRefinement.C +++ /dev/null @@ -1,1054 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "lineRefinement.H" -#include "helperFunctions.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -//- callback functions - -extern "C" -{ - -static void showDataForLineRefinement -( - GtkWidget* widget, - GtkWidget* lineRefinementFramePtr -) -{ - GtkWidget* comboboxentry_lineRefinement_createdLines = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "comboboxentry_lineRefinement_createdLines" - ); - GtkWidget* entry_lineRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedCellSize" - ); - GtkWidget* entry_lineRefinement_selectedP0X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP0X" - ); - GtkWidget* entry_lineRefinement_selectedP0Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP0Y" - ); - GtkWidget* entry_lineRefinement_selectedP0Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP0Z" - ); - GtkWidget* entry_lineRefinement_selectedP1X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP1X" - ); - GtkWidget* entry_lineRefinement_selectedP1Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP1Y" - ); - GtkWidget* entry_lineRefinement_selectedP1Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP1Z" - ); - - //- find the object in the dictionary - const word lineName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_lineRefinement_createdLines)->entry - ) - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - - forAll(refs, refI) - if( refs[refI].keyword() == lineName ) - { - const dictionary dict = refs[refI].dict(); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_lineRefinement_selectedCellSize), - help::scalarToText - ( - scalar(readScalar(dict.lookup("cellSize"))) - ).c_str() - ); - const vector p0(dict.lookup("p0")); - gtk_entry_set_text - ( - GTK_ENTRY(entry_lineRefinement_selectedP0X), - help::scalarToText(p0.x()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_lineRefinement_selectedP0Y), - help::scalarToText(p0.y()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_lineRefinement_selectedP0Z), - help::scalarToText(p0.z()).c_str() - ); - - const vector p1(dict.lookup("p1")); - gtk_entry_set_text - ( - GTK_ENTRY(entry_lineRefinement_selectedP1X), - help::scalarToText(p1.x()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_lineRefinement_selectedP1Y), - help::scalarToText(p1.y()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_lineRefinement_selectedP1Z), - help::scalarToText(p1.z()).c_str() - ); - - return; - } - - gtk_entry_set_text(GTK_ENTRY(entry_lineRefinement_selectedCellSize), ""); - gtk_entry_set_text(GTK_ENTRY(entry_lineRefinement_selectedP0X), ""); - gtk_entry_set_text(GTK_ENTRY(entry_lineRefinement_selectedP0Y), ""); - gtk_entry_set_text(GTK_ENTRY(entry_lineRefinement_selectedP0Z), ""); - gtk_entry_set_text(GTK_ENTRY(entry_lineRefinement_selectedP1X), ""); - gtk_entry_set_text(GTK_ENTRY(entry_lineRefinement_selectedP1Y), ""); - gtk_entry_set_text(GTK_ENTRY(entry_lineRefinement_selectedP1Z), ""); -} - -static void resetValuesForSelectedLine -( - GtkWidget* widget, - GtkWidget* lineRefinementFramePtr -) -{ - GtkWidget* comboboxentry_lineRefinement_createdLines = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "comboboxentry_lineRefinement_createdLines" - ); - GtkWidget* entry_lineRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedCellSize" - ); - GtkWidget* entry_lineRefinement_selectedP0X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP0X" - ); - GtkWidget* entry_lineRefinement_selectedP0Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP0Y" - ); - GtkWidget* entry_lineRefinement_selectedP0Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP0Z" - ); - GtkWidget* entry_lineRefinement_selectedP1X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP1X" - ); - GtkWidget* entry_lineRefinement_selectedP1Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP1Y" - ); - GtkWidget* entry_lineRefinement_selectedP1Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_selectedP1Z" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_lineRefinement_createdLines - )->entry - ) - ); - - if( name == "" ) - return; - - const PtrList<entry> refs = guiPtr->objectRefinements(); - dictionary dict; - forAll(refs, refI) - if( refs[refI].keyword() == name ) - dict = refs[refI].dict(); - guiPtr->removeObjectRefinement(name); - if( widget == entry_lineRefinement_selectedCellSize ) - { - const word size = - gtk_entry_get_text(GTK_ENTRY(entry_lineRefinement_selectedCellSize)); - dict.remove("cellSize"); - dict.add("cellSize", help::textToScalar(size)); - } - else if( widget == entry_lineRefinement_selectedP0X ) - { - point p0(dict.lookup("p0")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_lineRefinement_selectedP0X)); - dict.remove("p0"); - p0.x() = help::textToScalar(c); - dict.add("p0", p0); - } - else if( widget == entry_lineRefinement_selectedP0Y ) - { - point p0(dict.lookup("p0")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_lineRefinement_selectedP0Y)); - dict.remove("p0"); - p0.y() = help::textToScalar(c); - dict.add("p0", p0); - } - else if( widget == entry_lineRefinement_selectedP0Z ) - { - point p0(dict.lookup("p0")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_lineRefinement_selectedP0Z)); - dict.remove("p0"); - p0.z() = help::textToScalar(c); - dict.add("p0", p0); - } - else if( widget == entry_lineRefinement_selectedP1X ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_lineRefinement_selectedP1X)); - point p1(dict.lookup("p1")); - dict.remove("p1"); - p1.x() = help::textToScalar(l); - dict.add("p1", p1); - } - else if( widget == entry_lineRefinement_selectedP1Y ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_lineRefinement_selectedP1Y)); - point p1(dict.lookup("p1")); - dict.remove("p1"); - p1.y() = help::textToScalar(l); - dict.add("p1", p1); - } - else if( widget == entry_lineRefinement_selectedP1Z ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_lineRefinement_selectedP1Z)); - point p1(dict.lookup("p1")); - dict.remove("p1"); - p1.z() = help::textToScalar(l); - dict.add("p1", p1); - } - - lineRefinement br(name, dict); - guiPtr->addObjectRefinement(br); -} - -static void updateLineRefinements(GtkWidget* lineRefinementFramePtr) -{ - GtkWidget* comboboxentry_lineRefinement_createdLines = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "comboboxentry_lineRefinement_createdLines" - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - label nLines(0); - GList* createdLines = 0; - forAll(refs, refI) - { - const word& key = refs[refI].keyword(); - const dictionary& dict = refs[refI].dict(); - const word type(dict.lookup("type")); - - if( type == "line" ) - { - ++nLines; - lineRefinement line(key, dict); - createdLines = - g_list_append - ( - createdLines, - const_cast<char*>(line.name().c_str()) - ); - } - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_lineRefinement_createdLines - ), createdLines - ); - - if( nLines == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_lineRefinement_createdLines)->entry - ), - "" - ); - } - - g_list_free(createdLines); - - showDataForLineRefinement(NULL, lineRefinementFramePtr); -} - -static void addLineRefinement -( - GtkWidget* button, - GtkWidget* lineRefinementFramePtr -) -{ - GtkWidget* name = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineName" - ); - GtkWidget* cellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_cellSize" - ); - GtkWidget* p0X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_p0X" - ); - GtkWidget* p0Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_p0Y" - ); - GtkWidget* p0Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_p0Z" - ); - GtkWidget* p1X = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_p1X" - ); - GtkWidget* p1Y = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_p1Y" - ); - GtkWidget* p1Z = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "entry_lineRefinement_p1Z" - ); - - //- create all necessary settings - const word lineName = gtk_entry_get_text(GTK_ENTRY(name)); - gtk_entry_set_text(GTK_ENTRY(name), ""); - const scalar lineCellSize = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(cellSize))); - gtk_entry_set_text(GTK_ENTRY(cellSize), ""); - point p0, p1; - p0.x() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p0X))); - gtk_entry_set_text(GTK_ENTRY(p0X), ""); - p0.y() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p0Y))); - gtk_entry_set_text(GTK_ENTRY(p0Y), ""); - p0.z() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p0Z))); - gtk_entry_set_text(GTK_ENTRY(p0Z), ""); - p1.x() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p1X))); - gtk_entry_set_text(GTK_ENTRY(p1X), ""); - p1.y() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p1Y))); - gtk_entry_set_text(GTK_ENTRY(p1Y), ""); - p1.z() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(p1Z))); - gtk_entry_set_text(GTK_ENTRY(p1Z), ""); - - lineRefinement line - ( - lineName, - lineCellSize, - p0, - p1 - ); - - guiPtr->addObjectRefinement(line); - - updateLineRefinements(lineRefinementFramePtr); -} - -static void removeLineRefinement -( - GtkWidget* button, - GtkWidget* lineRefinementFramePtr -) -{ - GtkWidget* createdLines = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(lineRefinementFramePtr), - "comboboxentry_lineRefinement_createdLines" - ); - - const word lineName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(createdLines)->entry - ) - ); - - guiPtr->removeObjectRefinement(lineName); - - updateLineRefinements(lineRefinementFramePtr); -} - -} - -void meshGenGTK::createLineRefinementWindowPage() -{ - guiPtr = &meshGui_; - - lineRefinementFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(5, 11, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(lineRefinementFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for box name - GtkWidget* label_lineName = gtk_label_new("Line name"); - gtk_widget_show(label_lineName); - gtk_table_attach(GTK_TABLE(table1), label_lineName, 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_lineName), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create an entry for box name - GtkWidget* entry_lineName = gtk_entry_new(); - gtk_widget_show(entry_lineName); - - gtk_table_attach(GTK_TABLE(table1), entry_lineName, 1, 4, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* label_lineRefinement_cellSize = gtk_label_new("Cell size [m]"); - gtk_widget_show(label_lineRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), label_lineRefinement_cellSize, - 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_lineRefinement_cellSize), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* entry_lineRefinement_cellSize = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_cellSize, - 1, 4, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - GtkWidget* label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for p0 - GtkWidget* label_lineRefinement_p0 = gtk_label_new("Starting point"); - gtk_widget_show(label_lineRefinement_p0); - gtk_table_attach(GTK_TABLE(table1), label_lineRefinement_p0, - 0, 1, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_lineRefinement_p0), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for p0 - GtkWidget* entry_lineRefinement_p0X = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_p0X); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_p0X, - 1, 2, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_p0Y = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_p0Y); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_p0Y, - 2, 3, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_p0Z = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_p0Z); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_p0Z, - 3, 4, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for p1 - GtkWidget* label_lineRefinement_p1 = gtk_label_new("End point"); - gtk_widget_show(label_lineRefinement_p1); - gtk_table_attach(GTK_TABLE(table1), label_lineRefinement_p1, - 0, 1, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_lineRefinement_p1), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for p1 - GtkWidget* entry_lineRefinement_p1X = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_p1X); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_p1X, - 1, 2, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_p1Y = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_p1Y); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_p1Y, - 2, 3, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_p1Z = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_p1Z); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_p1Z, - 3, 4, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding lines - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 4, 5, 0, 5, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addLineRefinement), - lineRefinementFramePtr_ - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- horizontal separator - GtkWidget* hseparator0 = gtk_hseparator_new(); - gtk_widget_show(hseparator0); - gtk_table_attach(GTK_TABLE(table1), hseparator0, 0, 5, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for existing line objects - GtkWidget* label_lineRefinement_existing = gtk_label_new("Existing lines"); - gtk_widget_show(label_lineRefinement_existing); - gtk_table_attach(GTK_TABLE(table1), label_lineRefinement_existing, - 0, 1, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- combobox for existing box objects - GtkWidget* comboboxentry_lineRefinement_createdLines = - gtk_combo_new(); - gtk_widget_show(comboboxentry_lineRefinement_createdLines); - gtk_table_attach - ( - GTK_TABLE(table1),comboboxentry_lineRefinement_createdLines, - 1, 2, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO(comboboxentry_lineRefinement_createdLines)->entry - ), - 0 - ); - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* label_lineRefinement_selectedCellSize = - gtk_label_new("Cell size [m]"); - gtk_widget_show(label_lineRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), label_lineRefinement_selectedCellSize, - 0, 1, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_lineRefinement_selectedCellSize), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* entry_lineRefinement_selectedCellSize = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_selectedCellSize, - 1, 4, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for p0 - GtkWidget* label_lineRefinement_selectedP0 = - gtk_label_new("Starting point"); - gtk_widget_show(label_lineRefinement_selectedP0); - gtk_table_attach(GTK_TABLE(table1), label_lineRefinement_selectedP0, - 0, 1, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_lineRefinement_selectedP0), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for selected p0 - GtkWidget* entry_lineRefinement_selectedP0X = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_selectedP0X); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_selectedP0X, - 1, 2, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_selectedP0Y = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_selectedP0Y); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_selectedP0Y, - 2, 3, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_selectedP0Z = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_selectedP0Z); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_selectedP0Z, - 3, 4, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for selected p1 - GtkWidget* label_lineRefinement_selectedP1 = - gtk_label_new("End point"); - gtk_widget_show(label_lineRefinement_selectedP1); - gtk_table_attach(GTK_TABLE(table1), label_lineRefinement_selectedP1, - 0, 1, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_lineRefinement_selectedP1), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for p1 - GtkWidget* entry_lineRefinement_selectedP1X = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_selectedP1X); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_selectedP1X, - 1, 2, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_selectedP1Y = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_selectedP1Y); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_selectedP1Y, - 2, 3, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_lineRefinement_selectedP1Z = gtk_entry_new(); - gtk_widget_show(entry_lineRefinement_selectedP1Z); - gtk_table_attach(GTK_TABLE(table1), entry_lineRefinement_selectedP1Z, - 3, 4, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing patches - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 4, 5, 6, 11, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removeLineRefinement), - lineRefinementFramePtr_ - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - lineRefinementFramePtr_, - lineRefinementFramePtr_, - "lineRefinementFramePtr_"); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - table1, - "table1" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineName, - "entry_lineName" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_cellSize, - "entry_lineRefinement_cellSize" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_p0X, - "entry_lineRefinement_p0X" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_p0Y, - "entry_lineRefinement_p0Y" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_p0Z, - "entry_lineRefinement_p0Z" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_p1X, - "entry_lineRefinement_p1X" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_p1Y, - "entry_lineRefinement_p1Y" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_p1Z, - "entry_lineRefinement_p1Z" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - comboboxentry_lineRefinement_createdLines, - "comboboxentry_lineRefinement_createdLines" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_selectedCellSize, - "entry_lineRefinement_selectedCellSize" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_selectedP0X, - "entry_lineRefinement_selectedP0X" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_selectedP0Y, - "entry_lineRefinement_selectedP0Y" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_selectedP0Z, - "entry_lineRefinement_selectedP0Z" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_selectedP1X, - "entry_lineRefinement_selectedP1X" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_selectedP1Y, - "entry_lineRefinement_selectedP1Y" - ); - GLADE_HOOKUP_OBJECT - ( - lineRefinementFramePtr_, - entry_lineRefinement_selectedP1Z, - "entry_lineRefinement_selectedP1Z" - ); - - updateLineRefinements(lineRefinementFramePtr_); - - g_signal_connect - ( - G_OBJECT - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_lineRefinement_createdLines)->entry - ) - ), - "changed", - G_CALLBACK(showDataForLineRefinement), - lineRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_lineRefinement_selectedCellSize), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - lineRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_lineRefinement_selectedP0X), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - lineRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_lineRefinement_selectedP0Y), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - lineRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_lineRefinement_selectedP0Z), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - lineRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_lineRefinement_selectedP1X), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - lineRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_lineRefinement_selectedP1Y), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - lineRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_lineRefinement_selectedP1Z), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - lineRefinementFramePtr_ - ); - - gtk_widget_show(lineRefinementFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKLocalRefinement.C b/GUI/meshGenGTK/meshGenGTKLocalRefinement.C deleted file mode 100644 index 2d835069880e7e46d5eea681c2efb74343c58a1b..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKLocalRefinement.C +++ /dev/null @@ -1,591 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "patchRefinementList.H" -#include "HashSet.H" -#include "triSurface.H" -#include "helperFunctions.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -extern "C" -{ - -static void updateSizeForSelectedPatch -( - GtkWidget* widget, - GtkWidget* entry_localRefinement_selectedCellSize -) -{ - //- display the size for a patch selected in combo box - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - widget - ) - ); - - if( name == "" ) - { - gtk_entry_set_text - ( - GTK_ENTRY(entry_localRefinement_selectedCellSize), - "" - ); - } - - patchRefinementList refPatches = guiPtr->patchCellSize(); - forAll(refPatches, patchI) - if( refPatches[patchI].patchName() == name ) - { - const word s = help::scalarToText(refPatches[patchI].cellSize()); - gtk_entry_set_text - ( - GTK_ENTRY(entry_localRefinement_selectedCellSize), - s.c_str() - ); - } -} - -static void resetSizeForSelectedPatch -( - GtkWidget* widget, - GtkWidget* comboboxentry_localRefinement_selectedPatches -) -{ - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_localRefinement_selectedPatches - )->entry - ) - ); - - if( name == "" ) - return; - - guiPtr->removePatchCellSize(name); - - const word text = - gtk_entry_get_text - ( - GTK_ENTRY - ( - widget - ) - ); - const scalar size = help::textToScalar(text); - - patchRefinement pr(name, Foam::min(size, guiPtr->maxCellSize())); - - guiPtr->addPatchCellSize(pr); -} - -static void updateLocalRefinementPatches(GtkWidget* localRefinementFramePtr) -{ - GtkWidget* comboboxentry_localRefinement_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(localRefinementFramePtr), - "comboboxentry_localRefinement_availablePatches" - ); - GtkWidget* comboboxentry_localRefinement_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(localRefinementFramePtr), - "comboboxentry_localRefinement_selectedPatches" - ); - //- update available patches - patchRefinementList alreadyUsed = guiPtr->patchCellSize(); - - wordHashSet usedNames; - forAll(alreadyUsed, nameI) - usedNames.insert(alreadyUsed[nameI].patchName()); - - GList* avPatches = 0; - label nAvailable(0); - const triSurface& surf = guiPtr->surface(); - forAll(surf.patches(), patchI) - { - if( usedNames.found(surf.patches()[patchI].name()) ) - continue; - const char* name = surf.patches()[patchI].name().c_str(); - avPatches = g_list_append(avPatches, const_cast<char*>(name)); - ++nAvailable; - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_localRefinement_availablePatches - ), avPatches - ); - - if( nAvailable == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_localRefinement_availablePatches - )->entry - ), "" - ); - } - - //- update used patches - GList* selPatches = 0; - forAll(alreadyUsed, patchI) - { - const char* name = alreadyUsed[patchI].patchName().c_str(); - selPatches = g_list_append(selPatches, const_cast<char*>(name)); - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_localRefinement_selectedPatches - ), selPatches - ); - - if( alreadyUsed.size() == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_localRefinement_selectedPatches - )->entry - ), "" - ); - } - - g_list_free(avPatches); - g_list_free(selPatches); - - GtkWidget* entry_localRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(localRefinementFramePtr), - "entry_localRefinement_selectedCellSize" - ); - - updateSizeForSelectedPatch - ( - GTK_COMBO - ( - comboboxentry_localRefinement_selectedPatches - )->entry, - entry_localRefinement_selectedCellSize - ); -} - -static void addPatchCellSize -( - GtkWidget* widget, - GtkWidget* localRefinementFramePtr -) -{ - GtkWidget* comboboxentry_localRefinement_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(localRefinementFramePtr), - "comboboxentry_localRefinement_availablePatches" - ); - GtkWidget* entry_localRefinement_cellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(localRefinementFramePtr), - "entry_localRefinement_cellSize" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_localRefinement_availablePatches - )->entry - ) - ); - - if( name == "" ) - return; - - const word text = - gtk_entry_get_text - ( - GTK_ENTRY - ( - entry_localRefinement_cellSize - ) - ); - const scalar size = help::textToScalar(text); - - patchRefinement pr(name, Foam::min(size, guiPtr->maxCellSize())); - - guiPtr->addPatchCellSize(pr); - - updateLocalRefinementPatches(localRefinementFramePtr); -} - -static void removePatchRefinement -( - GtkWidget* widget, - GtkWidget* localRefinementFramePtr -) -{ - GtkWidget* comboboxentry_localRefinement_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(localRefinementFramePtr), - "comboboxentry_localRefinement_selectedPatches" - ); - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_localRefinement_selectedPatches - )->entry - ) - ); - - if( name == "" ) - return; - - guiPtr->removePatchCellSize(name); - - updateLocalRefinementPatches(localRefinementFramePtr); -} - -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenGTK::createLocalRefinementWindowPage() -{ - guiPtr = &meshGui_; - - localRefinementFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(2, 4, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(localRefinementFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set label for available patches - GtkWidget* label_localRefinement_availablePatches = - gtk_label_new("Available patches"); - gtk_widget_show(label_localRefinement_availablePatches); - gtk_table_attach - ( - GTK_TABLE(table1), - label_localRefinement_availablePatches, - 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions) (0), 0, 0 - ); - gtk_misc_set_alignment - ( - GTK_MISC(label_localRefinement_availablePatches), - 0, - 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the combo box for available patches - GtkWidget* comboboxentry_localRefinement_availablePatches = - gtk_combo_new(); - gtk_widget_show - ( - comboboxentry_localRefinement_availablePatches - ); - gtk_table_attach - ( - GTK_TABLE(table1), - comboboxentry_localRefinement_availablePatches, - 1, 2, 0, 1, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(GTK_FILL), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO - ( - comboboxentry_localRefinement_availablePatches - )->entry - ), - 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entry for cell size - GtkWidget* entry_localRefinement_cellSize = gtk_entry_new(); - gtk_widget_show(entry_localRefinement_cellSize); - - gtk_table_attach - ( - GTK_TABLE(table1), - entry_localRefinement_cellSize, - 2, 3, 0, 1, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(GTK_FILL), 0, 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding patches - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 3, 4, 0, 1, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addPatchCellSize), - localRefinementFramePtr_ - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set label for selected patches - GtkWidget* label_localRefinement_selectedPatches = - gtk_label_new("Selected patches"); - gtk_widget_show(label_localRefinement_selectedPatches); - gtk_table_attach - ( - GTK_TABLE(table1), - label_localRefinement_selectedPatches, - 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - gtk_misc_set_alignment - ( - GTK_MISC(label_localRefinement_selectedPatches), - 0, - 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entry for selected cell size - GtkWidget* entry_localRefinement_selectedCellSize = gtk_entry_new(); - gtk_widget_show(entry_localRefinement_selectedCellSize); - - gtk_table_attach - ( - GTK_TABLE(table1), - entry_localRefinement_selectedCellSize, - 2, 3, 1, 2, - (GtkAttachOptions)(GTK_EXPAND | GTK_FILL), - (GtkAttachOptions)(GTK_FILL), 0, 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the combo box for selected patches - GtkWidget* comboboxentry_localRefinement_selectedPatches = gtk_combo_new(); - gtk_widget_show(comboboxentry_localRefinement_selectedPatches); - - gtk_table_attach - ( - GTK_TABLE(table1), - comboboxentry_localRefinement_selectedPatches, - 1, 2, 1, 2, - (GtkAttachOptions) (GTK_FILL), (GtkAttachOptions) (GTK_FILL), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO - ( - comboboxentry_localRefinement_selectedPatches - )->entry - ), - 0 - ); - - //- change the displayed value to match the selected patch - g_signal_connect - ( - G_OBJECT - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_localRefinement_selectedPatches - )->entry - ) - ), - "changed", - G_CALLBACK(updateSizeForSelectedPatch), - entry_localRefinement_selectedCellSize - ); - - //- change the selected size in case the user decides it - g_signal_connect - ( - G_OBJECT(entry_localRefinement_selectedCellSize), - "changed", - G_CALLBACK(resetSizeForSelectedPatch), - comboboxentry_localRefinement_selectedPatches - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing patches - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 3, 4, 1, 2, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 0 - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removePatchRefinement), - localRefinementFramePtr_ - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - localRefinementFramePtr_, - localRefinementFramePtr_, - "Local refinement frame" - ); - GLADE_HOOKUP_OBJECT - ( - localRefinementFramePtr_, - comboboxentry_localRefinement_availablePatches, - "comboboxentry_localRefinement_availablePatches" - ); - GLADE_HOOKUP_OBJECT - ( - localRefinementFramePtr_, - entry_localRefinement_cellSize, - "entry_localRefinement_cellSize" - ); - GLADE_HOOKUP_OBJECT - ( - localRefinementFramePtr_, - comboboxentry_localRefinement_selectedPatches, - "comboboxentry_localRefinement_selectedPatches" - ); - GLADE_HOOKUP_OBJECT - ( - localRefinementFramePtr_, - entry_localRefinement_selectedCellSize, - "entry_localRefinement_selectedCellSize" - ); - - updateLocalRefinementPatches(localRefinementFramePtr_); - - gtk_widget_show(localRefinementFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKLocalSettingsMainWindow.C b/GUI/meshGenGTK/meshGenGTKLocalSettingsMainWindow.C deleted file mode 100644 index 139d4bc9c3496d71c36d1cae5eee15fa9190027b..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKLocalSettingsMainWindow.C +++ /dev/null @@ -1,128 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenGTK::createLocalSettingsMainWindowPage() -{ - //- create pages within this page - createLocalRefinementWindowPage(); - createKeepCellsIntersectingPatchesWindowPage(); - createBndLayersWindowPage(); - - localSettingsMainFramePtr_ = gtk_frame_new(NULL); - - GtkWidget* notebook1 = gtk_notebook_new (); - - gtk_container_add(GTK_CONTAINER(localSettingsMainFramePtr_), notebook1); - - //- add page for local refinement - GtkWidget* label_localRefinement = gtk_label_new("Local refinement"); - gtk_widget_show(label_localRefinement); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - localRefinementFramePtr_, - label_localRefinement - ); - - //- add page for keepCellsIntersectingPatches - GtkWidget* label_keepBoxesIntersectingPatches = - gtk_label_new("Keep octree boxes intersecting patches"); - gtk_widget_show(label_keepBoxesIntersectingPatches); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - keepCellsIntersectingPatchesFramePtr_, - label_keepBoxesIntersectingPatches - ); - - //- add page for bnd layers - GtkWidget* label_bndLayers = - gtk_label_new("Boundary layer for patches"); - gtk_widget_show(label_bndLayers); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - bndLayersFramePtr_, - label_bndLayers - ); - - //- show the notebook - gtk_widget_show(notebook1); - - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - localSettingsMainFramePtr_, - localSettingsMainFramePtr_, - "localSettingsMainFramePtr_" - ); - GLADE_HOOKUP_OBJECT - ( - localSettingsMainFramePtr_, - notebook1, - "notebook1" - ); - GLADE_HOOKUP_OBJECT - ( - localSettingsMainFramePtr_, - label_localRefinement, - "label_localRefinement" - ); - GLADE_HOOKUP_OBJECT - ( - localSettingsMainFramePtr_, - label_keepBoxesIntersectingPatches, - "label_keepBoxesIntersectingPatches" - ); - GLADE_HOOKUP_OBJECT - ( - localSettingsMainFramePtr_, - label_bndLayers, - "label_bndLayers" - ); - - gtk_widget_show(localSettingsMainFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKMainWindow.C b/GUI/meshGenGTK/meshGenGTKMainWindow.C deleted file mode 100644 index e1b6aec7b22c9c55669a4f7c550e945d8d3bd2a3..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKMainWindow.C +++ /dev/null @@ -1,187 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -// Callback functions go here -void saveMeshDictCallback(void* data) -{ - guiPtr->writeDict(); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenGTK::createMainWindowPage() -{ - guiPtr = &meshGui_; - - //- create the main window - GtkWidget* mainWindowPtr_ = gtk_window_new(GTK_WINDOW_TOPLEVEL); - gtk_window_set_title(GTK_WINDOW (mainWindowPtr_), "Mesh generation GUI"); - g_signal_connect - ( - G_OBJECT(mainWindowPtr_), - "destroy", - G_CALLBACK(gtk_main_quit), - NULL - ); - - GtkWidget* vbox1 = gtk_vbox_new(FALSE, 0); - gtk_widget_show(vbox1); - gtk_container_add(GTK_CONTAINER (mainWindowPtr_), vbox1); - - //- create a toolbar (for reading and saving meshDict) - GtkWidget* toolbar1 = gtk_toolbar_new(); - gtk_widget_show(toolbar1); - gtk_box_pack_start(GTK_BOX(vbox1), toolbar1, FALSE, FALSE, 0); - gtk_toolbar_set_style(GTK_TOOLBAR(toolbar1), GTK_TOOLBAR_ICONS); - //GtkIconSize tmp_toolbar_icon_size = - //gtk_toolbar_get_icon_size(GTK_TOOLBAR(toolbar1)); - - GtkWidget* toolitem1 = (GtkWidget*)gtk_tool_item_new(); - gtk_widget_show(toolitem1); - gtk_container_add(GTK_CONTAINER(toolbar1), toolitem1); - - GtkWidget* button_mainWindow_save = - gtk_button_new_with_mnemonic("Save meshDict"); - gtk_widget_show(button_mainWindow_save); - gtk_container_add(GTK_CONTAINER(toolitem1), button_mainWindow_save); - - g_signal_connect - ( - G_OBJECT(button_mainWindow_save), - "clicked", - G_CALLBACK(saveMeshDictCallback), - static_cast<void*>(&meshGui_) - ); - - //- create exit button - GtkWidget* toolitem2 = (GtkWidget*)gtk_tool_item_new(); - gtk_widget_show(toolitem2); - gtk_container_add(GTK_CONTAINER(toolbar1), toolitem2); - - GtkWidget* button_mainWindow_exit = gtk_button_new_with_mnemonic("Exit"); - gtk_widget_show(button_mainWindow_exit); - gtk_container_add(GTK_CONTAINER(toolitem2), button_mainWindow_exit); - - g_signal_connect - ( - G_OBJECT(button_mainWindow_exit), - "clicked", - G_CALLBACK(gtk_main_quit), - NULL - ); - - //- create a notebook which allows the user to switch between - //- the local and global settings - GtkWidget* notebook1 = gtk_notebook_new(); - - gtk_box_pack_start(GTK_BOX(vbox1), notebook1, TRUE, TRUE, 0); - - //- append the page for general settings - GtkWidget* label_generalSettings = gtk_label_new("General settings"); - gtk_widget_show(label_generalSettings); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - generalPageFramePtr_, - label_generalSettings - ); - - //- add local settings - GtkWidget* label_localSettings = gtk_label_new("Local settings"); - gtk_widget_show(label_localSettings); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - localSettingsMainFramePtr_, - label_localSettings - ); - - //- add object refinements - GtkWidget* label_objectRefinements = gtk_label_new("Object refinements"); - gtk_widget_show(label_objectRefinements); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - objectRefinementMainFramePtr_, - label_objectRefinements - ); - - //- add patch renaming - GtkWidget* label_renameBoundary = gtk_label_new("Rename boundary patches"); - gtk_widget_show(label_renameBoundary); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - renameBoundaryFramePtr_, - label_renameBoundary - ); - - gtk_widget_show(notebook1); - - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - mainWindowPtr_, - mainWindowPtr_, - "Mesh generation GUI" - ); - - GLADE_HOOKUP_OBJECT - ( - mainWindowPtr_, - button_mainWindow_save, - "button_mainWindow_save" - ); - GLADE_HOOKUP_OBJECT - ( - mainWindowPtr_, - button_mainWindow_exit, - "button_mainWindow_exit" - ); - - gtk_widget_show(mainWindowPtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKObjectRefinementMainWindow.C b/GUI/meshGenGTK/meshGenGTKObjectRefinementMainWindow.C deleted file mode 100644 index fca11f9b2ee47a69ee65479887ac05618c1e0534..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKObjectRefinementMainWindow.C +++ /dev/null @@ -1,120 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenGTK::createObjectRefinementMainWindowPage() -{ - //- create pages within this page - createBoxRefinementWindowPage(); - createLineRefinementWindowPage(); - createConeRefinementWindowPage(); - createSphereRefinementWindowPage(); - - objectRefinementMainFramePtr_ = gtk_frame_new(NULL); - - GtkWidget* notebook1 = gtk_notebook_new (); - - gtk_container_add(GTK_CONTAINER(objectRefinementMainFramePtr_), notebook1); - - //- add page for box refinement - GtkWidget* label_boxRefinement = gtk_label_new("Box refinement"); - gtk_widget_show(label_boxRefinement); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - boxRefinementFramePtr_, - label_boxRefinement - ); - - //- add page for line refinement - GtkWidget* label_lineRefinement = gtk_label_new("Line refinement"); - gtk_widget_show(label_lineRefinement); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - lineRefinementFramePtr_, - label_lineRefinement - ); - - //- add page for cone refinement - GtkWidget* label_coneRefinement = gtk_label_new("Cone refinement"); - gtk_widget_show(label_coneRefinement); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - coneRefinementFramePtr_, - label_coneRefinement - ); - - //- add page for sphere refinement - GtkWidget* label_sphereRefinement = gtk_label_new("Sphere refinement"); - gtk_widget_show(label_sphereRefinement); - - gtk_notebook_append_page - ( - GTK_NOTEBOOK(notebook1), - sphereRefinementFramePtr_, - label_sphereRefinement - ); - - //- show the notebook - gtk_widget_show(notebook1); - - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - objectRefinementMainFramePtr_, - objectRefinementMainFramePtr_, - "objectRefinementMainFramePtr_" - ); - GLADE_HOOKUP_OBJECT - ( - objectRefinementMainFramePtr_, - notebook1, - "notebook1" - ); - - gtk_widget_show(objectRefinementMainFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKRenameBoundary.C b/GUI/meshGenGTK/meshGenGTKRenameBoundary.C deleted file mode 100644 index d48a0430d64aa488a2486623dc83d4005a69d220..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKRenameBoundary.C +++ /dev/null @@ -1,1235 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "triSurface.H" -#include "helperFunctions.H" -#include "HashSet.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -extern "C" -{ - -static void resetNewPatchNamesForSelectedPatch -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* comboboxentry_renameBoundary_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "comboboxentry_renameBoundary_selectedPatches" - ); - GtkWidget* entry_renameBoundary_selectedPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_selectedPatchName" - ); - GtkWidget* entry_renameBoundary_selectedPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_selectedPatchType" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_renameBoundary_selectedPatches)->entry - ) - ); - - const PtrList<entry> newPatchNames = guiPtr->newPatchNames(); - forAll(newPatchNames, nameI) - if( newPatchNames[nameI].keyword() == name ) - { - const dictionary dict = newPatchNames[nameI].dict(); - - dictionary newDict; - if( widget == entry_renameBoundary_selectedPatchName ) - { - const word newName = - gtk_entry_get_text - ( - GTK_ENTRY(entry_renameBoundary_selectedPatchName) - ); - word type("patch"); - if( dict.found("type") ) - { - type = word(dict.lookup("type")); - } - newDict.add("newName", newName); - newDict.add("type", type); - } - else - { - const word newName(dict.lookup("newName")); - const word type = - gtk_entry_get_text - ( - GTK_ENTRY(entry_renameBoundary_selectedPatchType) - ); - newDict.add("newName", newName); - newDict.add("type", type); - } - - guiPtr->removePatchName(name); - guiPtr->addNewPatchName(name, newDict); - } -} - -static void updateNewPatchNamesForSelectedPatch -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* comboboxentry_renameBoundary_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "comboboxentry_renameBoundary_selectedPatches" - ); - GtkWidget* entry_renameBoundary_selectedPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_selectedPatchName" - ); - GtkWidget* entry_renameBoundary_selectedPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_selectedPatchType" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_renameBoundary_selectedPatches)->entry - ) - ); - - if( name == "" ) - { - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_selectedPatchName), "" - ); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_selectedPatchType), "" - ); - - return; - } - - const PtrList<entry> newPatchNames = guiPtr->newPatchNames(); - forAll(newPatchNames, nameI) - if( newPatchNames[nameI].keyword() == name ) - { - const dictionary dict = newPatchNames[nameI].dict(); - - const word newName(dict.lookup("newName")); - word type("patch"); - if( dict.found("type") ) - { - type = word(dict.lookup("type")); - } - - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_selectedPatchName), - newName.c_str() - ); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_selectedPatchType), - type.c_str() - ); - } -} - -static void updateNewPatchNames -( - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* comboboxentry_renameBoundary_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "comboboxentry_renameBoundary_availablePatches" - ); - GtkWidget* comboboxentry_renameBoundary_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "comboboxentry_renameBoundary_selectedPatches" - ); - - if( guiPtr->newPatchNamesEntryExist() ) - { - wordHashSet selectedPatches; - PtrList<entry> newPatchNames = guiPtr->newPatchNames(); - forAll(newPatchNames, pI) - selectedPatches.insert(newPatchNames[pI].keyword()); - - label nAvailable(0); - GList* avPatches = 0; - const triSurface& surf = guiPtr->surface(); - forAll(surf.patches(), patchI) - { - if( selectedPatches.found(surf.patches()[patchI].name()) ) - continue; - - ++nAvailable; - const char* name = surf.patches()[patchI].name().c_str(); - avPatches = g_list_append(avPatches, const_cast<char*>(name)); - } - - if( nAvailable == 0 ) - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_availablePatches - )->entry - ), - "" - ); - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_availablePatches - ), avPatches - ); - - g_list_free(avPatches); - - GList* selPatches = 0; - forAll(newPatchNames, nameI) - { - const char* name = newPatchNames[nameI].keyword().c_str(); - selPatches = g_list_append(selPatches, const_cast<char*>(name)); - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_selectedPatches - ), selPatches - ); - - g_list_free(selPatches); - - if( nAvailable == newPatchNames.size() ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_selectedPatches - )->entry - ), - "" - ); - } - } - else - { - GList* avPatches = 0; - - const triSurface& surf = guiPtr->surface(); - forAll(surf.patches(), patchI) - { - const char* name = surf.patches()[patchI].name().c_str(); - avPatches = g_list_append(avPatches, const_cast<char*>(name)); - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_availablePatches - ), avPatches - ); - - g_list_free(avPatches); - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_selectedPatches - ), avPatches - ); - - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_renameBoundary_selectedPatches)->entry - ), - "" - ); - } - - updateNewPatchNamesForSelectedPatch(NULL, renameBoundaryFramePtr); -} - -static void setDefaultValues(GtkWidget* renameBoundaryFramePtr) -{ - GtkWidget* checkbutton_renameBoundary_defaultPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "checkbutton_renameBoundary_defaultPatchName" - ); - GtkWidget* entry_renameBoundary_defaultPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_defaultPatchName" - ); - GtkWidget* checkbutton_renameBoundary_defaultPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "checkbutton_renameBoundary_defaultPatchType" - ); - GtkWidget* entry_renameBoundary_defaultPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_defaultPatchType" - ); - - if( guiPtr->defaultPatchNameEntryExist() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchName), - 1 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchName), 1 - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchName), - guiPtr->defaultPatchName().c_str() - ); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchName), - 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchName), 0 - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchName), - "" - ); - } - - if( guiPtr->defaultPatchTypeEntryExist() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchType), - 1 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchType), 1 - ); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchType), - guiPtr->defaultPatchType().c_str() - ); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchType), - 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchType), 0 - ); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchType), - "" - ); - } -} - -static void useDefaultPatchName -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* checkbutton_renameBoundary_defaultPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "checkbutton_renameBoundary_defaultPatchName" - ); - GtkWidget* entry_renameBoundary_defaultPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_defaultPatchName" - ); - - if( guiPtr->defaultPatchNameEntryExist() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchName), 0 - ); - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchName), 0 - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchName), "" - ); - guiPtr->removeDefaultPatchName(); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchName), 1 - ); - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchName), 1 - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchName), "defaultFaces" - ); - guiPtr->setDefaultPatchName("defaultFaces"); - } -} - -static void setDefaultPatchName -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* checkbutton_renameBoundary_defaultPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "checkbutton_renameBoundary_defaultPatchName" - ); - GtkWidget* entry_renameBoundary_defaultPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_defaultPatchName" - ); - - if( - gtk_toggle_button_get_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchName) - ) - ) - { - const word name = - gtk_entry_get_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchName) - ); - - guiPtr->setDefaultPatchName(name); - } -} - -static void useDefaultPatchType -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* checkbutton_renameBoundary_defaultPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "checkbutton_renameBoundary_defaultPatchType" - ); - GtkWidget* entry_renameBoundary_defaultPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_defaultPatchType" - ); - - if( guiPtr->defaultPatchTypeEntryExist() ) - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchType), 0 - ); - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchType), 0 - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchType), "" - ); - guiPtr->removeDefaultPatchType(); - } - else - { - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchType), 1 - ); - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_defaultPatchType), 1 - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchType), "patch" - ); - guiPtr->setDefaultPatchType("patch"); - } -} - -static void setDefaultPatchType -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* checkbutton_renameBoundary_defaultPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "checkbutton_renameBoundary_defaultPatchType" - ); - GtkWidget* entry_renameBoundary_defaultPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_defaultPatchType" - ); - - if( - gtk_toggle_button_get_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_defaultPatchType) - ) - ) - { - const word pType = - gtk_entry_get_text - ( - GTK_ENTRY(entry_renameBoundary_defaultPatchType) - ); - - guiPtr->setDefaultPatchType(pType); - } -} - -static void useNewPatchType -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* entry_renameBoundary_newPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_newPatchType" - ); - - Info << "Here " << gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget)) << endl; - if( gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(widget)) ) - { - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_newPatchType), 1 - ); - } - else - { - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_newPatchType), "" - ); - gtk_editable_set_editable - ( - GTK_EDITABLE(entry_renameBoundary_newPatchType), 0 - ); - } -} - -static void addNewPatchName -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* comboboxentry_renameBoundary_availablePatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "comboboxentry_renameBoundary_availablePatches" - ); - GtkWidget* entry_renameBoundary_newPatchName = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_newPatchName" - ); - GtkWidget* checkbutton_renameBoundary_newPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "checkbutton_renameBoundary_newPatchType" - ); - GtkWidget* entry_renameBoundary_newPatchType = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "entry_renameBoundary_newPatchType" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_availablePatches - )->entry - ) - ); - - if( name == "" ) - return; - - const word newName = - gtk_entry_get_text - ( - GTK_ENTRY(entry_renameBoundary_newPatchName) - ); - gtk_entry_set_text(GTK_ENTRY(entry_renameBoundary_newPatchName), ""); - - word newType("patch"); - if( - gtk_toggle_button_get_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_newPatchType) - ) - ) - { - newType = - gtk_entry_get_text - ( - GTK_ENTRY(entry_renameBoundary_newPatchType) - ); - - gtk_toggle_button_set_active - ( - GTK_TOGGLE_BUTTON(checkbutton_renameBoundary_newPatchType), 0 - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_renameBoundary_newPatchType), "" - ); - } - - dictionary dict; - dict.add("newName", newName); - dict.add("type", newType); - guiPtr->addNewPatchName(name, dict); - - updateNewPatchNames(renameBoundaryFramePtr); -} - -static void removeNewPatchName -( - GtkWidget* widget, - GtkWidget* renameBoundaryFramePtr -) -{ - GtkWidget* comboboxentry_renameBoundary_selectedPatches = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(renameBoundaryFramePtr), - "comboboxentry_renameBoundary_selectedPatches" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_selectedPatches - )->entry - ) - ); - - if( name == "" ) - return; - - guiPtr->removePatchName(name); - - updateNewPatchNames(renameBoundaryFramePtr); -} - -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenGTK::createRenameBoundaryMainWindowPage() -{ - guiPtr = &meshGui_; - - renameBoundaryFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(3, 10, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(renameBoundaryFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a check button for default patch name - GtkWidget* checkbutton_renameBoundary_defaultPatchName = - gtk_check_button_new_with_mnemonic - ( - "Default patch name" - ); - gtk_widget_show(checkbutton_renameBoundary_defaultPatchName); - - gtk_table_attach(GTK_TABLE(table1), - checkbutton_renameBoundary_defaultPatchName, 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the entry for default patch name - GtkWidget* entry_renameBoundary_defaultPatchName = gtk_entry_new(); - gtk_widget_show(entry_renameBoundary_defaultPatchName); - - gtk_table_attach(GTK_TABLE(table1), - entry_renameBoundary_defaultPatchName, 1, 2, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a check button for default patch type - GtkWidget* checkbutton_renameBoundary_defaultPatchType = - gtk_check_button_new_with_mnemonic - ( - "Default patch type" - ); - gtk_widget_show(checkbutton_renameBoundary_defaultPatchType); - - gtk_table_attach(GTK_TABLE(table1), - checkbutton_renameBoundary_defaultPatchType, 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create the entry for default patch type - GtkWidget* entry_renameBoundary_defaultPatchType = gtk_entry_new(); - gtk_widget_show(entry_renameBoundary_defaultPatchType); - - gtk_table_attach(GTK_TABLE(table1), - entry_renameBoundary_defaultPatchType, 1, 2, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a horizontal separator - GtkWidget* hseparator = gtk_hseparator_new(); - gtk_widget_show(hseparator); - gtk_table_attach(GTK_TABLE(table1), hseparator, 0, 3, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a label for available patches - GtkWidget* label_renameBoundary_availablePatches = - gtk_label_new("Available patches"); - gtk_widget_show(label_renameBoundary_availablePatches); - - gtk_table_attach(GTK_TABLE(table1), - label_renameBoundary_availablePatches, 0, 1, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a combo box for available patches - GtkWidget* comboboxentry_renameBoundary_availablePatches = - gtk_combo_new(); - gtk_widget_show(comboboxentry_renameBoundary_availablePatches); - - gtk_table_attach(GTK_TABLE(table1), - comboboxentry_renameBoundary_availablePatches, 1, 2, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_availablePatches - )->entry - ), - 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a label for new patch name - GtkWidget* label_renameBoundary_newPatchName = - gtk_label_new("New name"); - gtk_widget_show(label_renameBoundary_newPatchName); - - gtk_table_attach(GTK_TABLE(table1), - label_renameBoundary_newPatchName, 0, 1, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add the entry for new patch name - GtkWidget* entry_renameBoundary_newPatchName = gtk_entry_new(); - gtk_widget_show(entry_renameBoundary_newPatchName); - - gtk_table_attach(GTK_TABLE(table1), - entry_renameBoundary_newPatchName, 1, 2, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a check button for new patch type - GtkWidget* checkbutton_renameBoundary_newPatchType = - gtk_check_button_new_with_mnemonic - ( - "New type" - ); - gtk_widget_show(checkbutton_renameBoundary_newPatchType); - - gtk_table_attach(GTK_TABLE(table1), - checkbutton_renameBoundary_newPatchType, 0, 1, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add the entry for new patch type - GtkWidget* entry_renameBoundary_newPatchType = gtk_entry_new(); - gtk_widget_show(entry_renameBoundary_newPatchType); - - gtk_table_attach(GTK_TABLE(table1), - entry_renameBoundary_newPatchType, 1, 2, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding new patch names - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 2, 3, 3, 6, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 3 - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a horizontal separator - hseparator = gtk_hseparator_new(); - gtk_widget_show(hseparator); - gtk_table_attach(GTK_TABLE(table1), hseparator, 0, 3, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a label for selected patches - GtkWidget* label_renameBoundary_selectedPatches = - gtk_label_new("Selected patches"); - gtk_widget_show(label_renameBoundary_selectedPatches); - - gtk_table_attach(GTK_TABLE(table1), - label_renameBoundary_selectedPatches, 0, 1, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a combo box for selected patches - GtkWidget* comboboxentry_renameBoundary_selectedPatches = - gtk_combo_new(); - gtk_widget_show(comboboxentry_renameBoundary_selectedPatches); - - gtk_table_attach(GTK_TABLE(table1), - comboboxentry_renameBoundary_selectedPatches, 1, 2, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO - ( - comboboxentry_renameBoundary_selectedPatches - )->entry - ), - 0 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a label for new patch name - GtkWidget* label_renameBoundary_selectedPatchName = - gtk_label_new("New name"); - gtk_widget_show(label_renameBoundary_selectedPatchName); - - gtk_table_attach(GTK_TABLE(table1), - label_renameBoundary_selectedPatchName, 0, 1, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add the entry for selected patch name - GtkWidget* entry_renameBoundary_selectedPatchName = gtk_entry_new(); - gtk_widget_show(entry_renameBoundary_selectedPatchName); - - gtk_table_attach(GTK_TABLE(table1), - entry_renameBoundary_selectedPatchName, 1, 2, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add a label for selected patch type - GtkWidget* label_renameBoundary_selectedPatchType = - gtk_label_new - ( - "New type" - ); - gtk_widget_show(label_renameBoundary_selectedPatchType); - - gtk_table_attach(GTK_TABLE(table1), - label_renameBoundary_selectedPatchType, 0, 1, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- add the entry for selected patch type - GtkWidget* entry_renameBoundary_selectedPatchType = gtk_entry_new(); - gtk_widget_show(entry_renameBoundary_selectedPatchType); - - gtk_table_attach(GTK_TABLE(table1), - entry_renameBoundary_selectedPatchType, 1, 2, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing new patch names - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 2, 3, 7, 10, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - - GLADE_HOOKUP_OBJECT_NO_REF - ( - renameBoundaryFramePtr_, - renameBoundaryFramePtr_, - "renameBoundaryFramePtr_" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - checkbutton_renameBoundary_defaultPatchName, - "checkbutton_renameBoundary_defaultPatchName" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - entry_renameBoundary_defaultPatchName, - "entry_renameBoundary_defaultPatchName" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - checkbutton_renameBoundary_defaultPatchType, - "checkbutton_renameBoundary_defaultPatchType" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - entry_renameBoundary_defaultPatchType, - "entry_renameBoundary_defaultPatchType" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - comboboxentry_renameBoundary_availablePatches, - "comboboxentry_renameBoundary_availablePatches" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - entry_renameBoundary_newPatchName, - "entry_renameBoundary_newPatchName" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - checkbutton_renameBoundary_newPatchType, - "checkbutton_renameBoundary_newPatchType" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - entry_renameBoundary_newPatchType, - "entry_renameBoundary_newPatchType" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - comboboxentry_renameBoundary_selectedPatches, - "comboboxentry_renameBoundary_selectedPatches" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - entry_renameBoundary_selectedPatchName, - "entry_renameBoundary_selectedPatchName" - ); - GLADE_HOOKUP_OBJECT - ( - renameBoundaryFramePtr_, - entry_renameBoundary_selectedPatchType, - "entry_renameBoundary_selectedPatchType" - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - - setDefaultValues(renameBoundaryFramePtr_); - updateNewPatchNames(renameBoundaryFramePtr_); - - g_signal_connect - ( - G_OBJECT - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_renameBoundary_selectedPatches)->entry - ) - ), - "changed", - G_CALLBACK(updateNewPatchNamesForSelectedPatch), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(checkbutton_renameBoundary_defaultPatchName), - "clicked", - G_CALLBACK(useDefaultPatchName), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_renameBoundary_defaultPatchName), - "changed", - G_CALLBACK(setDefaultPatchName), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(checkbutton_renameBoundary_defaultPatchType), - "clicked", - G_CALLBACK(useDefaultPatchType), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_renameBoundary_defaultPatchType), - "changed", - G_CALLBACK(setDefaultPatchType), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(checkbutton_renameBoundary_newPatchType), - "clicked", - G_CALLBACK(useNewPatchType), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_renameBoundary_selectedPatchName), - "changed", - G_CALLBACK(resetNewPatchNamesForSelectedPatch), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_renameBoundary_selectedPatchType), - "changed", - G_CALLBACK(resetNewPatchNamesForSelectedPatch), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addNewPatchName), - renameBoundaryFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removeNewPatchName), - renameBoundaryFramePtr_ - ); - - gtk_widget_show(renameBoundaryFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGTK/meshGenGTKSphereRefinement.C b/GUI/meshGenGTK/meshGenGTKSphereRefinement.C deleted file mode 100644 index ec69c6fcd55014eac3558094ed8984d398ce08d0..0000000000000000000000000000000000000000 --- a/GUI/meshGenGTK/meshGenGTKSphereRefinement.C +++ /dev/null @@ -1,917 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGTK.H" -#include "sphereRefinement.H" -#include "helperFunctions.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -//- callback functions - -extern "C" -{ - -static void showDataForSphereRefinement -( - GtkWidget* widget, - GtkWidget* sphereRefinementFramePtr -) -{ - GtkWidget* comboboxentry_sphereRefinement_createdSpheres = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "comboboxentry_sphereRefinement_createdSpheres" - ); - GtkWidget* entry_sphereRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCellSize" - ); - GtkWidget* entry_sphereRefinement_selectedCentreX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCentreX" - ); - GtkWidget* entry_sphereRefinement_selectedCentreY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCentreY" - ); - GtkWidget* entry_sphereRefinement_selectedCentreZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCentreZ" - ); - GtkWidget* entry_sphereRefinement_selectedRadius = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedRadius" - ); - - //- find the object in the dictionary - const word sphereName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_sphereRefinement_createdSpheres)->entry - ) - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - - forAll(refs, refI) - if( refs[refI].keyword() == sphereName ) - { - const dictionary dict = refs[refI].dict(); - - gtk_entry_set_text - ( - GTK_ENTRY(entry_sphereRefinement_selectedCellSize), - help::scalarToText - ( - scalar(readScalar(dict.lookup("cellSize"))) - ).c_str() - ); - const vector centre(dict.lookup("centre")); - gtk_entry_set_text - ( - GTK_ENTRY(entry_sphereRefinement_selectedCentreX), - help::scalarToText(centre.x()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_sphereRefinement_selectedCentreY), - help::scalarToText(centre.y()).c_str() - ); - gtk_entry_set_text - ( - GTK_ENTRY(entry_sphereRefinement_selectedCentreZ), - help::scalarToText(centre.z()).c_str() - ); - - const scalar radius(readScalar(dict.lookup("radius"))); - gtk_entry_set_text - ( - GTK_ENTRY(entry_sphereRefinement_selectedRadius), - help::scalarToText(radius).c_str() - ); - - return; - } - - gtk_entry_set_text(GTK_ENTRY(entry_sphereRefinement_selectedCellSize), ""); - gtk_entry_set_text(GTK_ENTRY(entry_sphereRefinement_selectedCentreX), ""); - gtk_entry_set_text(GTK_ENTRY(entry_sphereRefinement_selectedCentreY), ""); - gtk_entry_set_text(GTK_ENTRY(entry_sphereRefinement_selectedCentreZ), ""); - gtk_entry_set_text(GTK_ENTRY(entry_sphereRefinement_selectedRadius), ""); -} - -static void resetValuesForSelectedLine -( - GtkWidget* widget, - GtkWidget* sphereRefinementFramePtr -) -{ - GtkWidget* comboboxentry_sphereRefinement_createdSpheres = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "comboboxentry_sphereRefinement_createdSpheres" - ); - GtkWidget* entry_sphereRefinement_selectedCellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCellSize" - ); - GtkWidget* entry_sphereRefinement_selectedCentreX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCentreX" - ); - GtkWidget* entry_sphereRefinement_selectedCentreY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCentreY" - ); - GtkWidget* entry_sphereRefinement_selectedCentreZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedCentreZ" - ); - GtkWidget* entry_sphereRefinement_selectedRadius = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_selectedRadius" - ); - - const word name = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO - ( - comboboxentry_sphereRefinement_createdSpheres - )->entry - ) - ); - - if( name == "" ) - return; - - const PtrList<entry> refs = guiPtr->objectRefinements(); - dictionary dict; - forAll(refs, refI) - if( refs[refI].keyword() == name ) - dict = refs[refI].dict(); - guiPtr->removeObjectRefinement(name); - if( widget == entry_sphereRefinement_selectedCellSize ) - { - const word size = - gtk_entry_get_text(GTK_ENTRY(entry_sphereRefinement_selectedCellSize)); - dict.remove("cellSize"); - dict.add("cellSize", help::textToScalar(size)); - } - else if( widget == entry_sphereRefinement_selectedCentreX ) - { - point centre(dict.lookup("centre")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_sphereRefinement_selectedCentreX)); - dict.remove("centre"); - centre.x() = help::textToScalar(c); - dict.add("centre", centre); - } - else if( widget == entry_sphereRefinement_selectedCentreY ) - { - point centre(dict.lookup("centre")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_sphereRefinement_selectedCentreY)); - dict.remove("centre"); - centre.y() = help::textToScalar(c); - dict.add("centre", centre); - } - else if( widget == entry_sphereRefinement_selectedCentreZ ) - { - point centre(dict.lookup("centre")); - const word c = - gtk_entry_get_text(GTK_ENTRY(entry_sphereRefinement_selectedCentreZ)); - dict.remove("centre"); - centre.z() = help::textToScalar(c); - dict.add("centre", centre); - } - else if( widget == entry_sphereRefinement_selectedRadius ) - { - const word l = - gtk_entry_get_text(GTK_ENTRY(entry_sphereRefinement_selectedRadius)); - dict.remove("radius"); - scalar radius = help::textToScalar(l); - dict.add("radius", radius); - } - - sphereRefinement sr(name, dict); - guiPtr->addObjectRefinement(sr); -} - -static void updateSphereRefinements(GtkWidget* sphereRefinementFramePtr) -{ - GtkWidget* comboboxentry_sphereRefinement_createdSpheres = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "comboboxentry_sphereRefinement_createdSpheres" - ); - - const PtrList<entry> refs = guiPtr->objectRefinements(); - label nSpheres(0); - GList* createdSpheres = 0; - forAll(refs, refI) - { - const word& key = refs[refI].keyword(); - const dictionary& dict = refs[refI].dict(); - const word type(dict.lookup("type")); - - if( type == "sphere" ) - { - ++nSpheres; - sphereRefinement sphere(key, dict); - createdSpheres = - g_list_append - ( - createdSpheres, - const_cast<char*>(sphere.name().c_str()) - ); - } - } - - gtk_combo_set_popdown_strings - ( - GTK_COMBO - ( - comboboxentry_sphereRefinement_createdSpheres - ), createdSpheres - ); - - if( nSpheres == 0 ) - { - gtk_entry_set_text - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_sphereRefinement_createdSpheres)->entry - ), - "" - ); - } - - g_list_free(createdSpheres); - - showDataForSphereRefinement(NULL, sphereRefinementFramePtr); -} - -static void addSphereRefinement -( - GtkWidget* button, - GtkWidget* sphereRefinementFramePtr -) -{ - GtkWidget* name = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereName" - ); - GtkWidget* cellSize = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_cellSize" - ); - GtkWidget* centreX = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_centreX" - ); - GtkWidget* centreY = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_centreY" - ); - GtkWidget* centreZ = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_centreZ" - ); - GtkWidget* radius = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "entry_sphereRefinement_radius" - ); - - //- create all necessary settings - const word sphereName = gtk_entry_get_text(GTK_ENTRY(name)); - gtk_entry_set_text(GTK_ENTRY(name), ""); - const scalar sphereCellSize = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(cellSize))); - gtk_entry_set_text(GTK_ENTRY(cellSize), ""); - point centre, p1; - centre.x() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(centreX))); - gtk_entry_set_text(GTK_ENTRY(centreX), ""); - centre.y() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(centreY))); - gtk_entry_set_text(GTK_ENTRY(centreY), ""); - centre.z() = help::textToScalar(gtk_entry_get_text(GTK_ENTRY(centreZ))); - gtk_entry_set_text(GTK_ENTRY(centreZ), ""); - const scalar selectedRadius = - help::textToScalar(gtk_entry_get_text(GTK_ENTRY(radius))); - gtk_entry_set_text(GTK_ENTRY(radius), ""); - - sphereRefinement sphere - ( - sphereName, - sphereCellSize, - centre, - selectedRadius - ); - - guiPtr->addObjectRefinement(sphere); - - updateSphereRefinements(sphereRefinementFramePtr); -} - -static void removeSphereRefinement -( - GtkWidget* button, - GtkWidget* sphereRefinementFramePtr -) -{ - GtkWidget* createdSpheres = - (GtkWidget*)g_object_get_data - ( - G_OBJECT(sphereRefinementFramePtr), - "comboboxentry_sphereRefinement_createdSpheres" - ); - - const word sphereName = - gtk_entry_get_text - ( - GTK_ENTRY - ( - GTK_COMBO(createdSpheres)->entry - ) - ); - - guiPtr->removeObjectRefinement(sphereName); - - updateSphereRefinements(sphereRefinementFramePtr); -} - -} - -void meshGenGTK::createSphereRefinementWindowPage() -{ - guiPtr = &meshGui_; - - sphereRefinementFramePtr_ = gtk_frame_new(NULL); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a table - GtkWidget* table1 = gtk_table_new(5, 11, FALSE); - gtk_widget_show(table1); - gtk_container_add - ( - GTK_CONTAINER(sphereRefinementFramePtr_), - table1 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for sphere name - GtkWidget* label_sphereName = gtk_label_new("Sphere name"); - gtk_widget_show(label_sphereName); - gtk_table_attach(GTK_TABLE(table1), label_sphereName, 0, 1, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_sphereName), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create an entry for box name - GtkWidget* entry_sphereName = gtk_entry_new(); - gtk_widget_show(entry_sphereName); - - gtk_table_attach(GTK_TABLE(table1), entry_sphereName, 1, 4, 0, 1, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* label_sphereRefinement_cellSize = gtk_label_new("Cell size [m]"); - gtk_widget_show(label_sphereRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), label_sphereRefinement_cellSize, - 0, 1, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_sphereRefinement_cellSize), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for desired cell size - GtkWidget* entry_sphereRefinement_cellSize = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_cellSize); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_cellSize, - 1, 4, 1, 2, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - GtkWidget* label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 2, 3, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for centre - GtkWidget* label_sphereRefinement_centre = gtk_label_new("Centre"); - gtk_widget_show(label_sphereRefinement_centre); - gtk_table_attach(GTK_TABLE(table1), label_sphereRefinement_centre, - 0, 1, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_sphereRefinement_centre), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for centre - GtkWidget* entry_sphereRefinement_centreX = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_centreX); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_centreX, - 1, 2, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_sphereRefinement_centreY = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_centreY); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_centreY, - 2, 3, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_sphereRefinement_centreZ = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_centreZ); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_centreZ, - 3, 4, 3, 4, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for radius - GtkWidget* label_sphereRefinement_p1 = gtk_label_new("Radius [m]"); - gtk_widget_show(label_sphereRefinement_p1); - gtk_table_attach(GTK_TABLE(table1), label_sphereRefinement_p1, - 0, 1, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_sphereRefinement_p1), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entry for radius - GtkWidget* entry_sphereRefinement_radius = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_radius); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_radius, - 1, 4, 4, 5, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for adding lines - GtkWidget* button1 = gtk_button_new(); - gtk_widget_show(button1); - gtk_table_attach - ( - GTK_TABLE(table1), - button1, - 4, 5, 0, 5, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button1), - "clicked", - G_CALLBACK(addSphereRefinement), - sphereRefinementFramePtr_ - ); - - GtkWidget* alignment1 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment1); - gtk_container_add(GTK_CONTAINER(button1), alignment1); - - GtkWidget* hbox1 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox1); - gtk_container_add(GTK_CONTAINER(alignment1), hbox1); - - GtkWidget* image1 = - gtk_image_new_from_stock("gtk-add", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image1); - gtk_box_pack_start(GTK_BOX(hbox1), image1, FALSE, FALSE, 0); - - GtkWidget* label3 = gtk_label_new_with_mnemonic("Add"); - gtk_widget_show(label3); - gtk_box_pack_start(GTK_BOX(hbox1), label3, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- horizontal separator - GtkWidget* hseparator0 = gtk_hseparator_new(); - gtk_widget_show(hseparator0); - gtk_table_attach(GTK_TABLE(table1), hseparator0, 0, 5, 5, 6, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(GTK_EXPAND | GTK_SHRINK | GTK_FILL), - 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for existing line objects - GtkWidget* label_sphereRefinement_existing = - gtk_label_new("Existing spheres"); - gtk_widget_show(label_sphereRefinement_existing); - gtk_table_attach(GTK_TABLE(table1), label_sphereRefinement_existing, - 0, 1, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- combobox for existing box objects - GtkWidget* comboboxentry_sphereRefinement_createdSpheres = - gtk_combo_new(); - gtk_widget_show(comboboxentry_sphereRefinement_createdSpheres); - gtk_table_attach - ( - GTK_TABLE(table1),comboboxentry_sphereRefinement_createdSpheres, - 1, 2, 6, 7, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0 - ); - - gtk_editable_set_editable - ( - GTK_EDITABLE - ( - GTK_COMBO(comboboxentry_sphereRefinement_createdSpheres)->entry - ), - 0 - ); - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* label_sphereRefinement_selectedCellSize = - gtk_label_new("Cell size [m]"); - gtk_widget_show(label_sphereRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), label_sphereRefinement_selectedCellSize, - 0, 1, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_sphereRefinement_selectedCellSize), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create a label for selected cell size - GtkWidget* entry_sphereRefinement_selectedCellSize = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_selectedCellSize); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_selectedCellSize, - 1, 4, 7, 8, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- create labels for axes - label_axes = gtk_label_new("X"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 1, 2, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Y"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 2, 3, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - - label_axes = gtk_label_new("Z"); - gtk_widget_show(label_axes); - gtk_table_attach(GTK_TABLE(table1), label_axes, - 3, 4, 8, 9, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_axes), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for centre - GtkWidget* label_sphereRefinement_selectedCentre = - gtk_label_new("Centre"); - gtk_widget_show(label_sphereRefinement_selectedCentre); - gtk_table_attach(GTK_TABLE(table1), label_sphereRefinement_selectedCentre, - 0, 1, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment(GTK_MISC(label_sphereRefinement_selectedCentre), 0, 0.5); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for selected centre - GtkWidget* entry_sphereRefinement_selectedCentreX = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_selectedCentreX); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_selectedCentreX, - 1, 2, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_sphereRefinement_selectedCentreY = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_selectedCentreY); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_selectedCentreY, - 2, 3, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - - GtkWidget* entry_sphereRefinement_selectedCentreZ = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_selectedCentreZ); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_selectedCentreZ, - 3, 4, 9, 10, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- label for selected radius - GtkWidget* label_sphereRefinement_selectedRadius = - gtk_label_new("Radius [m]"); - gtk_widget_show(label_sphereRefinement_selectedRadius); - gtk_table_attach(GTK_TABLE(table1), label_sphereRefinement_selectedRadius, - 0, 1, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - gtk_misc_set_alignment - ( - GTK_MISC(label_sphereRefinement_selectedRadius), 0, 0.5 - ); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- entries for radius - GtkWidget* entry_sphereRefinement_selectedRadius = gtk_entry_new(); - gtk_widget_show(entry_sphereRefinement_selectedRadius); - gtk_table_attach(GTK_TABLE(table1), entry_sphereRefinement_selectedRadius, - 1, 4, 10, 11, - (GtkAttachOptions)(GTK_FILL), - (GtkAttachOptions)(0), 0, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - //- set the button for removing patches - GtkWidget* button2 = gtk_button_new(); - gtk_widget_show(button2); - gtk_table_attach - ( - GTK_TABLE(table1), - button2, - 4, 5, 6, 11, - (GtkAttachOptions)(GTK_FILL), (GtkAttachOptions)(0), 0, 5 - ); - - g_signal_connect - ( - G_OBJECT(button2), - "clicked", - G_CALLBACK(removeSphereRefinement), - sphereRefinementFramePtr_ - ); - - GtkWidget* alignment2 = gtk_alignment_new(0.5, 0.5, 0, 0); - gtk_widget_show(alignment2); - gtk_container_add(GTK_CONTAINER(button2), alignment2); - - GtkWidget* hbox2 = gtk_hbox_new(FALSE, 2); - gtk_widget_show(hbox2); - gtk_container_add(GTK_CONTAINER(alignment2), hbox2); - - GtkWidget* image2 = - gtk_image_new_from_stock("gtk-remove", GTK_ICON_SIZE_BUTTON); - gtk_widget_show(image2); - gtk_box_pack_start(GTK_BOX (hbox2), image2, FALSE, FALSE, 0); - - GtkWidget* label5 = gtk_label_new_with_mnemonic("Remove"); - gtk_widget_show(label5); - gtk_box_pack_start(GTK_BOX (hbox2), label5, FALSE, FALSE, 0); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - /* Store pointers to all widgets, for use by lookup_widget(). */ - GLADE_HOOKUP_OBJECT_NO_REF - ( - sphereRefinementFramePtr_, - sphereRefinementFramePtr_, - "sphereRefinementFramePtr_"); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - table1, - "table1" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereName, - "entry_sphereName" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_cellSize, - "entry_sphereRefinement_cellSize" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_centreX, - "entry_sphereRefinement_centreX" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_centreY, - "entry_sphereRefinement_centreY" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_centreZ, - "entry_sphereRefinement_centreZ" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_radius, - "entry_sphereRefinement_radius" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - comboboxentry_sphereRefinement_createdSpheres, - "comboboxentry_sphereRefinement_createdSpheres" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_selectedCellSize, - "entry_sphereRefinement_selectedCellSize" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_selectedCentreX, - "entry_sphereRefinement_selectedCentreX" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_selectedCentreY, - "entry_sphereRefinement_selectedCentreY" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_selectedCentreZ, - "entry_sphereRefinement_selectedCentreZ" - ); - GLADE_HOOKUP_OBJECT - ( - sphereRefinementFramePtr_, - entry_sphereRefinement_selectedRadius, - "entry_sphereRefinement_selectedRadius" - ); - - updateSphereRefinements(sphereRefinementFramePtr_); - - g_signal_connect - ( - G_OBJECT - ( - GTK_ENTRY - ( - GTK_COMBO(comboboxentry_sphereRefinement_createdSpheres)->entry - ) - ), - "changed", - G_CALLBACK(showDataForSphereRefinement), - sphereRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_sphereRefinement_selectedCellSize), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - sphereRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_sphereRefinement_selectedCentreX), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - sphereRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_sphereRefinement_selectedCentreY), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - sphereRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_sphereRefinement_selectedCentreZ), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - sphereRefinementFramePtr_ - ); - - g_signal_connect - ( - G_OBJECT(entry_sphereRefinement_selectedRadius), - "changed", - G_CALLBACK(resetValuesForSelectedLine), - sphereRefinementFramePtr_ - ); - - gtk_widget_show(sphereRefinementFramePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGUI/meshGenGUI.H b/GUI/meshGenGUI/meshGenGUI.H deleted file mode 100644 index 4c6e8b100c15c7c444a53a8411ffb144ad76069a..0000000000000000000000000000000000000000 --- a/GUI/meshGenGUI/meshGenGUI.H +++ /dev/null @@ -1,193 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Class - meshGenGUI - -Description - Implementation of the user inteface - -SourceFiles - meshGenGUI.C - -\*---------------------------------------------------------------------------*/ - -#ifndef meshGenGUI_H -#define meshGenGUI_H - -#include "IOdictionary.H" -#include "wordList.H" -#include "patchRefinement.H" -#include "objectRefinement.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -class triSurface; - -/*---------------------------------------------------------------------------*\ - Class meshGenGUI Declaration -\*---------------------------------------------------------------------------*/ - -class meshGenGUI -{ - // Private data - - //- IOdictionary containing information about cell sizes, etc.. - IOdictionary meshDict_; - - //- pointer to the triangulated surface - mutable triSurface* surfacePtr_; - - // Private member functions - //- create surface from fileName - void createSurface(const fileName&) const; - - //- Disallow default bitwise copy construct - meshGenGUI(const meshGenGUI&); - - //- Disallow default bitwise assignment - void operator=(const meshGenGUI&); - -public: - - // Constructors - - //- Construct from registry - meshGenGUI(const objectRegistry&); - - // Destructor - - ~meshGenGUI(); - - // Member Functions - - //- return surface - const triSurface& surface() const; - - // General meshDict settings - - //- set and get surface file name - void setSurfaceFileName(const fileName&); - fileName surfaceFileName() const; - - //- set and get max cell size - void setMaxCellSize(const scalar s); - scalar maxCellSize() const; - - //- set and get boundary cell size - bool boundaryCellSizeEntryExist() const; - void removeBoundaryCellSize(); - void setBoundaryCellSize(const scalar s); - scalar boundaryCellSize() const; - - //- set and get cell size for automatic refinement - bool minCellSizeEntryExist() const; - void removeMinCellSize(); - void setMinCellSize(const scalar s); - scalar minCellSize() const; - - //- set and get if boundary cells should be used - bool keepCellsIntersectingBoundaryEntryExist() const; - void setKeepCellsIntersectingBoundary(); - void removeKeepCellsIntersectingBoundary(); - bool keepCellsIntersectingBoundary() const; - - //- set and get the check for glued mesh should be used - bool checkForGluedMeshEntryExist() const; - void setCheckForGluedMesh(); - void removeCheckForGluedMesh(); - bool checkForGluedMesh() const; - - // Settings for patch-wise refinement - //- set and get patch refinement - bool patchCellSizeEntryExist() const; - void addPatchCellSize(const patchRefinement&); - void removePatchCellSize(const word&); - List<patchRefinement> patchCellSize() const; - - // Settings for keep cells intersecting patches - //- set end get keep cells intersecting patches - bool keepCellsIntersectingPatchesEntryExist() const; - void addKeepCellsIntersectingPatches(const word&); - void removeKeepCellsIntersectingPatches(const word&); - wordList keepCellsIntersectingPatches() const; - - // Settings for patch-wise boundary layers - //- set and get patches for which the layers should be created - bool bndLayersEntryExist() const; - void addBndLayersPatches(const word&); - void removeBndLayersPatches(const word&); - wordList keepBndLayersPatches() const; - - // Settings for subset-wise refinement - //- set and get functions for face-subset refinement - void setSubsetFileName(const fileName&); - fileName subsetFileName() const; - bool subsetCellSizeEntryExist() const; - void addSubsetCellSize(const patchRefinement&); - void removeSubsetCellSize(const word&); - List<patchRefinement> subsetCellSize() const; - - // object refinement - //- general object refinement stuff - bool objectRefinementEntryExist() const; - PtrList<entry> objectRefinements() const; - void addObjectRefinement(const objectRefinement&); - void removeObjectRefinement(const word& name); - - // rename boundaries - bool renameBoundaryEntryExist() const; - bool defaultPatchNameEntryExist() const; - word defaultPatchName() const; - void setDefaultPatchName(const word&); - void removeDefaultPatchName(); - bool defaultPatchTypeEntryExist() const; - word defaultPatchType() const; - void setDefaultPatchType(const word&); - void removeDefaultPatchType(); - bool newPatchNamesEntryExist() const; - PtrList<entry> newPatchNames() const; - void addNewPatchName(const word&, const dictionary&); - void removePatchName(const word&); - - // write the dictionary - void writeDict() const - { - meshDict_.regIOobject::write(); - } -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/GUI/meshGenGUI/meshGenGUIGeneral.C b/GUI/meshGenGUI/meshGenGUIGeneral.C deleted file mode 100644 index 2f7f517ee32fac0565e9717c1fb986380641fd1c..0000000000000000000000000000000000000000 --- a/GUI/meshGenGUI/meshGenGUIGeneral.C +++ /dev/null @@ -1,176 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGUI.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenGUI::setSurfaceFileName(const fileName& fName) -{ - if( meshDict_.found("surfaceFile") ) - meshDict_.remove("surfaceFile"); - - meshDict_.add("surfaceFile", fName); -} - -fileName meshGenGUI::surfaceFileName() const -{ - if( !meshDict_.found("surfaceFile") ) - { - fileName f(""); - const_cast<IOdictionary&>(meshDict_).add("surfaceFile", f); - } - - return meshDict_.lookup("surfaceFile"); -} - -void meshGenGUI::setMaxCellSize(const scalar s) -{ - if( meshDict_.found("maxCellSize") ) - meshDict_.remove("maxCellSize"); - - meshDict_.add("maxCellSize", s); -} - -scalar meshGenGUI::maxCellSize() const -{ - if( !meshDict_.found("maxCellSize") ) - const_cast<IOdictionary&>(meshDict_).add("maxCellSize", 1.0); - - return readScalar(meshDict_.lookup("maxCellSize")); -} - -bool meshGenGUI::boundaryCellSizeEntryExist() const -{ - word w("boundaryCellSize"); - return meshDict_.found(w); -} - -void meshGenGUI::removeBoundaryCellSize() -{ - meshDict_.remove("boundaryCellSize"); -} - -void meshGenGUI::setBoundaryCellSize(const scalar s) -{ - if( boundaryCellSizeEntryExist() ) - meshDict_.remove("boundaryCellSize"); - - meshDict_.add("boundaryCellSize", s); -} - -scalar meshGenGUI::boundaryCellSize() const -{ - return readScalar(meshDict_.lookup("boundaryCellSize")); -} - -bool meshGenGUI::minCellSizeEntryExist() const -{ - return meshDict_.found("minCellSize"); -} - -void meshGenGUI::removeMinCellSize() -{ - if( minCellSizeEntryExist() ) - meshDict_.remove("minCellSize"); -} - -void meshGenGUI::setMinCellSize(const scalar s) -{ - removeMinCellSize(); - - meshDict_.add("minCellSize", s); -} - -scalar meshGenGUI::minCellSize() const -{ - return readScalar(meshDict_.lookup("minCellSize")); -} - -bool meshGenGUI::keepCellsIntersectingBoundaryEntryExist() const -{ - return meshDict_.found("keepCellsIntersectingBoundary"); -} - -void meshGenGUI::setKeepCellsIntersectingBoundary() -{ - removeKeepCellsIntersectingBoundary(); - - meshDict_.add("keepCellsIntersectingBoundary", 1); -} - -void meshGenGUI::removeKeepCellsIntersectingBoundary() -{ - if( keepCellsIntersectingBoundaryEntryExist() ) - meshDict_.remove("keepCellsIntersectingBoundary"); -} - -bool meshGenGUI::keepCellsIntersectingBoundary() const -{ - if( !keepCellsIntersectingBoundaryEntryExist() ) - return false; - - return meshDict_.lookup("keepCellsIntersectingBoundary"); -} - -bool meshGenGUI::checkForGluedMeshEntryExist() const -{ - return meshDict_.found("checkForGluedMesh"); -} - -void meshGenGUI::setCheckForGluedMesh() -{ - removeCheckForGluedMesh(); - - meshDict_.add("checkForGluedMesh", 1); -} - -void meshGenGUI::removeCheckForGluedMesh() -{ - if( checkForGluedMeshEntryExist() ) - meshDict_.remove("checkForGluedMesh"); -} - -bool meshGenGUI::checkForGluedMesh() const -{ - if( !checkForGluedMeshEntryExist() ) - return false; - - return readBool(meshDict_.lookup("checkForGluedMesh")); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGUI/meshGenGUIKeepCellsIntersectingPatches.C b/GUI/meshGenGUI/meshGenGUIKeepCellsIntersectingPatches.C deleted file mode 100644 index 881a125b0ec85d35b5dc97ffa20a71ca2f76a9c9..0000000000000000000000000000000000000000 --- a/GUI/meshGenGUI/meshGenGUIKeepCellsIntersectingPatches.C +++ /dev/null @@ -1,102 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGUI.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -bool meshGenGUI::keepCellsIntersectingPatchesEntryExist() const -{ - return meshDict_.found("keepCellsIntersectingPatches"); -} - -void meshGenGUI::addKeepCellsIntersectingPatches(const word& pName) -{ - if( keepCellsIntersectingPatchesEntryExist() ) - { - wordList pList(meshDict_.lookup("keepCellsIntersectingPatches")); - - const label size = pList.size(); - pList.setSize(size + 1); - pList[size] = pName; - - meshDict_.remove("keepCellsIntersectingPatches"); - meshDict_.add("keepCellsIntersectingPatches", pList); - } - else - { - wordList pList(1); - pList[0] = pName; - - meshDict_.add("keepCellsIntersectingPatches", pList); - } -} - -void meshGenGUI::removeKeepCellsIntersectingPatches(const word& pName) -{ - if( keepCellsIntersectingPatchesEntryExist() ) - { - wordList pList(meshDict_.lookup("keepCellsIntersectingPatches")); - - label pos(-1); - forAll(pList, elI) - if( pList[elI] == pName ) - { - pos = elI; - break; - } - - pList[pos] = pList[pList.size() - 1]; - pList.setSize(pList.size() - 1); - - meshDict_.remove("keepCellsIntersectingPatches"); - - if( pList.size() != 0 ) - meshDict_.add("keepCellsIntersectingPatches", pList); - } -} - -wordList meshGenGUI::keepCellsIntersectingPatches() const -{ - if( !keepCellsIntersectingPatchesEntryExist() ) - return wordList(); - - wordList pNames(meshDict_.lookup("keepCellsIntersectingPatches")); - return pNames; -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGUI/meshGenGUIObjectRefinement.C b/GUI/meshGenGUI/meshGenGUIObjectRefinement.C deleted file mode 100644 index 1815faa64d5206e3009d41f72d154297c9f1533f..0000000000000000000000000000000000000000 --- a/GUI/meshGenGUI/meshGenGUIObjectRefinement.C +++ /dev/null @@ -1,127 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGUI.H" -#include "dictionaryEntry.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -bool meshGenGUI::objectRefinementEntryExist() const -{ - return meshDict_.found("objectRefinements"); -} - -PtrList<entry> meshGenGUI::objectRefinements() const -{ - if( !objectRefinementEntryExist() ) - { - return PtrList<entry>(); - } - - // Read polyPatchList - Istream& is = meshDict_.lookup("objectRefinements"); - - PtrList<entry> objectEntries(is); - - return objectEntries; -} - -void meshGenGUI::addObjectRefinement(const objectRefinement& object) -{ - if( objectRefinementEntryExist() ) - { - PtrList<entry> objectEntries(meshDict_.lookup("objectRefinements")); - const label s = objectEntries.size(); - - objectEntries.setSize(s+1); - objectEntries.set - ( - s, - new dictionaryEntry(object.name(), object.dict()) - ); - - meshDict_.remove("objectRefinements"); - meshDict_.add("objectRefinements", objectEntries); - } - else - { - PtrList<entry> objectEntries(1); - objectEntries.set - ( - 0, - new dictionaryEntry - ( - object.name(), - object.dict() - ) - ); - - meshDict_.add("objectRefinements", objectEntries); - } -} - -void meshGenGUI::removeObjectRefinement(const word& name) -{ - if( !objectRefinementEntryExist() ) - return; - - PtrList<entry> objectEntries(meshDict_.lookup("objectRefinements")); - meshDict_.remove("objectRefinements"); - - if( objectEntries.size() == 1 ) - return; - - PtrList<entry> refs(objectEntries.size()-1); - label counter(0); - forAll(objectEntries, i) - if( objectEntries[i].keyword() != name ) - { - refs.set - ( - counter++, - new dictionaryEntry - ( - objectEntries[i].keyword(), - objectEntries[i].dict() - ) - ); - } - - meshDict_.add("objectRefinements", refs); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGUI/meshGenGUIPatchRefinement.C b/GUI/meshGenGUI/meshGenGUIPatchRefinement.C deleted file mode 100644 index 24a51cb2393ec0e2dd5a2bcb19791541eb9fb051..0000000000000000000000000000000000000000 --- a/GUI/meshGenGUI/meshGenGUIPatchRefinement.C +++ /dev/null @@ -1,100 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGUI.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -bool meshGenGUI::patchCellSizeEntryExist() const -{ - return meshDict_.found("patchCellSize"); -} - -void meshGenGUI::addPatchCellSize(const patchRefinement& pr) -{ - if( patchCellSizeEntryExist() ) - { - List<patchRefinement> prList(meshDict_.lookup("patchCellSize")); - - const label size = prList.size(); - prList.setSize(size + 1); - prList[size] = pr; - - meshDict_.remove("patchCellSize"); - meshDict_.add("patchCellSize", prList); - } - else - { - List<patchRefinement> prList(1); - prList[0] = pr; - - meshDict_.add("patchCellSize", prList); - } -} - -void meshGenGUI::removePatchCellSize(const word& patchName) -{ - if( patchCellSizeEntryExist() ) - { - List<patchRefinement> prList(meshDict_.lookup("patchCellSize")); - - label pos(-1); - forAll(prList, elI) - if( prList[elI].patchName() == patchName ) - { - pos = elI; - break; - } - - prList[pos] = prList[prList.size() - 1]; - prList.setSize(prList.size() - 1); - - meshDict_.remove("patchCellSize"); - meshDict_.add("patchCellSize", prList); - } -} - -List<patchRefinement> meshGenGUI::patchCellSize() const -{ - if( !patchCellSizeEntryExist() ) - return List<patchRefinement>(); - - List<patchRefinement> pr(meshDict_.lookup("patchCellSize")); - return pr; -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenGUI/meshGenGUIRenameBoundary.C b/GUI/meshGenGUI/meshGenGUIRenameBoundary.C deleted file mode 100644 index 0e76c61af068574d0e00fd1d6f64aeee578a37ef..0000000000000000000000000000000000000000 --- a/GUI/meshGenGUI/meshGenGUIRenameBoundary.C +++ /dev/null @@ -1,269 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenGUI.H" -#include "dictionaryEntry.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -bool meshGenGUI::renameBoundaryEntryExist() const -{ - if( meshDict_.found("renameBoundary") ) - return true; - - return false; -} - -bool meshGenGUI::defaultPatchNameEntryExist() const -{ - if( renameBoundaryEntryExist() ) - { - const dictionary& dict = meshDict_.subDict("renameBoundary"); - - if( dict.found("defaultName") ) - return true; - } - - return false; -} - -word meshGenGUI::defaultPatchName() const -{ - if( defaultPatchNameEntryExist() ) - { - const dictionary& dict = meshDict_.subDict("renameBoundary"); - const word name(dict.lookup("defaultName")); - return name; - } - - return word(); -} - -void meshGenGUI::setDefaultPatchName(const word& name) -{ - if( renameBoundaryEntryExist() ) - { - dictionary dict = meshDict_.subDict("renameBoundary"); - meshDict_.remove("renameBoundary"); - - if( dict.found("defaultName") ) - dict.remove("defaultName"); - - dict.add("defaultName", name); - meshDict_.add("renameBoundary", dict); - } - else - { - dictionary dict; - dict.add("defaultName", name); - meshDict_.add("renameBoundary", dict); - } -} - -void meshGenGUI::removeDefaultPatchName() -{ - if( renameBoundaryEntryExist() ) - { - dictionary dict = meshDict_.subDict("renameBoundary"); - meshDict_.remove("renameBoundary"); - - dict.remove("defaultName"); - - if( dict.toc().size() != 0 ) - meshDict_.add("renameBoundary", dict); - } -} - -bool meshGenGUI::defaultPatchTypeEntryExist() const -{ - if( renameBoundaryEntryExist() ) - { - const dictionary& dict = meshDict_.subDict("renameBoundary"); - - if( dict.found("defaultType") ) - return true; - } - - return false; -} - -word meshGenGUI::defaultPatchType() const -{ - if( defaultPatchNameEntryExist() ) - { - const dictionary& dict = meshDict_.subDict("renameBoundary"); - const word type(dict.lookup("defaultType")); - return type; - } - - return word(); -} - -void meshGenGUI::setDefaultPatchType(const word& type) -{ - if( renameBoundaryEntryExist() ) - { - dictionary dict = meshDict_.subDict("renameBoundary"); - meshDict_.remove("renameBoundary"); - - if( dict.found("defaultType") ) - dict.remove("defaultType"); - - dict.add("defaultType", type); - meshDict_.add("renameBoundary", dict); - } - else - { - dictionary dict; - dict.add("defaultType", type); - meshDict_.add("renameBoundary", dict); - } -} - -void meshGenGUI::removeDefaultPatchType() -{ - if( renameBoundaryEntryExist() ) - { - dictionary dict = meshDict_.subDict("renameBoundary"); - meshDict_.remove("renameBoundary"); - - dict.remove("defaultType"); - - if( dict.toc().size() != 0 ) - meshDict_.add("renameBoundary", dict); - } -} - -bool meshGenGUI::newPatchNamesEntryExist() const -{ - if( renameBoundaryEntryExist() ) - { - const dictionary& dict = meshDict_.subDict("renameBoundary"); - - if( dict.found("newPatchNames") ) - return true; - } - - return false; -} - -PtrList<entry> meshGenGUI::newPatchNames() const -{ - if( newPatchNamesEntryExist() ) - { - const dictionary& dict = meshDict_.subDict("renameBoundary"); - Istream& is = dict.lookup("newPatchNames"); - - PtrList<entry> patchEntries(is); - return patchEntries; - } - - return PtrList<entry>(); -} - -void meshGenGUI::addNewPatchName(const word& name, const dictionary& pDict) -{ - if( renameBoundaryEntryExist() ) - { - dictionary& dict = - const_cast<dictionary&>(meshDict_.subDict("renameBoundary")); - - if( dict.found("newPatchNames") ) - { - Istream& is = dict.lookup("newPatchNames"); - PtrList<entry> entries(is); - - const label s = entries.size(); - entries.setSize(s+1); - entries.set(s, new dictionaryEntry(name, pDict)); - - dict.remove("newPatchNames"); - dict.add("newPatchNames", entries); - } - else - { - PtrList<entry> entries(1); - entries.set(0, new dictionaryEntry(name, pDict)); - dict.add("newPatchNames", entries); - } - } - else - { - PtrList<entry> entries(1); - entries.set(0, new dictionaryEntry(name, pDict)); - dictionary dict; - dict.add("newPatchNames", entries); - meshDict_.add("renameBoundary", dict); - } -} - -void meshGenGUI::removePatchName(const word& name) -{ - if( newPatchNamesEntryExist() ) - { - dictionary& dict = - const_cast<dictionary&>(meshDict_.subDict("renameBoundary")); - - Istream& is = dict.lookup("newPatchNames"); - PtrList<entry> entries(is); - - PtrList<entry> newEntries(entries.size()-1); - label counter(0); - - forAll(entries, i) - { - if( entries[i].keyword() == name ) - continue; - - newEntries.set - ( - counter++, - new dictionaryEntry(entries[i].keyword(), entries[i].dict()) - ); - } - - dict.remove("newPatchNames"); - - if( newEntries.size() != 0 ) - dict.add("newPatchNames", newEntries); - - if( dict.toc().size() == 0 ) - meshDict_.remove("renameBoundary"); - } -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenQt/designer/form1.ui b/GUI/meshGenQt/designer/form1.ui deleted file mode 100644 index d790845a4f7ea2378da4c20cfd8bb6c7eed926c0..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/designer/form1.ui +++ /dev/null @@ -1,47 +0,0 @@ -<!DOCTYPE UI><UI version="3.3" stdsetdef="1"> -<class>Form1</class> -<widget class="QWidget"> - <property name="name"> - <cstring>Form1</cstring> - </property> - <property name="geometry"> - <rect> - <x>0</x> - <y>0</y> - <width>600</width> - <height>480</height> - </rect> - </property> - <property name="caption"> - <string>Form1</string> - </property> - <widget class="QLineEdit"> - <property name="name"> - <cstring>lineEdit1</cstring> - </property> - <property name="geometry"> - <rect> - <x>90</x> - <y>70</y> - <width>174</width> - <height>26</height> - </rect> - </property> - </widget> -</widget> -<connections> - <connection> - <sender>lineEdit1</sender> - <signal>textChanged(const QString&)</signal> - <receiver>Form1</receiver> - <slot>lineEdit1_textChanged(const QString&)</slot> - </connection> -</connections> -<includes> - <include location="local" impldecl="in implementation">form1.ui.h</include> -</includes> -<slots> - <slot>lineEdit1_textChanged( const QString & )</slot> -</slots> -<layoutdefaults spacing="6" margin="11"/> -</UI> diff --git a/GUI/meshGenQt/designer/form1.ui.h b/GUI/meshGenQt/designer/form1.ui.h deleted file mode 100644 index b6881967e9c6326c3910859e90acc025c4aa5453..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/designer/form1.ui.h +++ /dev/null @@ -1,17 +0,0 @@ -/**************************************************************************** -** ui.h extension file, included from the uic-generated form implementation. -** -** If you want to add, delete, or rename functions or slots, use -** Qt Designer to update this file, preserving your code. -** -** You should not define a constructor or destructor in this file. -** Instead, write your code in functions called init() and destroy(). -** These will automatically be called by the form's constructor and -** destructor. -*****************************************************************************/ - - -void Form1::lineEdit1_textChanged( const QString & ) -{ - -} diff --git a/GUI/meshGenQt/designer/generalPage.h b/GUI/meshGenQt/designer/generalPage.h deleted file mode 100644 index 3396fa7a8b0c0e26eb3bc660fdd69c8322038e57..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/designer/generalPage.h +++ /dev/null @@ -1,183 +0,0 @@ -#ifndef FORM1_H -#define FORM1_H - -#include <qvariant.h> - - -#include <QtCore/QVariant> -#include <QtGui/QAction> -#include <QtGui/QApplication> -#include <QtGui/QButtonGroup> -#include <QtGui/QCheckBox> -#include <QtGui/QFrame> -#include <QtGui/QGridLayout> -#include <QtGui/QLabel> -#include <QtGui/QLineEdit> -#include <QtGui/QPushButton> -#include <QtGui/QWidget> -#include <Qt3Support/Q3MimeSourceFactory> - -class Ui_Form1 -{ -public: - QGridLayout *gridLayout; - QLabel *textLabel1; - QLineEdit *lineEdit1; - QPushButton *pushButton1; - QLabel *textLabel2; - QLineEdit *lineEdit2; - QFrame *line1; - QCheckBox *checkBox1; - QLineEdit *lineEdit3; - QLabel *textLabel3; - QFrame *line2; - QCheckBox *checkBox2; - QLabel *textLabel4; - QLineEdit *lineEdit4; - QFrame *line3; - QCheckBox *checkBox3; - QCheckBox *checkBox4; - - void setupUi(QWidget *Form1) - { - Form1->setObjectName(QString::fromUtf8("Form1")); - gridLayout = new QGridLayout(Form1); - gridLayout->setSpacing(6); - gridLayout->setMargin(11); - gridLayout->setObjectName(QString::fromUtf8("gridLayout")); - textLabel1 = new QLabel(Form1); - textLabel1->setObjectName(QString::fromUtf8("textLabel1")); - textLabel1->setWordWrap(false); - - gridLayout->addWidget(textLabel1, 0, 0, 1, 1); - - lineEdit1 = new QLineEdit(Form1); - lineEdit1->setObjectName(QString::fromUtf8("lineEdit1")); - - gridLayout->addWidget(lineEdit1, 0, 1, 1, 2); - - pushButton1 = new QPushButton(Form1); - pushButton1->setObjectName(QString::fromUtf8("pushButton1")); - - gridLayout->addWidget(pushButton1, 0, 3, 1, 1); - - textLabel2 = new QLabel(Form1); - textLabel2->setObjectName(QString::fromUtf8("textLabel2")); - textLabel2->setWordWrap(false); - - gridLayout->addWidget(textLabel2, 1, 0, 1, 1); - - lineEdit2 = new QLineEdit(Form1); - lineEdit2->setObjectName(QString::fromUtf8("lineEdit2")); - - gridLayout->addWidget(lineEdit2, 1, 1, 1, 2); - - line1 = new QFrame(Form1); - line1->setObjectName(QString::fromUtf8("line1")); - line1->setFrameShape(QFrame::HLine); - line1->setFrameShadow(QFrame::Sunken); - - gridLayout->addWidget(line1, 2, 0, 1, 4); - - checkBox1 = new QCheckBox(Form1); - checkBox1->setObjectName(QString::fromUtf8("checkBox1")); - - gridLayout->addWidget(checkBox1, 3, 0, 1, 2); - - lineEdit3 = new QLineEdit(Form1); - lineEdit3->setObjectName(QString::fromUtf8("lineEdit3")); - - gridLayout->addWidget(lineEdit3, 4, 2, 1, 1); - - textLabel3 = new QLabel(Form1); - textLabel3->setObjectName(QString::fromUtf8("textLabel3")); - textLabel3->setWordWrap(false); - - gridLayout->addWidget(textLabel3, 4, 0, 1, 1); - - line2 = new QFrame(Form1); - line2->setObjectName(QString::fromUtf8("line2")); - line2->setFrameShape(QFrame::HLine); - line2->setFrameShadow(QFrame::Sunken); - - gridLayout->addWidget(line2, 5, 0, 1, 4); - - checkBox2 = new QCheckBox(Form1); - checkBox2->setObjectName(QString::fromUtf8("checkBox2")); - - gridLayout->addWidget(checkBox2, 6, 0, 1, 1); - - textLabel4 = new QLabel(Form1); - textLabel4->setObjectName(QString::fromUtf8("textLabel4")); - textLabel4->setWordWrap(false); - - gridLayout->addWidget(textLabel4, 7, 0, 1, 1); - - lineEdit4 = new QLineEdit(Form1); - lineEdit4->setObjectName(QString::fromUtf8("lineEdit4")); - - gridLayout->addWidget(lineEdit4, 7, 1, 1, 2); - - line3 = new QFrame(Form1); - line3->setObjectName(QString::fromUtf8("line3")); - line3->setFrameShape(QFrame::HLine); - line3->setFrameShadow(QFrame::Sunken); - - gridLayout->addWidget(line3, 8, 0, 1, 4); - - checkBox3 = new QCheckBox(Form1); - checkBox3->setObjectName(QString::fromUtf8("checkBox3")); - - gridLayout->addWidget(checkBox3, 9, 0, 1, 3); - - checkBox4 = new QCheckBox(Form1); - checkBox4->setObjectName(QString::fromUtf8("checkBox4")); - - gridLayout->addWidget(checkBox4, 10, 0, 1, 2); - - - retranslateUi(Form1); - - QSize size(600, 480); - size = size.expandedTo(Form1->minimumSizeHint()); - Form1->resize(size); - - - QMetaObject::connectSlotsByName(Form1); - } // setupUi - - void retranslateUi(QWidget *Form1) - { - Form1->setWindowTitle(QApplication::translate("Form1", "Form1", 0, QApplication::UnicodeUTF8)); - textLabel1->setText(QApplication::translate("Form1", "textLabel1", 0, QApplication::UnicodeUTF8)); - pushButton1->setText(QApplication::translate("Form1", "pushButton1", 0, QApplication::UnicodeUTF8)); - textLabel2->setText(QApplication::translate("Form1", "textLabel2", 0, QApplication::UnicodeUTF8)); - checkBox1->setText(QApplication::translate("Form1", "checkBox1", 0, QApplication::UnicodeUTF8)); - textLabel3->setText(QApplication::translate("Form1", "textLabel3", 0, QApplication::UnicodeUTF8)); - checkBox2->setText(QApplication::translate("Form1", "checkBox2", 0, QApplication::UnicodeUTF8)); - textLabel4->setText(QApplication::translate("Form1", "textLabel4", 0, QApplication::UnicodeUTF8)); - checkBox3->setText(QApplication::translate("Form1", "checkBox3", 0, QApplication::UnicodeUTF8)); - checkBox4->setText(QApplication::translate("Form1", "checkBox4", 0, QApplication::UnicodeUTF8)); - Q_UNUSED(Form1); - } // retranslateUi - -}; - -namespace Ui { - class Form1: public Ui_Form1 {}; -} // namespace Ui - -class Form1 : public QWidget, public Ui::Form1 -{ - Q_OBJECT - -public: - Form1(QWidget* parent = 0, const char* name = 0, Qt::WindowFlags fl = 0); - ~Form1(); - -protected slots: - virtual void languageChange(); - -}; - -#endif // FORM1_H diff --git a/GUI/meshGenQt/designer/generalPage.ui b/GUI/meshGenQt/designer/generalPage.ui deleted file mode 100644 index 0926604b284d57009d8a5f614af5436f9ea8fbd7..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/designer/generalPage.ui +++ /dev/null @@ -1,159 +0,0 @@ -<!DOCTYPE UI><UI version="3.3" stdsetdef="1"> -<class>Form1</class> -<widget class="QWidget"> - <property name="name"> - <cstring>Form1</cstring> - </property> - <property name="geometry"> - <rect> - <x>0</x> - <y>0</y> - <width>600</width> - <height>480</height> - </rect> - </property> - <property name="caption"> - <string>Form1</string> - </property> - <grid> - <property name="name"> - <cstring>unnamed</cstring> - </property> - <widget class="QLabel" row="0" column="0"> - <property name="name"> - <cstring>textLabel1</cstring> - </property> - <property name="text"> - <string>textLabel1</string> - </property> - </widget> - <widget class="QLineEdit" row="0" column="1" rowspan="1" colspan="2"> - <property name="name"> - <cstring>lineEdit1</cstring> - </property> - </widget> - <widget class="QPushButton" row="0" column="3"> - <property name="name"> - <cstring>pushButton1</cstring> - </property> - <property name="text"> - <string>pushButton1</string> - </property> - </widget> - <widget class="QLabel" row="1" column="0"> - <property name="name"> - <cstring>textLabel2</cstring> - </property> - <property name="text"> - <string>textLabel2</string> - </property> - </widget> - <widget class="QLineEdit" row="1" column="1" rowspan="1" colspan="2"> - <property name="name"> - <cstring>lineEdit2</cstring> - </property> - </widget> - <widget class="Line" row="2" column="0" rowspan="1" colspan="4"> - <property name="name"> - <cstring>line1</cstring> - </property> - <property name="frameShape"> - <enum>HLine</enum> - </property> - <property name="frameShadow"> - <enum>Sunken</enum> - </property> - <property name="orientation"> - <enum>Horizontal</enum> - </property> - </widget> - <widget class="QCheckBox" row="3" column="0" rowspan="1" colspan="2"> - <property name="name"> - <cstring>checkBox1</cstring> - </property> - <property name="text"> - <string>checkBox1</string> - </property> - </widget> - <widget class="QLineEdit" row="4" column="2"> - <property name="name"> - <cstring>lineEdit3</cstring> - </property> - </widget> - <widget class="QLabel" row="4" column="0"> - <property name="name"> - <cstring>textLabel3</cstring> - </property> - <property name="text"> - <string>textLabel3</string> - </property> - </widget> - <widget class="Line" row="5" column="0" rowspan="1" colspan="4"> - <property name="name"> - <cstring>line2</cstring> - </property> - <property name="frameShape"> - <enum>HLine</enum> - </property> - <property name="frameShadow"> - <enum>Sunken</enum> - </property> - <property name="orientation"> - <enum>Horizontal</enum> - </property> - </widget> - <widget class="QCheckBox" row="6" column="0"> - <property name="name"> - <cstring>checkBox2</cstring> - </property> - <property name="text"> - <string>checkBox2</string> - </property> - </widget> - <widget class="QLabel" row="7" column="0"> - <property name="name"> - <cstring>textLabel4</cstring> - </property> - <property name="text"> - <string>textLabel4</string> - </property> - </widget> - <widget class="QLineEdit" row="7" column="1" rowspan="1" colspan="2"> - <property name="name"> - <cstring>lineEdit4</cstring> - </property> - </widget> - <widget class="Line" row="8" column="0" rowspan="1" colspan="4"> - <property name="name"> - <cstring>line3</cstring> - </property> - <property name="frameShape"> - <enum>HLine</enum> - </property> - <property name="frameShadow"> - <enum>Sunken</enum> - </property> - <property name="orientation"> - <enum>Horizontal</enum> - </property> - </widget> - <widget class="QCheckBox" row="9" column="0" rowspan="1" colspan="3"> - <property name="name"> - <cstring>checkBox3</cstring> - </property> - <property name="text"> - <string>checkBox3</string> - </property> - </widget> - <widget class="QCheckBox" row="10" column="0" rowspan="1" colspan="2"> - <property name="name"> - <cstring>checkBox4</cstring> - </property> - <property name="text"> - <string>checkBox4</string> - </property> - </widget> - </grid> -</widget> -<layoutdefaults spacing="6" margin="11"/> -</UI> diff --git a/GUI/meshGenQt/designer/mainWindow.h b/GUI/meshGenQt/designer/mainWindow.h deleted file mode 100755 index 50d618a748e4bf543f4824a63ba6a2ef50def22f..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/designer/mainWindow.h +++ /dev/null @@ -1,93 +0,0 @@ -#ifndef FORM1_H -#define FORM1_H - -#include <qvariant.h> - - -#include <Qt3Support/Q3MainWindow> -#include <QtCore/QVariant> -#include <QtGui/QAction> -#include <QtGui/QApplication> -#include <QtGui/QButtonGroup> -#include <QtGui/QPushButton> -#include <QtGui/QTabWidget> -#include <QtGui/QWidget> -#include <Qt3Support/Q3MimeSourceFactory> - -class Ui_meshGenQt -{ -public: - QWidget *widget; - QPushButton *saveButton; - QPushButton *quitButton; - QTabWidget *tabWidget; - QWidget *tab; - QWidget *tab1; - QWidget *TabPage; - - void setupUi(Q3MainWindow *meshGenQt) - { - meshGenQt->setObjectName(QString::fromUtf8("meshGenQt")); - widget = new QWidget(meshGenQt); - widget->setObjectName(QString::fromUtf8("widget")); - saveButton = new QPushButton(widget); - saveButton->setObjectName(QString::fromUtf8("saveButton")); - saveButton->setGeometry(QRect(11, 11, 112, 24)); - quitButton = new QPushButton(widget); - quitButton->setObjectName(QString::fromUtf8("quitButton")); - quitButton->setGeometry(QRect(129, 11, 112, 24)); - tabWidget = new QTabWidget(widget); - tabWidget->setObjectName(QString::fromUtf8("tabWidget")); - tabWidget->setGeometry(QRect(9, 41, 580, 406)); - tab = new QWidget(); - tab->setObjectName(QString::fromUtf8("tab")); - tabWidget->addTab(tab, QApplication::translate("meshGenQt", "General settings", 0, QApplication::UnicodeUTF8)); - tab1 = new QWidget(); - tab1->setObjectName(QString::fromUtf8("tab1")); - tabWidget->addTab(tab1, QApplication::translate("meshGenQt", "Refinement", 0, QApplication::UnicodeUTF8)); - TabPage = new QWidget(); - TabPage->setObjectName(QString::fromUtf8("TabPage")); - tabWidget->addTab(TabPage, QApplication::translate("meshGenQt", "Rename patches", 0, QApplication::UnicodeUTF8)); - meshGenQt->setCentralWidget(widget); - - retranslateUi(meshGenQt); - - QSize size(600, 480); - size = size.expandedTo(meshGenQt->minimumSizeHint()); - meshGenQt->resize(size); - - - QMetaObject::connectSlotsByName(meshGenQt); - } // setupUi - - void retranslateUi(Q3MainWindow *meshGenQt) - { - meshGenQt->setWindowTitle(QApplication::translate("meshGenQt", "Form1", 0, QApplication::UnicodeUTF8)); - saveButton->setText(QApplication::translate("meshGenQt", "Save meshDict", 0, QApplication::UnicodeUTF8)); - quitButton->setText(QApplication::translate("meshGenQt", "Quit", 0, QApplication::UnicodeUTF8)); - tabWidget->setTabText(tabWidget->indexOf(tab), QApplication::translate("meshGenQt", "General settings", 0, QApplication::UnicodeUTF8)); - tabWidget->setTabText(tabWidget->indexOf(tab1), QApplication::translate("meshGenQt", "Refinement", 0, QApplication::UnicodeUTF8)); - tabWidget->setTabText(tabWidget->indexOf(TabPage), QApplication::translate("meshGenQt", "Rename patches", 0, QApplication::UnicodeUTF8)); - Q_UNUSED(meshGenQt); - } // retranslateUi - -}; - -namespace Ui { - class meshGenQt: public Ui_meshGenQt {}; -} // namespace Ui - -class meshGenQt : public Q3MainWindow, public Ui::meshGenQt -{ - Q_OBJECT - -public: - meshGenQt(QWidget* parent = 0, const char* name = 0, Qt::WindowFlags fl = Qt::WType_TopLevel); - ~meshGenQt(); - -protected slots: - virtual void languageChange(); - -}; - -#endif // FORM1_H diff --git a/GUI/meshGenQt/designer/mainWindow.ui b/GUI/meshGenQt/designer/mainWindow.ui deleted file mode 100755 index 79d44076cb87656bce98eb4a8ed6ca0b9dd0d221..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/designer/mainWindow.ui +++ /dev/null @@ -1,89 +0,0 @@ -<ui version="4.0" > - <class>meshGenQt</class> - <widget class="Q3MainWindow" name="meshGenQt" > - <property name="geometry" > - <rect> - <x>0</x> - <y>0</y> - <width>600</width> - <height>480</height> - </rect> - </property> - <property name="windowTitle" > - <string>Form1</string> - </property> - <widget class="QWidget" name="widget" > - <property name="geometry" > - <rect> - <x>0</x> - <y>0</y> - <width>600</width> - <height>480</height> - </rect> - </property> - <widget class="QPushButton" name="saveButton" > - <property name="geometry" > - <rect> - <x>11</x> - <y>11</y> - <width>112</width> - <height>24</height> - </rect> - </property> - <property name="text" > - <string>Save meshDict</string> - </property> - </widget> - <widget class="QPushButton" name="quitButton" > - <property name="geometry" > - <rect> - <x>129</x> - <y>11</y> - <width>112</width> - <height>24</height> - </rect> - </property> - <property name="text" > - <string>Quit</string> - </property> - </widget> - <widget class="QTabWidget" name="tabWidget" > - <property name="geometry" > - <rect> - <x>9</x> - <y>41</y> - <width>580</width> - <height>406</height> - </rect> - </property> - <widget class="QWidget" name="tab" > - <attribute name="title" > - <string>General settings</string> - </attribute> - </widget> - <widget class="QWidget" name="tab" > - <attribute name="title" > - <string>Refinement</string> - </attribute> - </widget> - <widget class="QWidget" name="TabPage" > - <attribute name="title" > - <string>Rename patches</string> - </attribute> - </widget> - </widget> - </widget> - </widget> - <layoutdefault spacing="6" margin="11" /> - <pixmapfunction>qPixmapFromMimeSource</pixmapfunction> - <customwidgets> - <customwidget> - <class>Q3MainWindow</class> - <extends>QWidget</extends> - <header>q3mainwindow.h</header> - <container>1</container> - </customwidget> - </customwidgets> - <resources/> - <connections/> -</ui> diff --git a/GUI/meshGenQt/makeResources b/GUI/meshGenQt/makeResources deleted file mode 100755 index 02ff8996c8be2d92a35c4a2aa07a5e4df8cd6f22..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/makeResources +++ /dev/null @@ -1,3 +0,0 @@ -#!/bin/sh -$QTDIR/bin/moc meshGenQt.H -o meshGenQt.moc.C -$QTDIR/bin/moc meshGenQtGeneralSettings.H -o meshGenQtGeneralSettings.moc.C diff --git a/GUI/meshGenQt/meshGenQt.C b/GUI/meshGenQt/meshGenQt.C deleted file mode 100755 index a3f56d7db6d194b5ce069435cfaa78085b87d817..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/meshGenQt.C +++ /dev/null @@ -1,115 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenQt.H" -#include "objectRegistry.H" -#include "Time.H" - -#include "meshGenQtGeneralSettings.H" - -#include <qlayout.h> -#include <qvbox.h> - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from objectRegistry -meshGenQt::meshGenQt -( - label argc, char* argv[], const objectRegistry& reg -) -: - QMainWindow(), - meshGui_(reg), - saveButtonPtr_(NULL), - quitButtonPtr_(NULL), - tabWidgetPtr_(NULL), - tabGeneralSettingsPtr_(NULL), - tabRefinementPtr_(NULL), - tabPatchRenamePtr_(NULL) -{ - createMainWindow(); -} - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -meshGenQt::~meshGenQt() -{ -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenQt::createMainWindow() -{ - QWidget* widget = new QWidget(this); - widget->setGeometry(QRect(0, 0, 600, 480)); - - //- create and add save button - saveButtonPtr_ = new QPushButton(QString("Save meshDict"), widget); - saveButtonPtr_->setGeometry(QRect(11, 11, 150, 24)); - connect - ( - saveButtonPtr_, - SIGNAL(clicked()), - this, - SLOT(saveMeshDictCallback()) - ); - - //- create and add quit button - quitButtonPtr_ = new QPushButton(QString("Quit"), widget); - quitButtonPtr_->setGeometry(QRect(160, 11, 180, 24)); - connect(quitButtonPtr_, SIGNAL(clicked()), qApp, SLOT(quit())); - - //- create the table - tabWidgetPtr_ = new QTabWidget(widget); - tabWidgetPtr_->setGeometry(QRect(9, 41, 580, 406)); - - tabGeneralSettingsPtr_ = new meshGenQtGeneralSettings(widget, meshGui_); - tabWidgetPtr_->addTab(tabGeneralSettingsPtr_, "General settings"); - - QWidget* tab1 = new QWidget(); - tabWidgetPtr_->addTab(tab1, "Refinement"); - - //- set the front page - this->setCentralWidget(widget); - - //- resize to the desired size - QSize size(600, 480); - size = size.expandedTo(this->minimumSizeHint()); - this->resize(size); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenQt/meshGenQt.H b/GUI/meshGenQt/meshGenQt.H deleted file mode 100755 index 95bf8a3b2d107abfdc0b565d082c9d87abaed5d7..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/meshGenQt.H +++ /dev/null @@ -1,127 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Class - meshGenQt - -Description - Graphical user inteface using Qt - -SourceFiles - meshGenQt.C - -\*---------------------------------------------------------------------------*/ - -#ifndef meshGenQt_H -#define meshGenQt_H - -#include "meshGenGUI.H" - -#include <qvariant.h> -#include "qwidget.h" -#include <qapplication.h> -#include <qmainwindow.h> -#include <qpushbutton.h> -#include <qtabwidget.h> -#include <qaction.h> - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -//- Forward declarations -class triSurf; - -class meshGenQtGeneralSettings; - -/*---------------------------------------------------------------------------*\ - Class meshGenQt Declaration -\*---------------------------------------------------------------------------*/ - -class meshGenQt -: - public QMainWindow -{ - Q_OBJECT - - // Private data - - //- mesh generation dictionary - meshGenGUI meshGui_; - - //- main window data - QPushButton* saveButtonPtr_; - QPushButton* quitButtonPtr_; - QTabWidget* tabWidgetPtr_; - meshGenQtGeneralSettings* tabGeneralSettingsPtr_; - QWidget* tabRefinementPtr_; - QWidget* tabPatchRenamePtr_; - -private slots: - - // Private callback functions - - //- save meshDict file - void saveMeshDictCallback() - { - meshGui_.writeDict(); - } - -private: - - // Private member functions - - //- create main window - void createMainWindow(); - - //- Disallow default bitwise copy construct - meshGenQt(const meshGenQt&); - - //- Disallow default bitwise assignment - void operator=(const meshGenQt&); - -public: - - // Constructors - - //- Construct from registry - meshGenQt(label argc, char* argv[], const objectRegistry&); - - // Destructor - - ~meshGenQt(); - - // Member Functions -}; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/GUI/meshGenQt/meshGenQtGeneralSettings.C b/GUI/meshGenQt/meshGenQtGeneralSettings.C deleted file mode 100755 index cb32df50eb3a2015770f00f148749f8366fa4eb6..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/meshGenQtGeneralSettings.C +++ /dev/null @@ -1,380 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "meshGenQtGeneralSettings.H" - -#include "helperFunctions.H" - -#include <qlabel.h> -#include <qlayout.h> -#include <qfiledialog.h> - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from objectRegistry -meshGenQtGeneralSettings::meshGenQtGeneralSettings -( - ::QWidget* parent, meshGenGUI& meshGui -) -: - QWidget(parent), - meshGui_(meshGui), - openButtonPtr_(NULL), - surfaceFileEditPtr_(NULL), - maxCellSizeEditPtr_(NULL), - bndCellSizeCheckPtr_(NULL), - bndCellSizeEditPtr_(NULL), - autoRefineCheckPtr_(NULL), - autoRefineCellSizeEditPtr_(NULL), - keepBndCellsCheckPtr_(NULL), - gluedMeshCheckPtr_(NULL) -{ - createWindow(); -} - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -meshGenQtGeneralSettings::~meshGenQtGeneralSettings() -{ -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void meshGenQtGeneralSettings::createWindow() -{ - QGridLayout* gridLayout = new QGridLayout(this); - gridLayout->setSpacing(6); - gridLayout->setMargin(11); - - //- set surface file name - QLabel* surfaceLabel = new QLabel(QString("Surface file name"), this); - - gridLayout->addWidget(surfaceLabel, 0, 0); - - surfaceFileEditPtr_ = new QLineEdit(this); - surfaceFileEditPtr_->setText(meshGui_.surfaceFileName()); - gridLayout->addWidget(surfaceFileEditPtr_, 0, 1); - - openButtonPtr_ = new QPushButton(QString("Open"), this); - connect(openButtonPtr_, SIGNAL(clicked()), this, SLOT(openSurfaceFile())); - - gridLayout->addWidget(openButtonPtr_, 0, 3); - - //- set max cell size - QLabel* maxCellSize = new QLabel(QString("Max cell size [m]"), this); - gridLayout->addWidget(maxCellSize, 1, 0); - - maxCellSizeEditPtr_ = new QLineEdit(this); - maxCellSizeEditPtr_->setText(help::scalarToText(meshGui_.maxCellSize())); - gridLayout->addWidget(maxCellSizeEditPtr_, 1, 1); - - connect - ( - maxCellSizeEditPtr_, - SIGNAL(textChanged(const QString&)), - this, - SLOT(setMaxCellSize(const QString&)) - ); - - QFrame* line1 = new QFrame(this); - //line1->setObjectName(QString::fromUtf8("line1")); - line1->setFrameShape(QFrame::HLine); - line1->setFrameShadow(QFrame::Sunken); - - gridLayout->addMultiCellWidget(line1, 2, 2, 0, 3); - - //- bnd cell size settings - bndCellSizeCheckPtr_ = - new QCheckBox(QString("Use different boundary cell size"), this); - - gridLayout->addMultiCellWidget(bndCellSizeCheckPtr_, 3, 3, 0, 2); - - bndCellSizeEditPtr_ = new QLineEdit(this); - - if( meshGui_.boundaryCellSizeEntryExist() ) - { - bndCellSizeCheckPtr_->setChecked(true); - bndCellSizeEditPtr_->setText - ( - help::scalarToText(meshGui_.boundaryCellSize()) - ); - } - else - { - bndCellSizeEditPtr_->setReadOnly(true); - } - - connect - ( - bndCellSizeCheckPtr_, - SIGNAL(clicked()), - this, - SLOT(activateBndCellSize()) - ); - - connect - ( - bndCellSizeEditPtr_, - SIGNAL(textChanged(const QString&)), - this, - SLOT(setBndCellSize(const QString&)) - ); - - gridLayout->addWidget(bndCellSizeEditPtr_, 4, 1); - - QLabel* bndCellSize = new QLabel(QString("Bnd cell size [m]"), this); - - gridLayout->addWidget(bndCellSize, 4, 0); - - QFrame* line2 = new QFrame(this); - line2->setFrameShape(QFrame::HLine); - line2->setFrameShadow(QFrame::Sunken); - - gridLayout->addMultiCellWidget(line2, 5, 5, 0, 3); - - //- auto refinement settings - autoRefineCheckPtr_ = new QCheckBox("Use automatic refinement", this); - - connect - ( - autoRefineCheckPtr_, - SIGNAL(clicked()), - this, - SLOT(activateMinCellSize()) - ); - - gridLayout->addMultiCellWidget(autoRefineCheckPtr_, 6, 6, 0, 2); - - QLabel* minCellSize = new QLabel(QString("Min cell size [m]"), this); - gridLayout->addWidget(minCellSize, 7, 0); - - autoRefineCellSizeEditPtr_ = new QLineEdit(this); - gridLayout->addWidget(autoRefineCellSizeEditPtr_, 7, 1); - - if( meshGui_.minCellSizeEntryExist() ) - { - autoRefineCheckPtr_->setChecked(true); - autoRefineCellSizeEditPtr_->setText - ( - help::scalarToText(meshGui_.minCellSize()) - ); - } - else - { - autoRefineCellSizeEditPtr_->setReadOnly(true); - } - - connect - ( - autoRefineCellSizeEditPtr_, - SIGNAL(textChanged(const QString&)), - this, - SLOT(setMinCellSize(const QString&)) - ); - - QFrame* line3 = new QFrame(this); - line3->setFrameShape(QFrame::HLine); - line3->setFrameShadow(QFrame::Sunken); - - gridLayout->addMultiCellWidget(line3, 8, 8, 0, 3); - - //- keep boundary intersected cells - keepBndCellsCheckPtr_ = - new QCheckBox(QString("Keep cell intersecting boundary"), this); - - if( meshGui_.keepCellsIntersectingBoundaryEntryExist() ) - { - keepBndCellsCheckPtr_->setChecked(true); - } - else - { - keepBndCellsCheckPtr_->setChecked(false); - } - - connect - ( - keepBndCellsCheckPtr_, - SIGNAL(clicked()), - this, - SLOT(activateKeepCellsIntersectingBoundary()) - ); - - gridLayout->addMultiCellWidget(keepBndCellsCheckPtr_, 9, 9, 0, 2); - - //- remove glued mesh - gluedMeshCheckPtr_ = - new QCheckBox(QString("Remove glued mesh parts"), this); - - if( meshGui_.checkForGluedMeshEntryExist() ) - { - gluedMeshCheckPtr_->setChecked(true); - } - else - { - gluedMeshCheckPtr_->setChecked(false); - } - - connect - ( - gluedMeshCheckPtr_, - SIGNAL(clicked()), - this, - SLOT(activateCheckForGluedMesh()) - ); - - gridLayout->addMultiCellWidget(gluedMeshCheckPtr_, 10, 10, 0, 2); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -// Private slots - -void meshGenQtGeneralSettings::openSurfaceFile() -{ - QString fn = - QFileDialog::getOpenFileName - ( - QString::null, - "Surface files (*.ftr *.stl)", - this - ); - - if( !fn.isEmpty() ) - { - surfaceFileEditPtr_->setText(fn); - fileName fName(fn.ascii()); - meshGui_.setSurfaceFileName(fName); - } -} - -void meshGenQtGeneralSettings::setMaxCellSize(const QString& s) -{ - const word sn(s.ascii()); - - const scalar size = help::textToScalar(sn); - meshGui_.setMaxCellSize(size); -} - -void meshGenQtGeneralSettings::activateBndCellSize() -{ - if( bndCellSizeCheckPtr_->isChecked() ) - { - bndCellSizeEditPtr_->setReadOnly(false); - } - else - { - bndCellSizeEditPtr_->setText(QString("")); - bndCellSizeEditPtr_->setReadOnly(true); - meshGui_.removeBoundaryCellSize(); - } -} - -void meshGenQtGeneralSettings::setBndCellSize(const QString& s) -{ - if( bndCellSizeCheckPtr_->isChecked() ) - { - const word sn(s.ascii()); - - const scalar size = help::textToScalar(sn); - meshGui_.setBoundaryCellSize(size); - } -} - -void meshGenQtGeneralSettings::activateMinCellSize() -{ - if( autoRefineCheckPtr_->isChecked() ) - { - autoRefineCellSizeEditPtr_->setReadOnly(false); - } - else - { - autoRefineCellSizeEditPtr_->setText(QString("")); - autoRefineCellSizeEditPtr_->setReadOnly(true); - meshGui_.removeMinCellSize(); - } -} - -void meshGenQtGeneralSettings::setMinCellSize(const QString& s) -{ - if( bndCellSizeCheckPtr_->isChecked() ) - { - const word sn(s.ascii()); - - const scalar size = help::textToScalar(sn); - meshGui_.setMinCellSize(size); - } -} - -void meshGenQtGeneralSettings::activateKeepCellsIntersectingBoundary() -{ - if( keepBndCellsCheckPtr_->isChecked() ) - { - meshGui_.setKeepCellsIntersectingBoundary(); - } - else - { - meshGui_.removeKeepCellsIntersectingBoundary(); - - if( gluedMeshCheckPtr_->isChecked() ) - { - gluedMeshCheckPtr_->setChecked(false); - meshGui_.removeCheckForGluedMesh(); - } - } -} - -void meshGenQtGeneralSettings::activateCheckForGluedMesh() -{ - if( keepBndCellsCheckPtr_->isChecked() ) - { - meshGui_.setCheckForGluedMesh(); - - if( gluedMeshCheckPtr_->isChecked() ) - { - meshGui_.setCheckForGluedMesh(); - } - else - { - meshGui_.removeCheckForGluedMesh(); - } - } - else - { - meshGui_.removeCheckForGluedMesh(); - } -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/GUI/meshGenQt/meshGenQtGeneralSettings.H b/GUI/meshGenQt/meshGenQtGeneralSettings.H deleted file mode 100755 index 149df8ce3e540eccd2e9695610411bbf3fdcac5a..0000000000000000000000000000000000000000 --- a/GUI/meshGenQt/meshGenQtGeneralSettings.H +++ /dev/null @@ -1,148 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Class - meshGenQtGeneralSettings - -Description - General setting page - -SourceFiles - meshGenQtGeneralSettings.C - -\*---------------------------------------------------------------------------*/ - -#ifndef meshGenQtGeneralSettings_H -#define meshGenQtGeneralSettings_H - -#include "meshGenGUI.H" - -#include <qvariant.h> -#include <qwidget.h> -#include <qapplication.h> -#include <qpushbutton.h> -#include <qlineedit.h> -#include <qcheckbox.h> -#include <qaction.h> - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -//- Forward declarations - -/*---------------------------------------------------------------------------*\ - Class meshGenQtGeneralSettings Declaration -\*---------------------------------------------------------------------------*/ - -class meshGenQtGeneralSettings -: - public QWidget -{ - Q_OBJECT - - // Private data - - //- mesh generation dictionary - meshGenGUI& meshGui_; - - //- main window data - QPushButton* openButtonPtr_; - QLineEdit* surfaceFileEditPtr_; - QLineEdit* maxCellSizeEditPtr_; - - QCheckBox* bndCellSizeCheckPtr_; - QLineEdit* bndCellSizeEditPtr_; - - QCheckBox* autoRefineCheckPtr_; - QLineEdit* autoRefineCellSizeEditPtr_; - - QCheckBox* keepBndCellsCheckPtr_; - QCheckBox* gluedMeshCheckPtr_; - -private slots: - - // Private callback functions - - //- open surface file - void openSurfaceFile(); - - //- set max cell size - void setMaxCellSize(const QString&); - - //- set activity of bndCellSize - void activateBndCellSize(); - - //- set bndCellSize - void setBndCellSize(const QString&); - - //- set activity of auto refinement - void activateMinCellSize(); - - //- set min size in auto refinement - void setMinCellSize(const QString&); - - //- set activity of keepCellsIntersectingBoundary - void activateKeepCellsIntersectingBoundary(); - - //- set activity of glued mesh check - void activateCheckForGluedMesh(); - -private: - - // Private member functions - - //- create window - void createWindow(); - - //- Disallow default bitwise copy construct - meshGenQtGeneralSettings(const meshGenQtGeneralSettings&); - - //- Disallow default bitwise assignment - void operator=(const meshGenQtGeneralSettings&); - -public: - - // Constructors - - //- Construct parent and meshGenGUI - meshGenQtGeneralSettings(::QWidget* parent, meshGenGUI& meshGui); - - // Destructor - - virtual ~meshGenQtGeneralSettings(); - - // Member Functions -}; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/README b/README new file mode 100644 index 0000000000000000000000000000000000000000..43eb0ae0bc3139ecb4cb625963f7f5e0093863ef --- /dev/null +++ b/README @@ -0,0 +1,41 @@ +# -*- mode: org; -*- +# +#+TITLE: *cfMesh README for version 1.0* +#+AUTHOR: Franjo Juretic. +#+DATE: May 2014 +#+LINK: http://www.c-fields.com +#+OPTIONS: + +cfMesh is a library for mesh generation built on OpenFOAM. + +* License + cfMesh is free software; you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation; either version 3 of the License, or (at your option) any later + version. + +* System requirements + cfMesh is developed and tested on Linux and MS Windows. + +* Installation + The binaries can be downloaded from www.c-fields.com + +* Building from Sources (Optional) + + cfMesh can be built with recent versions of OpenFOAM and foam-extend. In order to build the library, a working OpenFOAM environment is needed. The build started by the Allwmake script located in this folder. It can be built with gcc and mingw compilers which support OpenMP (gcc-4.2.4 and above). Other compilers are not tested. + +* Getting Started + + Copy the 'tutorials' examples directory in the cfMesh distribution to the + 'run' directory. If the OpenFOAM environment variables are set correctly, + then the following command will work correctly: + + + cp -r tutorials $FOAM_RUN + + Run the first example case of a simplified car body: + + + cd $FOAM_RUN/tutorials/asmoOctree + + cartesianMesh + +* Documentation + http://www.c-fields.com \ No newline at end of file diff --git a/executables/cartesian2DMesh/Make/files b/executables/cartesian2DMesh/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..e9b6d81ac2d43d85ca7c43ed1191e6e4b49fbff4 --- /dev/null +++ b/executables/cartesian2DMesh/Make/files @@ -0,0 +1,3 @@ +cartesian2DMesh.C + +EXE = $(FOAM_USER_APPBIN)/cartesian2DMesh diff --git a/executables/dualMesh/Make/options b/executables/cartesian2DMesh/Make/options old mode 100755 new mode 100644 similarity index 83% rename from executables/dualMesh/Make/options rename to executables/cartesian2DMesh/Make/options index 38f9038a1748029f92967737062ce296a835f097..f9c6fde2a98d53d7d38a056c4121431fbdcd089a --- a/executables/dualMesh/Make/options +++ b/executables/cartesian2DMesh/Make/options @@ -8,4 +8,5 @@ EXE_LIBS = \ -lmeshTools \ -ltriSurface \ -lfiniteVolume \ - -lMeshLibrary + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary diff --git a/executables/cartesian2DMesh/cartesian2DMesh.C b/executables/cartesian2DMesh/cartesian2DMesh.C new file mode 100644 index 0000000000000000000000000000000000000000..1a03a036769b465df621c75f6cdab46a68e535ef --- /dev/null +++ b/executables/cartesian2DMesh/cartesian2DMesh.C @@ -0,0 +1,61 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Application + Generates cartesian mesh + +Description + Generates a 2D cartesian mesh + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "Time.H" +#include "cartesian2DMeshGenerator.H" + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +// Main program: + +int main(int argc, char *argv[]) +{ +# include "setRootCase.H" +# include "createTime.H" + + //- 2d cartesian mesher cannot be run in parallel + argList::noParallel(); + + cartesian2DMeshGenerator cmg(runTime); + + Info<< "ExecutionTime = " << runTime.elapsedCpuTime() << " s\n" + << "ClockTime = " << runTime.elapsedClockTime() << " s" << endl; + + cmg.writeMesh(); + + Info << "End\n" << endl; + return 0; +} + +// ************************************************************************* // diff --git a/executables/cartesianMesh/Make/options b/executables/cartesianMesh/Make/options index 38f9038a1748029f92967737062ce296a835f097..f9c6fde2a98d53d7d38a056c4121431fbdcd089a 100755 --- a/executables/cartesianMesh/Make/options +++ b/executables/cartesianMesh/Make/options @@ -8,4 +8,5 @@ EXE_LIBS = \ -lmeshTools \ -ltriSurface \ -lfiniteVolume \ - -lMeshLibrary + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary diff --git a/executables/cartesianMesh/cartesianMesh.C b/executables/cartesianMesh/cartesianMesh.C index c01d5d6bbc3444f9243330f0c0921356db3ed0ce..76783b8a416bdaf0b3e56af722a1db0971c75a74 100644 --- a/executables/cartesianMesh/cartesianMesh.C +++ b/executables/cartesianMesh/cartesianMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Application Generates cartesian mesh @@ -46,12 +45,12 @@ int main(int argc, char *argv[]) # include "setRootCase.H" # include "createTime.H" - cartesianMeshGenerator omg(runTime); + cartesianMeshGenerator cmg(runTime); Info<< "ExecutionTime = " << runTime.elapsedCpuTime() << " s\n" << "ClockTime = " << runTime.elapsedClockTime() << " s" << endl; - - omg.writeMesh(); + + cmg.writeMesh(); Info << "End\n" << endl; return 0; diff --git a/executables/dualMesh/Make/files b/executables/dualMesh/Make/files deleted file mode 100755 index 4c6d20a4f930acf121ad98456dd689e31bb76fb9..0000000000000000000000000000000000000000 --- a/executables/dualMesh/Make/files +++ /dev/null @@ -1,3 +0,0 @@ -dualMesh.C - -EXE = $(FOAM_USER_APPBIN)/dualMesh diff --git a/executables/hexMesh/Make/files b/executables/hexMesh/Make/files index 958685969dd1291bf9385b14d050c2394220dd0e..e832553b096347e3ad2e7bfc535cc940350a1b2b 100755 --- a/executables/hexMesh/Make/files +++ b/executables/hexMesh/Make/files @@ -1,3 +1,3 @@ hexMesh.C -EXE = $(FOAM_USER_APPBIN)/hexMesh +EXE = $(FOAM_APPBIN)/hexMesh diff --git a/executables/hexMesh/Make/options b/executables/hexMesh/Make/options index 38f9038a1748029f92967737062ce296a835f097..e3af8d5f1b5603025dad5f5a4af7288a381ede6e 100755 --- a/executables/hexMesh/Make/options +++ b/executables/hexMesh/Make/options @@ -8,4 +8,4 @@ EXE_LIBS = \ -lmeshTools \ -ltriSurface \ -lfiniteVolume \ - -lMeshLibrary + -lmeshLibrary diff --git a/executables/hexMesh/hexMesh.C b/executables/hexMesh/hexMesh.C index d88ca70b49b2ef7014d5557806d235b8ebab366e..f970b53ef7e82b9476beb473b95044969e4dd83f 100644 --- a/executables/hexMesh/hexMesh.C +++ b/executables/hexMesh/hexMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Application Generates a pure hex mesh @@ -46,12 +45,15 @@ int main(int argc, char *argv[]) # include "setRootCase.H" # include "createTime.H" - hexMeshGenerator omg(runTime); + //- hex mesher cannot be run in parallel yet + argList::noParallel(); + + hexMeshGenerator hmg(runTime); Info<< "ExecutionTime = " << runTime.elapsedCpuTime() << " s\n" << "ClockTime = " << runTime.elapsedClockTime() << " s" << endl; - - omg.writeMesh(); + + hmg.writeMesh(); Info << "End\n" << endl; return 0; diff --git a/executables/pMesh/Make/files b/executables/pMesh/Make/files index 760e5de196eea69177ad1fd66177c181870c4fd5..ea506df68c45e4071407faa834898153cc1e714e 100755 --- a/executables/pMesh/Make/files +++ b/executables/pMesh/Make/files @@ -1,3 +1,3 @@ pMesh.C -EXE = $(FOAM_USER_APPBIN)/pMesh +EXE = $(FOAM_APPBIN)/pMesh diff --git a/executables/pMesh/Make/options b/executables/pMesh/Make/options index 38f9038a1748029f92967737062ce296a835f097..e3af8d5f1b5603025dad5f5a4af7288a381ede6e 100755 --- a/executables/pMesh/Make/options +++ b/executables/pMesh/Make/options @@ -8,4 +8,4 @@ EXE_LIBS = \ -lmeshTools \ -ltriSurface \ -lfiniteVolume \ - -lMeshLibrary + -lmeshLibrary diff --git a/executables/pMesh/pMesh.C b/executables/pMesh/pMesh.C index ea48e0d9f539582762480a63f95322a13650cc58..18c63b1594508ea5f2e7d7327bbc2332fc1f3430 100644 --- a/executables/pMesh/pMesh.C +++ b/executables/pMesh/pMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Application Generates polyhedral mesh @@ -45,12 +44,15 @@ int main(int argc, char *argv[]) # include "setRootCase.H" # include "createTime.H" - voronoiMeshGenerator omg(runTime); + //- polyhedral mesher cannot be run in parallel yet + argList::noParallel(); + + voronoiMeshGenerator pmg(runTime); Info<< "ExecutionTime = " << runTime.elapsedCpuTime() << " s\n" << "ClockTime = " << runTime.elapsedClockTime() << endl; - - omg.writeMesh(); + + pmg.writeMesh(); Info << "End\n" << endl; return 0; diff --git a/executables/tetMesh/Make/options b/executables/tetMesh/Make/options index 38f9038a1748029f92967737062ce296a835f097..f9c6fde2a98d53d7d38a056c4121431fbdcd089a 100755 --- a/executables/tetMesh/Make/options +++ b/executables/tetMesh/Make/options @@ -8,4 +8,5 @@ EXE_LIBS = \ -lmeshTools \ -ltriSurface \ -lfiniteVolume \ - -lMeshLibrary + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary diff --git a/executables/tetMesh/tetMesh.C b/executables/tetMesh/tetMesh.C index e84f6b3393196d27e3de23231caf4966823c7b79..307f590c10a39dcab4b72d7f336f297e6715ee80 100644 --- a/executables/tetMesh/tetMesh.C +++ b/executables/tetMesh/tetMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Application Generates tetrahedral mesh @@ -45,12 +44,15 @@ int main(int argc, char *argv[]) # include "setRootCase.H" # include "createTime.H" - tetMeshGenerator omg(runTime); + //- tetrahedral mesher cannot be run in parallel yet + argList::noParallel(); + + tetMeshGenerator tmg(runTime); Info<< "ExecutionTime = " << runTime.elapsedCpuTime() << " s\n" << "ClockTime = " << runTime.elapsedClockTime() << endl; - - omg.writeMesh(); + + tmg.writeMesh(); Info << "End\n" << endl; return 0; diff --git a/meshLibrary/Make/files b/meshLibrary/Make/files index 8738d437abdc7fdbd81f61681a784e2fb872f318..7769c487e4b844cd9653e3587316386c7e557a65 100644 --- a/meshLibrary/Make/files +++ b/meshLibrary/Make/files @@ -5,23 +5,38 @@ meshSurfacePartitioner = utilities/surfaceTools/meshSurfacePartitioner boundaryFacesGenerator = utilities/surfaceTools/boundaryFacesGenerator boundaryLayers = utilities/boundaryLayers checkMeshDict = utilities/checkMeshDict + meshSurfaceCheckInvertedVertices = utilities/surfaceTools/meshSurfaceCheckInvertedVertices meshSurfaceCheckEdgeTypes = utilities/surfaceTools/meshSurfaceCheckEdgeTypes +meshSurfaceDetectPlanarRegions = utilities/surfaceTools/meshSurfaceDetectPlanarRegions meshSurfaceCutter = utilities/surfaceTools/meshSurfaceCutter meshSurfaceMapper = utilities/surfaceTools/meshSurfaceMapper +meshSurfaceMapper2D = utilities/surfaceTools/meshSurfaceMapper2D +edgeExtraction = utilities/surfaceTools/edgeExtraction +edgeExtractor = $(edgeExtraction)/edgeExtractor meshSurfaceEdgeExtractor = utilities/surfaceTools/meshSurfaceEdgeExtractor meshSurfaceEdgeExtractorNonTopo = utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo meshSurfaceEdgeExtractorFUN = utilities/surfaceTools/meshSurfaceEdgeExtractorFUN +meshSurfaceEdgeExtractor2D = utilities/surfaceTools/meshSurfaceEdgeExtractor2D correctEdgesBetweenPatches = utilities/surfaceTools/correctEdgesBetweenPatches + createFundamentalSheetsBase = utilities/surfaceTools/createFundamentalSheets createFundamentalSheets = $(createFundamentalSheetsBase)/createFundamentalSheets createFundamentalSheetsJFS = $(createFundamentalSheetsBase)/createFundamentalSheetsJFS createFundamentalSheetsFJ = $(createFundamentalSheetsBase)/createFundamentalSheetsFJ + decomposeCellsNearConcaveEdges = utilities/surfaceTools/decomposeCellsNearConcaveEdges renameBoundaryPatches = utilities/surfaceTools/renameBoundaryPatches hexHelpers = utilities/hexahedra/hexHelpers +intersectionTools = utilities/intersectionTools +findCellsIntersectingSurface = $(intersectionTools)/findCellsIntersectingSurface + +nonManifoldMeshing = utilities/nonManifoldMeshing +findNonManifoldInterfaces = $(nonManifoldMeshing)/findNonManifoldInterfaces +removeCellsInSelectedDomains = $(nonManifoldMeshing)/removeCellsInSelectedDomains + meshOptimizer = utilities/smoothers/geometry/meshOptimizer tetMeshOptimisation = $(meshOptimizer)/tetMeshOptimisation simplexSmoother = $(tetMeshOptimisation)/advancedSmoothers/simplexSmoother @@ -63,19 +78,28 @@ checkCellConnectionsOverFaces = $(topology)/checkCellConnectionsOverFaces checkIrregularSurfaceConnections = $(topology)/checkIrregularSurfaceConnections checkNonMappableCellConnections = $(topology)/checkNonMappableCellConnections -triSurfaceCleanupDuplicates = utilities/triSurfaceTools/triSurfaceCleanupDuplicates -triSurfaceCurvatureEstimator = utilities/triSurfaceTools/triSurfaceCurvatureEstimator -triSurfacePartitioner = utilities/triSurfaceTools/triSurfacePartitioner -triSurfaceDetectMaterials = utilities/triSurfaceTools/triSurfaceDetectMaterials -triSurfaceDetectPlanarRegions = utilities/triSurfaceTools/triSurfaceDetectPlanarRegions -triSurfaceDetectFeatureEdges = utilities/triSurfaceTools/triSurfaceDetectFeatureEdges +triSurfaceTools = utilities/triSurfaceTools +triSurfaceCleanupDuplicates = $(triSurfaceTools)/triSurfaceCleanupDuplicates +triSurfaceCopyParts = $(triSurfaceTools)/triSurfaceCopyParts +triSurfaceCurvatureEstimator = $(triSurfaceTools)/triSurfaceCurvatureEstimator +triSurfacePartitioner = $(triSurfaceTools)/triSurfacePartitioner +triSurfaceDetectMaterials = $(triSurfaceTools)/triSurfaceDetectMaterials +triSurfaceDetectPlanarRegions = $(triSurfaceTools)/triSurfaceDetectPlanarRegions +triSurfaceDetectFeatureEdges = $(triSurfaceTools)/triSurfaceDetectFeatureEdges +triSurfaceClassifyEdges = $(triSurfaceTools)/triSurfaceClassifyEdges +triSurfacePatchManipulator = $(triSurfaceTools)/triSurfacePatchManipulator +triSurfaceRemoveFacets = $(triSurfaceTools)/triSurfaceRemoveFacets +triSurfaceExtrude2DEdges = $(triSurfaceTools)/triSurfaceExtrude2DEdges +triSurfaceMetaData = $(triSurfaceTools)/triSurfaceMetaData polyMeshGen = utilities/meshes/polyMeshGen -writePatch = utilities/meshes/polyMeshGen/writePatch +boundaryPatch = utilities/meshes/polyMeshGen/boundaryPatch +polyMeshGen2DEngine = utilities/meshes/polyMeshGen2DEngine polyMeshGenModifier = utilities/meshes/polyMeshGenModifier polyMeshGenAddressing = utilities/meshes/polyMeshGenAddressing polyMeshGenChecks = utilities/meshes/polyMeshGenChecks partTetMesh = utilities/meshes/partTetMesh +partTriMesh = utilities/meshes/partTriMesh primitiveMesh = utilities/meshes/primitiveMesh triSurf = utilities/meshes/triSurf cell = utilities/meshes/primitives/cell @@ -90,12 +114,7 @@ lists = $(containers)/Lists meshZipper = utilities/meshZipper -writeAsEnsight = utilities/dataConversion/foamToEnsight -writeOctreeAsEnsight = utilities/dataConversion/octreeToEnsight writeAsFPMA = utilities/dataConversion/foamToFPMA -writeAsFLMA = utilities/dataConversion/foamToFLMA -simplexAsFLMA = utilities/dataConversion/simplexToFLMA -writeOctreeAsFPMA = utilities/dataConversion/octreeToFPMA polyMeshExtractor = pMeshLibrary/polyMeshExtractor polyMeshGenerator = pMeshLibrary/polyMeshGenerator @@ -103,9 +122,7 @@ polyMeshGenerator = pMeshLibrary/polyMeshGenerator cartesianMeshExtractor = cartesianMesh/cartesianMeshExtractor cartesianMeshGenerator = cartesianMesh/cartesianMeshGenerator -dualMeshExtractor = dualMesh/dualMeshExtractor -dualMeshGenerator = dualMesh/dualMeshGenerator -dualUnfoldConcaveCells = dualMesh/dualUnfoldConcaveCells +cartesian2DMeshGenerator = cartesian2DMesh/cartesian2DMeshGenerator hexMeshExtractor = hexMesh/hexMeshExtractor hexMeshGenerator = hexMesh/hexMeshGenerator @@ -135,9 +152,11 @@ $(polyMeshGen)/polyMeshGenPoints.C $(polyMeshGen)/polyMeshGenFaces.C $(polyMeshGen)/polyMeshGenCells.C -$(writePatch)/writePatchBase.C -$(writePatch)/writePatch.C -$(writePatch)/writeProcessorPatch.C +$(polyMeshGen2DEngine)/polyMeshGen2DEngine.C + +$(boundaryPatch)/boundaryPatchBase.C +$(boundaryPatch)/boundaryPatch.C +$(boundaryPatch)/processorBoundaryPatch.C $(polyMeshGenModifier)/polyMeshGenModifierRemoveUnusedVertices.C $(polyMeshGenModifier)/polyMeshGenModifierRemoveFaces.C @@ -178,10 +197,26 @@ $(partTetMesh)/partTetMeshAddressing.C $(partTetMesh)/partTetMeshParallelAddressing.C $(partTetMesh)/partTetMeshSimplex.C +$(partTriMesh)/partTriMesh.C +$(partTriMesh)/partTriMeshAddressing.C +$(partTriMesh)/partTriMeshParallelAddressing.C +$(partTriMesh)/partTriMeshSimplex.C + $(triSurf)/triSurf.C +$(triSurf)/triSurfPoints.C +$(triSurf)/triSurfFacets.C +$(triSurf)/triSurfFeatureEdges.C +$(triSurf)/triSurfAddressing.C +$(triSurf)/triSurfModifier.C $(hexHelpers)/hexHelpers.C +$(findCellsIntersectingSurface)/findCellsIntersectingSurface.C + +$(findNonManifoldInterfaces)/findNonManifoldInterfaces.C + +$(removeCellsInSelectedDomains)/removeCellsInSelectedDomains.C + $(tetrahedra)/tessellationElement.C $(tetrahedra)/tetTessellation.C $(tetrahedra)/tetTessellationFunctions.C @@ -241,6 +276,10 @@ $(boundaryLayers)/boundaryLayerCells.C $(boundaryLayers)/boundaryLayersCheckTopologyOfBndFaces.C $(boundaryLayers)/boundaryLayersWrapperLayer.C $(boundaryLayers)/extrudeLayer.C +$(boundaryLayers)/refineBoundaryLayers.C +$(boundaryLayers)/refineBoundaryLayersFunctions.C +$(boundaryLayers)/refineBoundaryLayersFaces.C +$(boundaryLayers)/refineBoundaryLayersCells.C $(boundaryOutwardOrientation)/boundaryOutwardOrientation.C @@ -260,6 +299,8 @@ $(meshSurfaceCheckInvertedVertices)/meshSurfaceCheckInvertedVertices.C $(meshSurfaceCheckEdgeTypes)/meshSurfaceCheckEdgeTypes.C +$(meshSurfaceDetectPlanarRegions)/meshSurfaceDetectPlanarRegions.C + $(meshSurfaceCutter)/meshSurfaceCutter.C $(meshSurfaceCutter)/meshSurfaceCutterFaceCutter.C $(meshSurfaceCutter)/meshSurfaceCutterInternalFaces.C @@ -271,6 +312,13 @@ $(meshSurfaceMapper)/meshSurfaceMapperMapVertices.C $(meshSurfaceMapper)/meshSurfaceMapperCornersAndEdges.C $(meshSurfaceMapper)/meshSurfaceMapperPremapVertices.C +$(meshSurfaceMapper2D)/meshSurfaceMapper2D.C +$(meshSurfaceMapper2D)/meshSurfaceMapper2DMapVertices.C +$(meshSurfaceMapper2D)/meshSurfaceMapper2DPremapVertices.C + +$(edgeExtractor)/edgeExtractor.C +$(edgeExtractor)/edgeExtractorCorners.C + $(meshSurfaceEdgeExtractor)/meshSurfaceEdgeExtractor.C $(meshSurfaceEdgeExtractor)/meshSurfaceEdgeCreateEdgeVertices.C $(meshSurfaceEdgeExtractor)/meshSurfaceEdgeCreateBoundaryFaces.C @@ -278,6 +326,9 @@ $(meshSurfaceEdgeExtractor)/meshSurfaceEdgeCreateBoundaryFaces.C $(meshSurfaceEdgeExtractorNonTopo)/meshSurfaceEdgeExtractorNonTopo.C $(meshSurfaceEdgeExtractorNonTopo)/meshSurfaceEdgeExtractorNonTopoDistributeFaces.C +$(meshSurfaceEdgeExtractor2D)/meshSurfaceEdgeExtractor2D.C +$(meshSurfaceEdgeExtractor2D)/meshSurfaceEdgeExtractor2DDistributeFaces.C + $(meshSurfaceEdgeExtractorFUN)/meshSurfaceEdgeExtractorFUN.C $(meshSurfaceEdgeExtractorFUN)/meshSurfaceEdgeExtractorFUNDistributeFaces.C @@ -384,6 +435,8 @@ $(surfaceIntersectionsOctree)/surfaceIntersectionsOctreeIntersections.C $(triSurfaceCleanupDuplicates)/triSurfaceCleanupDuplicates.C $(triSurfaceCleanupDuplicates)/triSurfaceCleanupDuplicatesFunctions.C +$(triSurfaceCopyParts)/triSurfaceCopyParts.C + $(triSurfacePartitioner)/triSurfacePartitioner.C $(triSurfacePartitioner)/triSurfacePartitionerCreateAddressing.C @@ -398,6 +451,19 @@ $(triSurfaceDetectPlanarRegions)/triSurfaceDetectPlanarRegions.C $(triSurfaceDetectFeatureEdges)/triSurfaceDetectFeatureEdges.C $(triSurfaceDetectFeatureEdges)/triSurfaceDetectFeatureEdgesFunctions.C +$(triSurfaceClassifyEdges)/triSurfaceClassifyEdges.C +$(triSurfaceClassifyEdges)/triSurfaceClassifyEdgesFunctions.C + +$(triSurfacePatchManipulator)/triSurfacePatchManipulator.C +$(triSurfacePatchManipulator)/triSurfacePatchManipulatorFunctions.C + +$(triSurfaceRemoveFacets)/triSurfaceRemoveFacets.C +$(triSurfaceRemoveFacets)/triSurfaceRemoveFacetsFunctions.C + +$(triSurfaceExtrude2DEdges)/triSurfaceExtrude2DEdges.C + +$(triSurfaceMetaData)/triSurfaceMetaData.C + $(cartesianMeshExtractor)/cartesianMeshExtractor.C $(cartesianMeshExtractor)/cartesianMeshExtractorPointsAndAddressing.C $(cartesianMeshExtractor)/cartesianMeshExtractorPolyMesh.C @@ -405,15 +471,7 @@ $(cartesianMeshExtractor)/cartesianMeshExtractorDecomposeSplitHexes.C $(cartesianMeshGenerator)/cartesianMeshGenerator.C -$(dualMeshExtractor)/dualMeshExtractor.C -$(dualMeshExtractor)/dualMeshExtractorDecompose.C -$(dualMeshExtractor)/dualMeshExtractorPolyMesh.C - -$(dualUnfoldConcaveCells)/dualUnfoldConcaveCells.C -$(dualUnfoldConcaveCells)/dualUnfoldConcaveCellsMergeFaces.C -$(dualUnfoldConcaveCells)/dualUnfoldConcaveCellsMergeFacesConsistency.C - -$(dualMeshGenerator)/dualMeshGenerator.C +$(cartesian2DMeshGenerator)/cartesian2DMeshGenerator.C $(hexMeshExtractor)/hexMeshExtractor.C $(hexMeshExtractor)/hexMeshExtractorHexMesh.C @@ -433,22 +491,7 @@ $(voronoiMeshExtractor)/voronoiMeshExtractorCreateMesh.C $(voronoiMeshGenerator)/voronoiMeshGenerator.C -$(writeAsEnsight)/ensightMesh.C -$(writeAsEnsight)/writeMeshEnsight.C - -$(writeOctreeAsEnsight)/octreeMesh.C -$(writeOctreeAsEnsight)/writeOctreeEnsight.C - $(writeAsFPMA)/writeMeshFPMA.C $(writeAsFPMA)/fpmaMesh.C -$(writeAsFLMA)/writeMeshFLMA.C -$(writeAsFLMA)/flmaMesh.C - -$(writeOctreeAsFPMA)/writeOctreeFPMA.C -$(writeOctreeAsFPMA)/octreeMeshFPMA.C - -$(simplexAsFLMA)/simplexMesh.C -$(simplexAsFLMA)/writeSimplexFLMA.C - -LIB = $(FOAM_LIBBIN)/libMeshLibrary +LIB = $(FOAM_USER_LIBBIN)/libmeshLibrary diff --git a/meshLibrary/Make/options b/meshLibrary/Make/options index f2ccffee930329f83f65647cf68a706c2eb4837e..3e1cae4a363f39a6f04db2cc3b3689f1bff37a49 100644 --- a/meshLibrary/Make/options +++ b/meshLibrary/Make/options @@ -1,5 +1,10 @@ -EXE_INC = \ - -I$(LIB_SRC)/triSurface/lnInclude \ - -I$(LIB_SRC)/meshTools/lnInclude +#if defined(__GNUC__) + OMP_FLAGS = -DUSE_OMP -fopenmp +#else + OMP_FLAGS = +#endif -/* EXE_LIBS = -lcfdTools */ +EXE_INC = \ + $(OMP_FLAGS) \ + -I$(LIB_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude diff --git a/meshLibrary/cartesian2DMesh/cartesian2DMeshGenerator/cartesian2DMeshGenerator.C b/meshLibrary/cartesian2DMesh/cartesian2DMeshGenerator/cartesian2DMeshGenerator.C new file mode 100644 index 0000000000000000000000000000000000000000..b4179487a52fe913479fe7d9342134e553982962 --- /dev/null +++ b/meshLibrary/cartesian2DMesh/cartesian2DMeshGenerator/cartesian2DMeshGenerator.C @@ -0,0 +1,318 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "cartesian2DMeshGenerator.H" +#include "polyMeshGen2DEngine.H" +#include "triSurf.H" +#include "triSurfacePatchManipulator.H" +#include "demandDrivenData.H" +#include "Time.H" +#include "meshOctreeCreator.H" +#include "cartesianMeshExtractor.H" +#include "meshSurfaceEngine.H" +#include "meshSurfaceMapper2D.H" +#include "meshSurfaceEdgeExtractor2D.H" +#include "meshSurfaceOptimizer.H" +#include "topologicalCleaner.H" +#include "boundaryLayers.H" +#include "refineBoundaryLayers.H" +#include "renameBoundaryPatches.H" +#include "checkMeshDict.H" +#include "checkCellConnectionsOverFaces.H" +#include "checkIrregularSurfaceConnections.H" +#include "checkNonMappableCellConnections.H" +#include "checkBoundaryFacesSharingTwoEdges.H" +#include "triSurfaceMetaData.H" + +//#define DEBUG + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * Private member functions * * * * * * * * * * * * // + +void cartesian2DMeshGenerator::createCartesianMesh() +{ + //- create polyMesh from octree boxes + cartesianMeshExtractor cme(*octreePtr_, meshDict_, mesh_); + + if( meshDict_.found("decomposePolyhedraIntoTetsAndPyrs") ) + { + if( readBool(meshDict_.lookup("decomposePolyhedraIntoTetsAndPyrs")) ) + cme.decomposeSplitHexes(); + } + + cme.createMesh(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif +} + +void cartesian2DMeshGenerator::surfacePreparation() +{ + //- removes unnecessary cells and morph the boundary + //- such that there is only one boundary face per cell + //- It also checks topology of cells after morphing is performed + bool changed; + + do + { + changed = false; + + checkIrregularSurfaceConnections checkConnections(mesh_); + if( checkConnections.checkAndFixIrregularConnections() ) + changed = true; + + if( checkNonMappableCellConnections(mesh_).removeCells() ) + changed = true; + + if( checkCellConnectionsOverFaces(mesh_).checkCellGroups() ) + changed = true; + } while( changed ); + + checkBoundaryFacesSharingTwoEdges(mesh_).improveTopology(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif +} + +void cartesian2DMeshGenerator::mapMeshToSurface() +{ + //- calculate mesh surface + meshSurfaceEngine* msePtr = new meshSurfaceEngine(mesh_); + + //- pre-map mesh surface + meshSurfaceMapper2D mapper(*msePtr, *octreePtr_); + + mapper.adjustZCoordinates(); + + mapper.preMapVertices(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif + + //- map mesh surface on the geometry surface + mapper.mapVerticesOntoSurface(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif + + deleteDemandDrivenData(msePtr); +} + +void cartesian2DMeshGenerator::mapEdgesAndCorners() +{ + meshSurfaceEdgeExtractor2D(mesh_, *octreePtr_); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif +} + +void cartesian2DMeshGenerator::optimiseMeshSurface() +{ + meshSurfaceEngine mse(mesh_); + meshSurfaceOptimizer optimizer(mse, *octreePtr_); + optimizer.optimizeSurface2D(); + optimizer.untangleSurface2D(); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif +} + +void cartesian2DMeshGenerator::generateBoundaryLayers() +{ + boundaryLayers bl(mesh_); + + bl.activate2DMode(); + + bl.addLayerForAllPatches(); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif +} + +void cartesian2DMeshGenerator::refBoundaryLayers() +{ + if( meshDict_.isDict("boundaryLayers") ) + { + refineBoundaryLayers refLayers(mesh_); + + refineBoundaryLayers::readSettings(meshDict_, refLayers); + + refLayers.activate2DMode(); + + refLayers.refineLayers(); + + meshSurfaceEngine mse(mesh_); + meshSurfaceOptimizer optimizer(mse, *octreePtr_); + + optimizer.untangleSurface2D(); + } +} + +void cartesian2DMeshGenerator::replaceBoundaries() +{ + renameBoundaryPatches rbp(mesh_, meshDict_); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif +} + +void cartesian2DMeshGenerator::renumberMesh() +{ + polyMeshGenModifier(mesh_).renumberMesh(); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif +} + +void cartesian2DMeshGenerator::generateMesh() +{ + createCartesianMesh(); + + surfacePreparation(); + + mapMeshToSurface(); + + mapEdgesAndCorners(); + + optimiseMeshSurface(); + + generateBoundaryLayers(); + + optimiseMeshSurface(); + + refBoundaryLayers(); + + renumberMesh(); + + replaceBoundaries(); +} + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +// Construct from objectRegistry +cartesian2DMeshGenerator::cartesian2DMeshGenerator(const Time& time) +: + db_(time), + surfacePtr_(NULL), + meshDict_ + ( + IOobject + ( + "meshDict", + db_.system(), + db_, + IOobject::MUST_READ, + IOobject::NO_WRITE + ) + ), + octreePtr_(NULL), + mesh_(time) +{ + if( true ) + { + checkMeshDict cmd(meshDict_); + } + + fileName surfaceFile = meshDict_.lookup("surfaceFile"); + if( Pstream::parRun() ) + surfaceFile = ".."/surfaceFile; + + surfacePtr_ = new triSurf(db_.path()/surfaceFile); + + if( true ) + { + //- save meta data with the mesh (surface mesh + its topology info) + triSurfaceMetaData sMetaData(*surfacePtr_); + const dictionary& surfMetaDict = sMetaData.metaData(); + + mesh_.metaData().add("surfaceFile", surfaceFile); + mesh_.metaData().add("surfaceMeta", surfMetaDict); + } + + if( surfacePtr_->featureEdges().size() != 0 ) + { + //- create surface patches based on the feature edges + //- and update the meshDict based on the given data + triSurfacePatchManipulator manipulator(*surfacePtr_); + + const triSurf* surfaceWithPatches = + manipulator.surfaceWithPatches(&meshDict_); + + //- delete the old surface and assign the new one + deleteDemandDrivenData(surfacePtr_); + surfacePtr_ = surfaceWithPatches; + } + + octreePtr_ = new meshOctree(*surfacePtr_, true); + + meshOctreeCreator(*octreePtr_, meshDict_).createOctreeBoxes(); + + generateMesh(); +} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +cartesian2DMeshGenerator::~cartesian2DMeshGenerator() +{ + deleteDemandDrivenData(surfacePtr_); + deleteDemandDrivenData(octreePtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void cartesian2DMeshGenerator::writeMesh() const +{ + mesh_.write(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualMeshGenerator/dualMeshGenerator.H b/meshLibrary/cartesian2DMesh/cartesian2DMeshGenerator/cartesian2DMeshGenerator.H similarity index 54% rename from meshLibrary/dualMesh/dualMeshGenerator/dualMeshGenerator.H rename to meshLibrary/cartesian2DMesh/cartesian2DMeshGenerator/cartesian2DMeshGenerator.H index 81ea1abb2c03594715f8dd9e0ea8f6d8560e4ee9..d966386f0808903e0321429d9c094e2e8f61f650 100644 --- a/meshLibrary/dualMesh/dualMeshGenerator/dualMeshGenerator.H +++ b/meshLibrary/cartesian2DMesh/cartesian2DMeshGenerator/cartesian2DMeshGenerator.H @@ -1,44 +1,42 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class - dualMeshGenerator + cartesian2DMeshGenerator Description - Octree for mesh generation + Creates a 2D cartesian mesh from the quadtree SourceFiles - dualMeshGenerator.C + cartesian2DMeshGenerator.C \*---------------------------------------------------------------------------*/ -#ifndef dualMeshGenerator_H -#define dualMeshGenerator_H +#ifndef cartesian2DMeshGenerator_H +#define cartesian2DMeshGenerator_H #include "polyMeshGen.H" #include "IOdictionary.H" -//#include "volFields.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -51,77 +49,74 @@ class meshOctree; class Time; /*---------------------------------------------------------------------------*\ - Class dualMeshGenerator Declaration + Class cartesian2DMeshGenerator Declaration \*---------------------------------------------------------------------------*/ -class dualMeshGenerator +class cartesian2DMeshGenerator { // Private data //- reference to Time - const Time& runTime_; + const Time& db_; //- pointer to the surface - triSurf* surfacePtr_; + const triSurf* surfacePtr_; //- IOdictionary containing information about cell sizes, etc.. IOdictionary meshDict_; //- pointer to the octree meshOctree* octreePtr_; - - //- mesh - polyMeshGen mesh_; + + //- mesh + polyMeshGen mesh_; // Private member functions - //- generate dual mesh - void generateDualMesh(); - - //- prepare mesh surface - void surfacePreparation(); - - //- map mesh to the surface and untangle surface - void mapMeshToSurface(); - - //- optimise surface of the mesh - void optimiseMeshSurface(); - - //- change mesh topology near concave edges - void checkConcaveEdges(); - - //- add boundary layers - void generateBoudaryLayers(); - - //- mesh optimisation - void optimiseFinalMesh(); - + //- create cartesian mesh + void createCartesianMesh(); + + //- prepare mesh surface + void surfacePreparation(); + + //- map mesh to the surface and untangle surface + void mapMeshToSurface(); + + //- capture edges and corners + void mapEdgesAndCorners(); + + //- optimise surface mesh + void optimiseMeshSurface(); + + //- add boundary layers + void generateBoundaryLayers(); + + //- refine boundary layers + void refBoundaryLayers(); + //- replace boundaries void replaceBoundaries(); - - //- renumber the mesh - void renumberMesh(); - + + //- renumber the mesh + void renumberMesh(); + //- generate mesh void generateMesh(); //- Disallow default bitwise copy construct - dualMeshGenerator(const dualMeshGenerator&); + cartesian2DMeshGenerator(const cartesian2DMeshGenerator&); //- Disallow default bitwise assignment - void operator=(const dualMeshGenerator&); + void operator=(const cartesian2DMeshGenerator&); public: // Constructors //- Construct from time - dualMeshGenerator(const Time&); - - //- Construct from time and desired cell size - //dualMeshGenerator(const Time&, const volScalarField&); + cartesian2DMeshGenerator(const Time&); // Destructor - ~dualMeshGenerator(); + ~cartesian2DMeshGenerator(); // Member Functions diff --git a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.C b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.C index 5c7e3461803f41749f111f3bc7ab887ab4e132b2..d81f2dd50dfc6286327bc8293414fc01f9ad0911 100644 --- a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.C +++ b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,7 +39,7 @@ namespace Foam void cartesianMeshExtractor::clearOut() { - deleteDemandDrivenData(leafCellLabelPtr_); + deleteDemandDrivenData(leafCellLabelPtr_); } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -49,14 +48,14 @@ void cartesianMeshExtractor::clearOut() cartesianMeshExtractor::cartesianMeshExtractor ( meshOctree& octree, - const IOdictionary& meshDict, - polyMeshGen& mesh + const IOdictionary& meshDict, + polyMeshGen& mesh ) : octreeCheck_(octree, meshDict, false), - mesh_(mesh), - decomposeSplitHexes_(false), - leafCellLabelPtr_(new labelList(octree.numberOfLeaves(), -1)) + mesh_(mesh), + decomposeSplitHexes_(false), + leafCellLabelPtr_(new labelList(octree.numberOfLeaves(), -1)) { } @@ -64,36 +63,36 @@ cartesianMeshExtractor::cartesianMeshExtractor cartesianMeshExtractor::~cartesianMeshExtractor() { - clearOut(); + clearOut(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void cartesianMeshExtractor::decomposeSplitHexes() { - decomposeSplitHexes_ = true; + decomposeSplitHexes_ = true; } void cartesianMeshExtractor::createMesh() { - Info << "Extracting polyMesh" << endl; - - //- create points and pointLeaves addressing + Info << "Extracting polyMesh" << endl; + + //- create points and pointLeaves addressing createPointsAndAddressing(); - //- create the mesh + //- create the mesh createPolyMesh(); //- decompose split-hex cells into tetrahedra and pyramids decomposeSplitHexesIntoTetsAndPyramids(); - - //- remove unused vertices - polyMeshGenModifier(mesh_).removeUnusedVertices(); - - Info << "Mesh has :" << nl - << mesh_.points().size() << " vertices " << nl - << mesh_.faces().size() << " faces" << nl - << mesh_.cells().size() << " cells" << endl; + + //- remove unused vertices + polyMeshGenModifier(mesh_).removeUnusedVertices(); + + Info << "Mesh has :" << nl + << mesh_.points().size() << " vertices " << nl + << mesh_.faces().size() << " faces" << nl + << mesh_.cells().size() << " cells" << endl; if( Pstream::parRun() ) { @@ -113,7 +112,7 @@ void cartesianMeshExtractor::createMesh() << " This can be reolved by reducing the maxCellSize by a fraction." << "i.e. 2.49999 instead of 2.5." << exit(FatalError); } - + Info << "Finished extracting polyMesh" << endl; } diff --git a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.H b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.H index d44bdd6a704ec319c76c71ae8a7135419ca5a265..fdbd60a24352295cbf84225c6f688787d5feb1cd 100644 --- a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.H +++ b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractor.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class cartesianMeshExtractor @@ -43,7 +42,7 @@ SourceFiles namespace Foam { - + class IOdictionary; /*---------------------------------------------------------------------------*\ @@ -55,28 +54,28 @@ class cartesianMeshExtractor // Private data //- reference to the octree addressing meshOctreeAddressing octreeCheck_; - - //- reference to the mesh - polyMeshGen& mesh_; - - //- decompose split hex cells - bool decomposeSplitHexes_; - - //- cell label for a given leaf - labelList* leafCellLabelPtr_; + + //- reference to the mesh + polyMeshGen& mesh_; + + //- decompose split hex cells + bool decomposeSplitHexes_; + + //- cell label for a given leaf + labelList* leafCellLabelPtr_; // Private member functions - //- delete all freestore data - void clearOut(); + //- delete all freestore data + void clearOut(); //- create vertices and pointLeaves addressing void createPointsAndAddressing(); //- create mesh data void createPolyMesh(); - - //- decompose split hexes into pyramids and tets - void decomposeSplitHexesIntoTetsAndPyramids(); + + //- decompose split hexes into pyramids and tets + void decomposeSplitHexesIntoTetsAndPyramids(); // Private copy constructor //- Disallow default bitwise copy construct @@ -93,8 +92,8 @@ public: cartesianMeshExtractor ( meshOctree& octree, - const IOdictionary& meshDict, - polyMeshGen& mesh + const IOdictionary& meshDict, + polyMeshGen& mesh ); // Destructor @@ -104,11 +103,11 @@ public: // Member Functions - //- decompose split hexes into standard cells - void decomposeSplitHexes(); - - //- create the mesh with the above options - void createMesh(); + //- decompose split hexes into standard cells + void decomposeSplitHexes(); + + //- create the mesh with the above options + void createMesh(); }; diff --git a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorDecomposeSplitHexes.C b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorDecomposeSplitHexes.C index 097ad7da9a24a42633bdf7c2aaf232da407eaaa7..d33800736687a8db90479384a54830480e4139b5 100644 --- a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorDecomposeSplitHexes.C +++ b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorDecomposeSplitHexes.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,11 +42,11 @@ namespace Foam void cartesianMeshExtractor::decomposeSplitHexesIntoTetsAndPyramids() { - if( !decomposeSplitHexes_ ) return; + if( !decomposeSplitHexes_ ) return; - Info << "Decomposing split-hex cells" << endl; - - const faceListPMG& faces = mesh_.faces(); + Info << "Decomposing split-hex cells" << endl; + + const faceListPMG& faces = mesh_.faces(); //- decompose faces which have more than 4 vertices boolList decompose(faces.size(), false); @@ -100,8 +99,8 @@ void cartesianMeshExtractor::decomposeSplitHexesIntoTetsAndPyramids() decomposeCells dc(mesh_); dc.decomposeMesh(decompose); } - - Info << "Finished decomposing split-hex cells" << endl; + + Info << "Finished decomposing split-hex cells" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPointsAndAddressing.C b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPointsAndAddressing.C index c76d282ac1155b6586c3ae18989e2d3b8a8098be..4508327038b116382bff15ac48f898b6c7b0ab9e 100644 --- a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPointsAndAddressing.C +++ b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPointsAndAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,16 +40,18 @@ void cartesianMeshExtractor::createPointsAndAddressing() { Info << "Creating octree vertices" << endl; + Info << "Octree nodes " << octreeCheck_.numberOfNodes() << endl; + //- set the size of the point field - pointFieldPMG& points = mesh_.points(); - points.setSize(octreeCheck_.numberOfNodes()); - - //- store vertices into the pointField + pointFieldPMG& points = mesh_.points(); + points.setSize(octreeCheck_.numberOfNodes()); + + //- store vertices into the pointField const pointField& octreePoints = octreeCheck_.octreePoints(); - + forAll(points, pointI) points[pointI] = octreePoints[pointI]; - + Info << "Finished creating octree vertices" << endl; } diff --git a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPolyMesh.C b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPolyMesh.C index 79c2192bedf98479a0c677cd539cdd016ab7195a..9118a7e757d7f857bc3b4ecb07be6df8e8d6befa 100644 --- a/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPolyMesh.C +++ b/meshLibrary/cartesianMesh/cartesianMeshExtractor/cartesianMeshExtractorPolyMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -52,13 +51,13 @@ namespace Foam void cartesianMeshExtractor::createPolyMesh() { Info << "Creating polyMesh from octree" << endl; - - const meshOctree& octree = octreeCheck_.octree(); - + + const meshOctree& octree = octreeCheck_.octree(); + //- give labels to cubes which will be used as mesh cells - const List<direction>& cType = octreeCheck_.boxType(); - - labelList& leafCellLabel = *leafCellLabelPtr_; + const List<direction>& cType = octreeCheck_.boxType(); + + labelList& leafCellLabel = *leafCellLabelPtr_; label nCells(0); forAll(cType, leafI) { @@ -67,43 +66,43 @@ void cartesianMeshExtractor::createPolyMesh() (octree.returnLeaf(leafI).procNo() != Pstream::myProcNo()) ) continue; - + if( cType[leafI] & meshOctreeAddressing::MESHCELL ) { leafCellLabel[leafI] = nCells++; } } - //- access to mesh data - polyMeshGenModifier meshModifier(mesh_); - faceListPMG& faces = meshModifier.facesAccess(); - cellListPMG& cells = meshModifier.cellsAccess(); - - //- start creating octree mesh + //- access to mesh data + polyMeshGenModifier meshModifier(mesh_); + faceListPMG& faces = meshModifier.facesAccess(); + cellListPMG& cells = meshModifier.cellsAccess(); + + //- start creating octree mesh cells.setSize(nCells); List<direction> nFacesInCell(nCells, direction(0)); label nFaces(0); - + const VRWGraph& octreeFaces = octreeCheck_.octreeFaces(); - const labelListPMG& owner = octreeCheck_.octreeFaceOwner(); - const labelListPMG& neighbour = octreeCheck_.octreeFaceNeighbour(); - + const labelLongList& owner = octreeCheck_.octreeFaceOwner(); + const labelLongList& neighbour = octreeCheck_.octreeFaceNeighbour(); + //- map storing box label and a direction for each processor face //- The map stores data in the same order on both sides of processor //- boundaries. This is a consequence of Morton ordering of //- leaf boxes in the octree. - std::map<label, labelListPMG> procFaces; - + std::map<label, labelLongList> procFaces; + forAll(octreeFaces, faceI) { const label own = owner[faceI]; const label nei = neighbour[faceI]; - + const label ownLabel = leafCellLabel[own]; label neiLabel(-1); if( nei != -1 ) neiLabel = leafCellLabel[nei]; - + if( (ownLabel != -1) && (neiLabel != -1) ) { ++nFaces; @@ -114,11 +113,11 @@ void cartesianMeshExtractor::createPolyMesh() { ++nFaces; ++nFacesInCell[ownLabel]; - + if( (nei != -1) && (cType[nei] & meshOctreeAddressing::MESHCELL) ) { const label procNo = octree.returnLeaf(nei).procNo(); - + procFaces[procNo].append(faceI); } } @@ -126,47 +125,47 @@ void cartesianMeshExtractor::createPolyMesh() { ++nFaces; ++nFacesInCell[neiLabel]; - + if( (own != -1) && (cType[own] & meshOctreeAddressing::MESHCELL) ) { const label procNo = octree.returnLeaf(own).procNo(); - + procFaces[procNo].append(faceI); } } } - + //- case is a serial run faces.setSize(nFaces); forAll(cells, cI) cells[cI].setSize(nFacesInCell[cI]); nFacesInCell = 0; - + //- calculate faces in processor patches if( Pstream::parRun() ) { - PtrList<writeProcessorPatch>& procBoundaries = + PtrList<processorBoundaryPatch>& procBoundaries = meshModifier.procBoundariesAccess(); - + //- set the number of procBoundaries procBoundaries.setSize(procFaces.size()); std::ostringstream ss; ss << Pstream::myProcNo(); const word name("processor"+ss.str()+"to"); label nProcBoundaries(nFaces), patchI(0); - + //- allocate memory for processor patches - std::map<label, labelListPMG>::const_iterator iter; + std::map<label, labelLongList>::const_iterator iter; for(iter=procFaces.begin();iter!=procFaces.end();++iter) { const label procI = iter->first; - + std::ostringstream ssNei; ssNei << procI; procBoundaries.set ( patchI, - new writeProcessorPatch + new processorBoundaryPatch ( name+ssNei.str(), "processor", @@ -176,7 +175,7 @@ void cartesianMeshExtractor::createPolyMesh() procI ) ); - + nProcBoundaries -= iter->second.size(); ++patchI; } @@ -187,15 +186,15 @@ void cartesianMeshExtractor::createPolyMesh() for(iter=procFaces.begin();iter!=procFaces.end();++iter) { procBoundaries[patchI].patchStart() = nProcBoundaries; - - const labelListPMG& patchFaces = iter->second; - + + const labelLongList& patchFaces = iter->second; + forAll(patchFaces, pfI) { const label fLabel = patchFaces[pfI]; const label own = owner[fLabel]; const label nei = neighbour[fLabel]; - + const label curCell = leafCellLabel[own]; label neiCell(-1); if( nei != -1 ) @@ -229,7 +228,7 @@ void cartesianMeshExtractor::createPolyMesh() << abort(FatalError); } } - + if( procBoundaries[patchI].patchSize() != (nProcBoundaries - procBoundaries[patchI].patchStart()) ) @@ -238,30 +237,30 @@ void cartesianMeshExtractor::createPolyMesh() "cartesianMeshExtractor::createPolyMesh()" ) << "Invalid patch size!" << Pstream::myProcNo() << abort(FatalError); - + ++patchI; } } - + nFaces = 0; - + forAll(octreeFaces, faceI) { const label own = owner[faceI]; const label nei = neighbour[faceI]; - + const label ownLabel = leafCellLabel[own]; label neiLabel(-1); if( nei != -1 ) neiLabel = leafCellLabel[nei]; - + if( (ownLabel != -1) && (neiLabel != -1) ) { //- internal face faces[nFaces].setSize(octreeFaces.sizeOfRow(faceI)); forAllRow(octreeFaces, faceI, pI) faces[nFaces][pI] = octreeFaces(faceI, pI); - + cells[ownLabel][nFacesInCell[ownLabel]++] = nFaces; cells[neiLabel][nFacesInCell[neiLabel]++] = nFaces; ++nFaces; @@ -273,12 +272,12 @@ void cartesianMeshExtractor::createPolyMesh() //- face at a parallel boundary continue; } - + //- boundary face faces[nFaces].setSize(octreeFaces.sizeOfRow(faceI)); forAllRow(octreeFaces, faceI, pI) faces[nFaces][pI] = octreeFaces(faceI, pI); - + cells[ownLabel][nFacesInCell[ownLabel]++] = nFaces; ++nFaces; } @@ -289,24 +288,24 @@ void cartesianMeshExtractor::createPolyMesh() //- face at a parallel boundary continue; } - + //- boundary face faces[nFaces].setSize(octreeFaces.sizeOfRow(faceI)); faces[nFaces][0] = octreeFaces(faceI, 0); for(label pI=octreeFaces.sizeOfRow(faceI)-1;pI>0;--pI) faces[nFaces][octreeFaces.sizeOfRow(faceI)-pI] = octreeFaces(faceI, pI); - + cells[neiLabel][nFacesInCell[neiLabel]++] = nFaces; ++nFaces; } } - + # ifdef DEBUGMesh label nProcBoundaries(0); forAll(procBoundaries, patchI) nProcBoundaries += procBoundaries[patchI].patchSize(); - + if( faces.size() != (nProcBoundaries + nFaces) ) { Serr << "Number of faces " << faces.size() << endl; @@ -318,10 +317,10 @@ void cartesianMeshExtractor::createPolyMesh() ) << Pstream::myProcNo() << "This mesh is invalid!" << abort(FatalError); } - + vectorField closedness(cells.size(), vector::zero); const labelList& owner = mesh_.owner(); - const labelList& neighbour = mesh_.neighbour(); + const labelList& neighbour = mesh_.neighbour(); forAll(owner, faceI) if( owner[faceI] == -1 ) { @@ -353,8 +352,76 @@ void cartesianMeshExtractor::createPolyMesh() # endif - meshModifier.reorderBoundaryFaces(); - + meshModifier.reorderBoundaryFaces(); + + if( octree.isQuadtree() ) + { + //- generate empty patches + //- search for faces with a dominant z coordinate and store them + //- into an empty patch + meshSurfaceEngine mse(mesh_); + const vectorField& fNormals = mse.faceNormals(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& fOwner = mse.faceOwners(); + const vectorField& fCentres = mse.faceCentres(); + + const boundBox& bb = octree.rootBox(); + const scalar tZ = 0.05 * (bb.max().z() - bb.min().z()); + + wordList patchNames(3); + patchNames[0] = "defaultFaces"; + patchNames[1] = "unusedFacesBottom"; + patchNames[2] = "unusedFacesTop"; + + VRWGraph boundaryFaces; + labelLongList newFaceOwner; + labelLongList newFacePatch; + + forAll(fNormals, bfI) + { + //- store the face and its owner + boundaryFaces.appendList(bFaces[bfI]); + newFaceOwner.append(fOwner[bfI]); + + const vector& fNormal = fNormals[bfI]; + + if( Foam::mag(fNormal.z()) > Foam::mag(fNormal.x() + fNormal.y()) ) + { + if( Foam::mag(fCentres[bfI].z() - bb.min().z()) < tZ ) + { + newFacePatch.append(1); + } + else if( Foam::mag(fCentres[bfI].z() - bb.max().z()) < tZ ) + { + newFacePatch.append(2); + } + else + { + FatalErrorIn + ( + "void cartesianMeshExtractor::createPolyMesh()" + ) << "Cannot distribute the face!!" << exit(FatalError); + } + } + else + { + newFacePatch.append(0); + } + } + + //- replace the boundary with faces in correct patches + meshModifier.replaceBoundary + ( + patchNames, + boundaryFaces, + newFaceOwner, + newFacePatch + ); + + meshModifier.boundariesAccess()[1].patchType() = "empty"; + meshModifier.boundariesAccess()[2].patchType() = "empty"; + } + Info << "Finished creating polyMesh" << endl; } diff --git a/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.C b/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.C index 151e4aecca1eabab9895c692dfa2b7be368b50e2..1c07e1b87d7bc01100991bf5963ec5db7147d0ca 100644 --- a/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.C +++ b/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -28,33 +27,29 @@ Description #include "cartesianMeshGenerator.H" #include "triSurf.H" +#include "triSurfacePatchManipulator.H" #include "demandDrivenData.H" -#include "objectRegistry.H" #include "Time.H" #include "meshOctreeCreator.H" #include "cartesianMeshExtractor.H" #include "meshSurfaceEngine.H" #include "meshSurfaceMapper.H" #include "meshSurfaceEdgeExtractorNonTopo.H" -#include "surfaceMorpherCells.H" #include "meshOptimizer.H" #include "meshSurfaceOptimizer.H" #include "topologicalCleaner.H" #include "boundaryLayers.H" +#include "refineBoundaryLayers.H" #include "renameBoundaryPatches.H" #include "checkMeshDict.H" #include "checkCellConnectionsOverFaces.H" #include "checkIrregularSurfaceConnections.H" #include "checkNonMappableCellConnections.H" #include "checkBoundaryFacesSharingTwoEdges.H" +#include "triSurfaceMetaData.H" +#include "removeCellsInSelectedDomains.H" //#define DEBUG -//#define DEBUGfpma - -# ifdef DEBUG -#include "writeMeshEnsight.H" -#include "writeMeshFPMA.H" -# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -62,45 +57,64 @@ namespace Foam { // * * * * * * * * * * * * Private member functions * * * * * * * * * * * * // - + void cartesianMeshGenerator::createCartesianMesh() { - //- create polyMesh from octree boxes - cartesianMeshExtractor cme(*octreePtr_, meshDict_, mesh_); - + //- create polyMesh from octree boxes + cartesianMeshExtractor cme(*octreePtr_, meshDict_, mesh_); + if( meshDict_.found("decomposePolyhedraIntoTetsAndPyrs") ) { if( readBool(meshDict_.lookup("decomposePolyhedraIntoTetsAndPyrs")) ) cme.decomposeSplitHexes(); } - - cme.createMesh(); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "cartesianMesh"); - # else - writeMeshEnsight(mesh_, "cartesianMesh"); - # endif - //::exit(EXIT_FAILURE); - # endif + + cme.createMesh(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif } - + void cartesianMeshGenerator::surfacePreparation() { - //- removes unnecessary cells and morph the boundary + //- remove cells inside the domains specified by the user + if( meshDict_.found("removeDomains") ) + { + if( Pstream::parRun() ) + { + WarningIn + ( + "void cartesianMeshGenerator::surfacePreparation()" + ) << "The feature removeDomains is not availabel for MPI runs" + << exit(FatalError); + } + + const dictionary& dict = meshDict_.subDict("removeDomains"); + + const wordList domainNames = dict.toc(); + + mesh_.clearAddressingData(); + removeCellsInSelectedDomains rCells(mesh_, *octreePtr_); + + //- read the patches/subsets forming this domain + forAll(domainNames, domainI) + { + wordList domainParts(dict.lookup(domainNames[domainI])); + + rCells.selectCellsInDomain(domainParts); + } + + rCells.removeCells(); + } + + + //- removes unnecessary cells and morph the boundary //- such that there is only one boundary face per cell - //- It also checks topology of cells after morphing is performed -/* do - { - surfaceMorpherCells* cmPtr = new surfaceMorpherCells(mesh_); - cmPtr->morphMesh(); - deleteDemandDrivenData(cmPtr); - } while( topologicalCleaner(mesh_).cleanTopology() ); - */ - + //- It also checks topology of cells after morphing is performed bool changed; + do { changed = false; @@ -108,199 +122,164 @@ void cartesianMeshGenerator::surfacePreparation() checkIrregularSurfaceConnections checkConnections(mesh_); if( checkConnections.checkAndFixIrregularConnections() ) changed = true; - + if( checkNonMappableCellConnections(mesh_).removeCells() ) changed = true; - + if( checkCellConnectionsOverFaces(mesh_).checkCellGroups() ) changed = true; - } while( changed ); - + } while( changed ); + checkBoundaryFacesSharingTwoEdges(mesh_).improveTopology(); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterTopoCleaning"); - # else - writeMeshEnsight(mesh_, "afterTopoCleaning"); - # endif - //::exit(EXIT_FAILURE); - # endif + + # ifdef DEBUG + mesh_.write(); + returnReduce(1, sumOp<label>()); + ::exit(EXIT_SUCCESS); + # endif } - + void cartesianMeshGenerator::mapMeshToSurface() { - //- calculate mesh surface + //- calculate mesh surface meshSurfaceEngine* msePtr = new meshSurfaceEngine(mesh_); - + //- pre-map mesh surface meshSurfaceMapper mapper(*msePtr, *octreePtr_); mapper.preMapVertices(); - + # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "preMappedMesh"); - # else - writeMeshEnsight(mesh_, "preMappedMesh"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif - - //- map mesh surface on the geometry surface - mapper.mapVerticesOntoSurface(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterMapping"); - # else - writeMeshEnsight(mesh_, "afterMapping"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif - - //- untangle surface faces - meshSurfaceOptimizer(*msePtr, *octreePtr_).preOptimizeSurface(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterSurfaceSmoothing"); - # else - writeMeshEnsight(mesh_, "afterSurfaceSmoothing"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif - + mesh_.write(); + returnReduce(1, sumOp<label>()); + //::exit(EXIT_SUCCESS); + # endif + + //- map mesh surface on the geometry surface + mapper.mapVerticesOntoSurface(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif + + //- untangle surface faces + meshSurfaceOptimizer(*msePtr, *octreePtr_).untangleSurface(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif + deleteDemandDrivenData(msePtr); } void cartesianMeshGenerator::mapEdgesAndCorners() { - meshSurfaceEdgeExtractorNonTopo(mesh_, *octreePtr_); - - # ifdef DEBUG - mesh_.write(); - //meshOptimizer(*octreePtr_, mesh_).preOptimize(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "withEdges"); - # else - writeMeshEnsight(mesh_, "withEdges"); - #endif - //::exit(EXIT_FAILURE); - # endif + meshSurfaceEdgeExtractorNonTopo(mesh_, *octreePtr_); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif } void cartesianMeshGenerator::optimiseMeshSurface() { - meshSurfaceEngine mse(mesh_); - meshSurfaceOptimizer(mse, *octreePtr_).optimizeSurface(); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "optSurfaceWithEdges"); - # else - writeMeshEnsight(mesh_, "optSurfaceWithEdges"); - #endif - //::exit(EXIT_FAILURE); - # endif + meshSurfaceEngine mse(mesh_); + meshSurfaceOptimizer(mse, *octreePtr_).optimizeSurface(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif } - -void cartesianMeshGenerator::generateBoudaryLayers() + +void cartesianMeshGenerator::generateBoundaryLayers() { - boundaryLayers bl(mesh_); - - if( meshDict_.found("boundaryLayers") ) + //- add boundary layers + boundaryLayers bl(mesh_); + bl.addLayerForAllPatches(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif +} + +void cartesianMeshGenerator::refBoundaryLayers() +{ + if( meshDict_.isDict("boundaryLayers") ) { - wordList createLayers(meshDict_.lookup("boundaryLayers")); - - forAll(createLayers, patchI) - bl.addLayerForPatch(createLayers[patchI]); + refineBoundaryLayers refLayers(mesh_); + + refineBoundaryLayers::readSettings(meshDict_, refLayers); + + refLayers.refineLayers(); + + meshOptimizer optimizer(mesh_); + optimizer.untangleMeshFV(); } - else - { - //bl.createOTopologyLayers(); - bl.addLayerForAllPatches(); - } - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "meshWithBndLayer"); - # else - writeMeshEnsight(mesh_, "meshWithBndLayer"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif } - + void cartesianMeshGenerator::optimiseFinalMesh() { - //- final optimisation - meshOptimizer optimizer(mesh_); - - optimizer.optimizeSurface(*octreePtr_); - + //- untangle the surface if needed + meshSurfaceEngine mse(mesh_); + meshSurfaceOptimizer(mse, *octreePtr_).optimizeSurface(); deleteDemandDrivenData(octreePtr_); - + + //- final optimisation + meshOptimizer optimizer(mesh_); optimizer.optimizeMeshFV(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"optimisedMesh"); - # else - writeMeshEnsight(mesh_, "optimisedMesh"); - #endif - # endif + optimizer.optimizeLowQualityFaces(); + optimizer.untangleMeshFV(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif } void cartesianMeshGenerator::replaceBoundaries() { renameBoundaryPatches rbp(mesh_, meshDict_); - + # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"renamedPatchesMesh"); - # else - writeMeshEnsight(mesh_, "renamedPatchesMesh"); - #endif - # endif + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif } void cartesianMeshGenerator::renumberMesh() { - polyMeshGenModifier(mesh_).renumberMesh(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"renumberedMesh"); - # else - writeMeshEnsight(mesh_, "renumberedMesh"); - #endif - # endif + polyMeshGenModifier(mesh_).renumberMesh(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_SUCCESS); + # endif } - + void cartesianMeshGenerator::generateMesh() { - createCartesianMesh(); - - surfacePreparation(); - - mapMeshToSurface(); - - mapEdgesAndCorners(); - - optimiseMeshSurface(); - - generateBoudaryLayers(); - - optimiseFinalMesh(); - - renumberMesh(); - + createCartesianMesh(); + + surfacePreparation(); + + mapMeshToSurface(); + + mapEdgesAndCorners(); + + optimiseMeshSurface(); + + generateBoundaryLayers(); + + optimiseFinalMesh(); + + refBoundaryLayers(); + + renumberMesh(); + replaceBoundaries(); } @@ -323,66 +302,49 @@ cartesianMeshGenerator::cartesianMeshGenerator(const Time& time) ) ), octreePtr_(NULL), - mesh_(time) + mesh_(time) { if( true ) { checkMeshDict cmd(meshDict_); } - + fileName surfaceFile = meshDict_.lookup("surfaceFile"); if( Pstream::parRun() ) - surfaceFile = ".."/surfaceFile; + surfaceFile = ".."/surfaceFile; surfacePtr_ = new triSurf(db_.path()/surfaceFile); - - if( meshDict_.found("subsetFileName") ) - { - fileName subsetFileName = meshDict_.lookup("subsetFileName"); - if( Pstream::parRun() ) - subsetFileName = ".."/subsetFileName; - surfacePtr_->readFaceSubsets(db_.path()/subsetFileName); - } - octreePtr_ = new meshOctree(*surfacePtr_); - - meshOctreeCreator(*octreePtr_, meshDict_).createOctreeBoxes(); + if( true ) + { + //- save meta data with the mesh (surface mesh + its topology info) + triSurfaceMetaData sMetaData(*surfacePtr_); + const dictionary& surfMetaDict = sMetaData.metaData(); - generateMesh(); -} + mesh_.metaData().add("surfaceFile", surfaceFile); + mesh_.metaData().add("surfaceMeta", surfMetaDict); + } -/* -cartesianMeshGenerator::cartesianMeshGenerator -( - const objectRegistry& time, - const volScalarField& localCellSize -) -: - db_(time), - surfacePtr_(NULL), - meshDict_ - ( - IOobject - ( - "meshDict", - db_.time().constant(), - db_, - IOobject::MUST_READ, - IOobject::NO_WRITE - ) - ), - octreePtr_(NULL), - mesh_(time) -{ - fileName surfaceFile = meshDict_.lookup("surfaceFile"); + if( surfacePtr_->featureEdges().size() != 0 ) + { + //- create surface patches based on the feature edges + //- and update the meshDict based on the given data + triSurfacePatchManipulator manipulator(*surfacePtr_); + + const triSurf* surfaceWithPatches = + manipulator.surfaceWithPatches(&meshDict_); - surfacePtr_ = new triSurface(db_.path()/surfaceFile); + //- delete the old surface and assign the new one + deleteDemandDrivenData(surfacePtr_); + surfacePtr_ = surfaceWithPatches; + } octreePtr_ = new meshOctree(*surfacePtr_); + meshOctreeCreator(*octreePtr_, meshDict_).createOctreeBoxes(); + generateMesh(); } -*/ // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // @@ -395,8 +357,8 @@ cartesianMeshGenerator::~cartesianMeshGenerator() // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void cartesianMeshGenerator::writeMesh() const -{ - mesh_.write(); +{ + mesh_.write(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.H b/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.H index b30881250338e0f483da27978b2369af890a18ee..1927acb685f3fbeca0df46322a2eff1cd0af9cc9 100644 --- a/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.H +++ b/meshLibrary/cartesianMesh/cartesianMeshGenerator/cartesianMeshGenerator.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class cartesianMeshGenerator @@ -61,45 +60,48 @@ class cartesianMeshGenerator const Time& db_; //- pointer to the surface - triSurf* surfacePtr_; + const triSurf* surfacePtr_; //- IOdictionary containing information about cell sizes, etc.. IOdictionary meshDict_; //- pointer to the octree meshOctree* octreePtr_; - - //- mesh - polyMeshGen mesh_; + + //- mesh + polyMeshGen mesh_; // Private member functions - //- create cartesian mesh - void createCartesianMesh(); - - //- prepare mesh surface - void surfacePreparation(); - - //- map mesh to the surface and untangle surface - void mapMeshToSurface(); - - //- capture edges and corners - void mapEdgesAndCorners(); - - //- optimise surface mesh - void optimiseMeshSurface(); - - //- add boundary layers - void generateBoudaryLayers(); - - //- mesh optimisation - void optimiseFinalMesh(); - + //- create cartesian mesh + void createCartesianMesh(); + + //- prepare mesh surface + void surfacePreparation(); + + //- map mesh to the surface and untangle surface + void mapMeshToSurface(); + + //- capture edges and corners + void mapEdgesAndCorners(); + + //- optimise surface mesh + void optimiseMeshSurface(); + + //- add boundary layers + void generateBoundaryLayers(); + + //- refine boundary layers + void refBoundaryLayers(); + + //- mesh optimisation + void optimiseFinalMesh(); + //- replace boundaries void replaceBoundaries(); - - //- renumber the mesh - void renumberMesh(); - + + //- renumber the mesh + void renumberMesh(); + //- generate mesh void generateMesh(); @@ -116,9 +118,6 @@ public: //- Construct from time cartesianMeshGenerator(const Time&); - //- Construct from time and desired cell size - //cartesianMeshGenerator(const objectRegistry&, const volScalarField&); - // Destructor ~cartesianMeshGenerator(); diff --git a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractor.C b/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractor.C deleted file mode 100644 index 7ae358c93d734e61802f74b252a2d2ded70b8762..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractor.C +++ /dev/null @@ -1,110 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "dualMeshExtractor.H" -#include "meshOctree.H" - -//#define DEBUGDual - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -const direction dualMeshExtractor::faceFlip_[6][4] = - { - {0, 4, 6, 2}, - {5, 1, 3, 7}, - {0, 2, 3, 1}, - {4, 5, 7, 6}, - {2, 6, 7, 3}, - {0, 1, 5, 4} - }; - -void dualMeshExtractor::clearOut() -{ - deleteDemandDrivenData(centreNodeLabelPtr_); -} - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from octree and mesh data -dualMeshExtractor::dualMeshExtractor -( - const meshOctree& octree, - const IOdictionary& dict, - polyMeshGen& mesh -) -: - octreeAddressing_(octree, dict, true), - mesh_(mesh), - centreNodeLabelPtr_(NULL) -{ -} - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -dualMeshExtractor::~dualMeshExtractor() -{ - clearOut(); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void dualMeshExtractor::createMesh() -{ - Info << "Extracting polyMesh" << endl; - - createPoints(); - - createPolyMesh(); - - polyMeshGenModifier(mesh_).removeUnusedVertices(); - polyMeshGenModifier(mesh_).reorderBoundaryFaces(); - - Info << "Mesh has :" << nl - << mesh_.points().size() << " vertices " << nl - << mesh_.faces().size() << " faces" << nl - << mesh_.cells().size() << " cells" << endl; - - # ifdef DEBUGDual - Info << "Points start at address " << long(&mesh_.points()) << endl; - Info << "Faces start at address " << long(&mesh_.faces()) << endl; - Info << "Cells start at address " << long(&mesh_.cells()) << endl; - # endif - - Info << "Finished extracting polyMesh" << endl; -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractor.H b/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractor.H deleted file mode 100644 index 5e7a08bcb3a5c7d72ba6671362f9909985d9c476..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractor.H +++ /dev/null @@ -1,174 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Class - dualMeshExtractor - -Description - Octree for mesh generation - -SourceFiles - dualMeshExtractor.C - -\*---------------------------------------------------------------------------*/ - -#ifndef dualMeshExtractor_H -#define dualMeshExtractor_H - -#include "polyMeshGenModifier.H" -#include "meshOctreeAddressing.H" -#include "Map.H" -#include "DynList.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// Forward declarations -class meshOctree; - -/*---------------------------------------------------------------------------*\ - Class dualMeshExtractor Declaration -\*---------------------------------------------------------------------------*/ - -class dualMeshExtractor -{ - // Private data - //- helper for cell creation - static const direction faceFlip_[6][4]; - - //- reference to the octree - meshOctreeAddressing octreeAddressing_; - - //- reference to the mesh - polyMeshGen& mesh_; - - //- centre node labels - labelListPMG* centreNodeLabelPtr_; - - // Private member functions - //- delete freestore data - void clearOut(); - - //- create vertices and pointLeaves addressing - void createPoints(); - - //- create mesh data - void createPolyMesh(); - - // Nested classes - class decomposeCreatedPoly - { - // Private data - const faceList& cellFaces_; - - const Map<direction>& nodeLevel_; - - boolListList splitFaceNode_; - - //- list of edges over which a face has been split - DynList<edge> splitEdge_; - - //- list containing information if a face - //- is a product of splitting - DynList<bool> splitFace_; - - //- a list of decomposed faces - DynList<face> decomposedFaces_; - - //- helper data - labelListList dfe_; - labelListList def_; - DynList<edge> de_; - boolList se_; - - // Private member functions - //- decompose non-planar faces into triangles - void decomposeFaces(); - - //- calculate helper data - void calculateHelperAddressing(); - - //- find additional splitting edges - void selectAdditionalSplitEdges(); - - //- distribute new faces into cells - void selectFacesForCell(List<faceList>& cFaces); - - //- create missing faces to topologically close new cells - void createMissingFaces(List<faceList>& cFaces); - - public: - - decomposeCreatedPoly - ( - const faceList& cf, - const Map<direction>& nl - ); - - ~decomposeCreatedPoly(); - - void decomposeCell(List<faceList>& decCells); - }; - - // Private copy constructor - //- Disallow default bitwise copy construct - dualMeshExtractor(const dualMeshExtractor&); - - //- Disallow default bitwise assignment - void operator=(const dualMeshExtractor&); - -public: - - // Constructors - - //- Construct from octree and mesh data - dualMeshExtractor - ( - const meshOctree& octree, - const IOdictionary& dict, - polyMeshGen& mesh - ); - - // Destructor - - ~dualMeshExtractor(); - - - // Member Functions - - void createMesh(); -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractorDecompose.C b/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractorDecompose.C deleted file mode 100644 index 020a407bbea2e959001309b5fe2345d099be39f1..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractorDecompose.C +++ /dev/null @@ -1,661 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "dualMeshExtractor.H" -#include "helperFunctions.H" - -//#define DEBUGDual -//#define DEBUGClosedness - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void dualMeshExtractor::decomposeCreatedPoly::decomposeFaces() -{ - //- check if face needs to be decomposed - forAll(cellFaces_, cfI) - { - const face& f = cellFaces_[cfI]; - - if( f.size() == 3 ) - { - decomposedFaces_.append(f); - splitFace_.append(false); - } - else - { - List<direction> nodeLevel(4); - forAll(f, pI) - nodeLevel[pI] = nodeLevel_.find(f[pI])(); - - # ifdef DEBUGDual - forAll(nodeLevel, nI) - Info << "level for node " << f[nI] << " is " - << label(nodeLevel[nI]) << endl; - # endif - - direction minLevel(nodeLevel[0]); - forAll(nodeLevel, nI) - if( minLevel > nodeLevel[nI] ) - minLevel = nodeLevel[nI]; - - //- find positions of min level nodes - DynList<direction> posMin(4); - forAll(nodeLevel, nI) - if( nodeLevel[nI] == minLevel ) - posMin.append(nI); - - switch( posMin.size() ) - { - case 4: - { - //- store face - decomposedFaces_.append(f); - splitFace_.append(false); - } break; - case 3: - { - # ifdef DEBUGDual - Info << "2. Decomposing " << f << endl; - # endif - //- decompose face into 2 triangles - direction posHigh(0); - forAll(nodeLevel, nI) - if( nodeLevel[nI] != minLevel ) - { - posHigh = nI; - break; - } - - splitEdge_.append - ( - edge(f[posHigh], f[(posHigh+2)%4]) - ); - splitFaceNode_[cfI][posHigh] = true; - splitFaceNode_[cfI][(posHigh+2)%4] = true; - - face tri(3); - tri[0] = f[posHigh]; - tri[1] = f[f.fcIndex(posHigh)]; - tri[2] = f[(posHigh+2)%4]; - # ifdef DEBUGDual - Info << "2. tri " << tri << endl; - # endif - decomposedFaces_.append(tri); - splitFace_.append(true); - - tri[0] = f[posHigh]; - tri[1] = f[(posHigh+2)%4]; - tri[2] = f[f.rcIndex(posHigh)]; - # ifdef DEBUGDual - Info << "2. tri " << tri << endl; - # endif - decomposedFaces_.append(tri); - splitFace_.append(true); - } break; - case 2: - { - if( - (f.fcIndex(posMin[0]) == posMin[1]) - || (f.rcIndex(posMin[0]) == posMin[1]) - ) - { - decomposedFaces_.append(f); - splitFace_.append(false); - } - else - { - # ifdef DEBUGDual - Info << "3. Decomposing " << f << endl; - # endif - face tri(3); - direction pm = posMin[0]; - - splitEdge_.append - ( - edge(f[f.fcIndex(pm)], f[f.rcIndex(pm)]) - ); - splitFaceNode_[cfI][f.fcIndex(pm)] = true; - splitFaceNode_[cfI][f.rcIndex(pm)] = true; - - tri[0] = f[pm]; - tri[1] = f[f.fcIndex(pm)]; - tri[2] = f[f.rcIndex(pm)]; - # ifdef DEBUGDual - Info << "3. tri " << tri << endl; - # endif - decomposedFaces_.append(tri); - splitFace_.append(true); - - pm = posMin[1]; - tri[0] = f[pm]; - tri[1] = f[f.fcIndex(pm)]; - tri[2] = f[f.rcIndex(pm)]; - # ifdef DEBUGDual - Info << "3. tri " << tri << endl; - # endif - decomposedFaces_.append(tri); - splitFace_.append(true); - } - } break; - case 1: - { - # ifdef DEBUGDual - Info << "4. Decomposing " << f << endl; - # endif - //- decompose face into 2 triangles - const direction pm = posMin[0]; - - splitEdge_.append - ( - edge(f[f.fcIndex(pm)], f[f.rcIndex(pm)]) - ); - splitFaceNode_[cfI][f.fcIndex(pm)] = true; - splitFaceNode_[cfI][f.rcIndex(pm)] = true; - - face tri(3); - tri[0] = f[pm]; - tri[1] = f[f.fcIndex(pm)]; - tri[2] = f[f.rcIndex(pm)]; - # ifdef DEBUGDual - Info << "4. tri " << tri << endl; - # endif - decomposedFaces_.append(tri); - splitFace_.append(true); - - tri[0] = f[f.fcIndex(pm)]; - tri[1] = f[(pm+2)%4]; - tri[2] = f[f.rcIndex(pm)]; - # ifdef DEBUGDual - Info << "4. tri " << tri << endl; - # endif - decomposedFaces_.append(tri); - splitFace_.append(true); - } break; - }; - } - } -} - -void dualMeshExtractor::decomposeCreatedPoly::calculateHelperAddressing() -{ - dfe_.setSize(decomposedFaces_.size()); - forAll(decomposedFaces_, faceI) - { - dfe_[faceI].setSize(decomposedFaces_[faceI].size()); - dfe_[faceI] = -1; - } - - direction edgeI(0); - forAll(decomposedFaces_, faceI) - { - const edgeList edg = decomposedFaces_[faceI].edges(); - forAll(edg, eI) - { - const label pos = de_.containsAtPosition(edg[eI]); - - if( pos == -1 ) - { - de_.append(edg[eI]); - dfe_[faceI][eI] = edgeI; - def_[edgeI][0] = faceI; - ++edgeI; - } - else - { - dfe_[faceI][eI] = pos; - def_[pos][1] = faceI; - } - } - } - - se_.setSize(edgeI); - se_ = false; - - forAll(de_, eI) - if( splitEdge_.contains(de_[eI]) ) - se_[eI] = true; - - # ifdef DEBUGDual - Info << "de_ " << de_ << endl; - Info << "def_ " << def_ << endl; - Info << "dfe_ " << dfe_ << endl; - Info << "se " << se_ << endl; - # endif -} - -void dualMeshExtractor::decomposeCreatedPoly::selectAdditionalSplitEdges() -{ - DynList<label> splitNode(8); - forAll(splitEdge_, eI) - { - splitNode.appendIfNotIn(splitEdge_[eI].start()); - splitNode.appendIfNotIn(splitEdge_[eI].end()); - } - - forAll(se_, eI) - { - if( se_[eI] ) - continue; - - const edgeList edges0 = decomposedFaces_[def_[eI][0]].edges(); - const edgeList edges1 = decomposedFaces_[def_[eI][1]].edges(); - - const edge& e = de_[eI]; - - # ifdef DEBUGDual - Info << "Checking edge " << eI << " with nodes " << e << endl; - # endif - - forAll(e, vI) - { - if( !splitNode.contains(e[vI]) ) - continue; - - DynList<edge> connectedEdges(2); - forAll(edges0, eJ) - if( (edges0[eJ] != e) && (edges0[eJ].otherVertex(e[vI]) != -1) ) - { - connectedEdges.append(edges0[eJ]); - break; - } - - forAll(edges1, eJ) - if( (edges1[eJ] != e) && (edges1[eJ].otherVertex(e[vI]) != -1) ) - { - connectedEdges.append(edges1[eJ]); - break; - } - - # ifdef DEBUGDual - Info << "Connected edges " << connectedEdges << endl; - # endif - - forAll(cellFaces_, cfI) - { - const face& f = cellFaces_[cfI]; - const edgeList fEdges = f.edges(); - - label e0(-1), e1(-1), cv(-1); - forAll(fEdges, feI) - { - if( fEdges[feI] == connectedEdges[0] ) - { - e0 = feI; - } - else if( fEdges[feI] == connectedEdges[1] ) - { - e1 = feI; - } - - if( f[feI] == e[vI] ) - cv = feI; - } - - # ifdef DEBUGDual - Info << "e0 " << e0 << endl; - Info << "e1 " << e1 << endl; - Info << "cv " << cv << endl; - # endif - - if( (e0 != -1) && (e1 != -1) && splitFaceNode_[cfI][cv] ) - { - se_[eI] = true; - break; - } - } - } - } -} - -void dualMeshExtractor::decomposeCreatedPoly::selectFacesForCell -( - List<faceList>& cFaces -) -{ - if( splitEdge_.size() == 0 ) - { - //- cell has not been split - cFaces.setSize(1); - cFaces[0] = cellFaces_; - } - else - { - direction cellI(0); - - cFaces.setSize(5); - boolList storedFace(decomposedFaces_.size(), false); - - forAll(storedFace, faceI) - { - if( storedFace[faceI] ) - continue; - - DynList<label> front; - front.append(faceI); - - # ifdef DEBUGDual - Info << "Starting front with face " << faceI << endl; - # endif - - cFaces.newElmt(cellI).setSize(5); - direction cfI(0); - - do - { - DynList<label> newFront; - - forAll(front, fI) - { - const label fLabel = front[fI]; - if( storedFace[fLabel] ) - continue; - cFaces[cellI].newElmt(cfI++) = decomposedFaces_[fLabel]; - storedFace[fLabel] = true; - - # ifdef DEBUGDual - Info << "Storing face " << decomposedFaces_[fLabel] - << " into cell " << label(cellI) << endl; - # endif - - forAll(dfe_[fLabel], eI) - { - const label eLabel = dfe_[fLabel][eI]; - if( !se_[eLabel] ) - { - if( !storedFace[def_[eLabel][1]] ) - { - newFront.append(def_[eLabel][1]); - # ifdef DEBUGDual - Info << "Adding face " << def_[eLabel][1] - << " into the front" << endl; - # endif - } - else if( !storedFace[def_[eLabel][0]] ) - { - newFront.append(def_[eLabel][0]); - # ifdef DEBUGDual - Info << "Adding face " << def_[eLabel][0] - << " into the front" << endl; - # endif - } - } - } - } - - front = newFront; - } while( front.size() ); - - cFaces[cellI].setSize(cfI); - ++cellI; - } - - cFaces.setSize(cellI); - # ifdef DEBUGDual - Info << "Decomposed faces " << decomposedFaces_ << endl; - Info << "Cell faces " << cFaces << endl; - forAll(storedFace, fI) - if( !storedFace[fI] ) - FatalErrorIn - ( - "void dualMeshExtractor::decomposeCreatedPoly::" - "selectFacesForCell(List<faceList>&)" - ) << "Face " << fI << " is not stored!" << abort(FatalError); - # endif - - if( cellI < 2 ) - { - //selectFacesForCellComplex(cFaces); - - if( cFaces.size() < 2 ) - FatalErrorIn - ( - "void dualMeshExtractor::decomposeCreatedPoly::" - "selectFacesForCell(List<faceList>&)" - ) << "Cell is not decomposed, but should be!" - << abort(FatalError); - } - } -} - -void dualMeshExtractor::decomposeCreatedPoly::createMissingFaces -( - List<faceList>& cFaces -) -{ - if( splitEdge_.size() == 0 ) - return; - - //- missing faces will be created from open edges shared by two - //- adjacent cells - # ifdef DEBUGDual - Info << "Creating missing faces for cells " << cFaces << endl; - # endif - List<direction> nFacesInCell(cFaces.size()); - forAll(cFaces, cI) - nFacesInCell[cI] = cFaces[cI].size(); - List<DynList<edge> > openEdges(cFaces.size()); - - forAll(cFaces, cI) - { - help::findOpenEdges(cFaces[cI], openEdges[cI]); - } - - # ifdef DEBUGDual - Info << "Open edges are " << openEdges << endl; - # endif - - forAll(openEdges, cellI) - { - const DynList<edge>& oe = openEdges[cellI]; - for(direction cellJ=(cellI+1);cellJ<openEdges.size();++cellJ) - { - const DynList<edge>& oes = openEdges[cellJ]; - - DynList<edge> commonEdges(4); - forAll(oes, eI) - if( oe.contains(oes[eI]) ) - commonEdges.append(oes[eI]); - - # ifdef DEBUGDual - Info << "Common edges are " << commonEdges << endl; - # endif - - if( commonEdges.size() > 1 ) - { - //- zip open chains - help::zipOpenChain(commonEdges); - - //- create a face - face newBf(help::sortEdgeChain(commonEdges)); - # ifdef DEBUGDual - Info << "Created face for cells " << label(cellI) << " and " - << label(cellJ) << " is " << newBf << endl; - # endif - - //- store face into new cells - cFaces[cellI].newElmt(nFacesInCell[cellI]++) = newBf; - cFaces[cellJ].newElmt(nFacesInCell[cellJ]++) = - newBf.reverseFace(); - } - } - } - - forAll(cFaces, cI) - { - cFaces[cI].setSize(nFacesInCell[cI]); - help::findOpenEdges(cFaces[cI], openEdges[cI]); - } - - # ifdef DEBUGDual - Info << "Open edges making internal cell are " << openEdges << endl; - # endif - faceList midCell(4); - direction fI(0); - - forAll(openEdges, cI) - if( openEdges[cI].size() > 1 ) - { - //- zip open chain - help::zipOpenChain(openEdges[cI]); - - //- create new face - face f(help::sortEdgeChain(openEdges[cI])); - midCell[fI++] = f; - cFaces[cI].newElmt(nFacesInCell[cI]++) = f.reverseFace(); - # ifdef DEBUGDual - Info << "1. Adding face of internal cell " << f << endl; - # endif - } - - if( fI > 3 ) - { - midCell.setSize(fI); - - cFaces.setSize(nFacesInCell.size()+1); - cFaces[nFacesInCell.size()] = midCell; - } - - forAll(nFacesInCell, cI) - cFaces[cI].setSize(nFacesInCell[cI]); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -dualMeshExtractor::decomposeCreatedPoly::decomposeCreatedPoly -( - const faceList& cf, - const Map<direction>& nl -) -: - cellFaces_(cf), - nodeLevel_(nl), - splitFaceNode_(cf.size()), - splitEdge_(6), - splitFace_(2*cf.size()), - decomposedFaces_(2*cf.size()), - dfe_(12), - def_(24, labelList(2)), - de_(24), - se_(24) -{ - forAll(cf, fI) - { - splitFaceNode_[fI].setSize(cf[fI].size()); - splitFaceNode_[fI] = true; - } -} - -dualMeshExtractor::decomposeCreatedPoly::~decomposeCreatedPoly() -{} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void dualMeshExtractor::decomposeCreatedPoly::decomposeCell -( - List<faceList>& decCells -) -{ - //decCells.setSize(1); - //decCells[0] = cellFaces_; - - # ifdef DEBUGDual - Info << nl << "Starting decomposing cell " << cellFaces_ << endl; - # endif - - decomposeFaces(); - - if( splitEdge_.size() == 0 ) - { - decCells.setSize(1); - decCells[0] = cellFaces_; - return; - } - - calculateHelperAddressing(); - - selectAdditionalSplitEdges(); - - selectFacesForCell(decCells); - - createMissingFaces(decCells); - - # ifdef DEBUGClosedness - //- check for topological closedness - forAll(decCells, cI) - { - const faceList& cf = decCells[cI]; - - DynList<edge> cEdges(12); - DynList<direction> nAppearances(12); - - forAll(cf, fI) - { - const edgeList edges = cf[fI].edges(); - - forAll(edges, eI) - { - const label pos = cEdges.containsAtPosition(edges[eI]); - - if( pos == -1 ) - { - cEdges.append(edges[eI]); - nAppearances.append(1); - } - else - { - nAppearances[pos]++; - } - } - } - - forAll(nAppearances, eI) - if( nAppearances[eI] != 2 ) - { - Info << "Original cell is " << cellFaces_ << endl; - Info << "cell faces are " << decCells << endl; - Info << "Edges for cell " << cI << " are " - << cEdges << endl; - FatalErrorIn - ( - "void dualMeshExtractor::decomposeCreatedPoly::" - "createMissingFaces(List<faceList>&)" - ) << "Edge " << eI << " is open!!" << abort(FatalError); - } - } - # endif -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractorPolyMesh.C b/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractorPolyMesh.C deleted file mode 100644 index aa619262b57f51e988a4a93bdf32d7dc4fbd9277..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualMeshExtractor/dualMeshExtractorPolyMesh.C +++ /dev/null @@ -1,168 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "dualMeshExtractor.H" -#include "demandDrivenData.H" -#include "meshOctree.H" -#include "polyMeshGenModifierAddCellByCell.H" -#include "labelListPMG.H" - -//#define DEBUGDual - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void dualMeshExtractor::createPoints() -{ - clearOut(); - - const List<direction>& boxType = octreeAddressing_.boxType(); - const meshOctree& octree = octreeAddressing_.octree(); - centreNodeLabelPtr_ = new labelListPMG(boxType.size(), -1); - labelListPMG& centreNode = *centreNodeLabelPtr_; - - const boundBox& rootBox = octree.rootBox(); - label nPoints(0); - - forAll(centreNode, boxI) - if( boxType[boxI] & meshOctreeAddressing::MESHCELL ) - centreNode[boxI] = nPoints++; - - pointFieldPMG& points = mesh_.points(); - points.setSize(nPoints); - - forAll(centreNode, boxI) - if( centreNode[boxI] != -1 ) - { - points[centreNode[boxI]] = - octree.returnLeaf(boxI).centre(rootBox); - } - -} - -void dualMeshExtractor::createPolyMesh() -{ - Info << "Creating polyMesh from octree" << endl; - - const meshOctree& octree = octreeAddressing_.octree(); - const labelListPMG& centreNode = *centreNodeLabelPtr_; - const FRWGraph<label, 8>& nodeLeaves = octreeAddressing_.nodeLeaves(); - - polyMeshGenModifierAddCellByCell meshModifier(mesh_); - - forAll(nodeLeaves, nodeI) - { - bool create(true); - - forAllRow(nodeLeaves, nodeI, nlI) - { - const label leafI = nodeLeaves(nodeI, nlI); - - if( (leafI == -1) || (centreNode[leafI] == -1) ) - { - create = false; - break; - } - } - - if( !create ) - continue; - - Map<direction> nodeLevel; - forAllRow(nodeLeaves, nodeI, nlI) - nodeLevel.insert - ( - centreNode[nodeLeaves(nodeI, nlI)], - octree.returnLeaf(nodeLeaves(nodeI, nlI)).level() - ); - - faceList cFaces(12); - direction fI(0); - - for(label i=0;i<6;++i) - { - DynList<label> f(4); - - for(label j=0;j<4;++j) - { - f.appendIfNotIn - ( - centreNode[nodeLeaves(nodeI, faceFlip_[i][j])] - ); - } - - if( f.size() == 4 ) - { - cFaces.newElmt(fI++) = face(f); - } - else if( f.size() == 3 ) - { - f.shrink(); - cFaces.newElmt(fI++) = face(f); - } - } - - cFaces.setSize(fI); - - # ifdef DEBUGDual - Info << "pLeaves " << pLeaves << endl; - forAll(pLeaves, plI) - Info << "Centre " << plI << " is " - << centreNode[pLeaves[plI]] << endl; - Info << "Cell faces are " << cFaces << nl << endl; - forAll(cFaces, cfI) - Info << "Face " << cfI << " normal is " - << cFaces[cfI].normal(mesh_.points()) << endl; - # endif - - List<faceList> tmpF; - decomposeCreatedPoly dcp(cFaces, nodeLevel); - dcp.decomposeCell(tmpF); - forAll(tmpF, cI) - { - # ifdef DEBUGDual - Info << cI << ". Cell " << cellI << " has faces " - << tmpF[cI] << endl; - # endif - - meshModifier.addCell(tmpF[cI]); - } - } - - Info << "Finished creating polyMesh" << endl; -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualMeshGenerator/dualMeshGenerator.C b/meshLibrary/dualMesh/dualMeshGenerator/dualMeshGenerator.C deleted file mode 100644 index 693d8124c176cd2978207e30ada2fa8a02bdfae8..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualMeshGenerator/dualMeshGenerator.C +++ /dev/null @@ -1,386 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "dualMeshGenerator.H" -#include "triSurf.H" -#include "demandDrivenData.H" -#include "Time.H" -#include "meshOctreeCreator.H" -#include "dualMeshExtractor.H" -#include "meshSurfaceEngine.H" -#include "meshSurfaceMapper.H" -#include "meshSurfaceEdgeExtractorNonTopo.H" -#include "surfaceMorpherCells.H" -#include "meshOptimizer.H" -#include "meshSurfaceOptimizer.H" -#include "topologicalCleaner.H" -#include "boundaryLayers.H" -#include "dualUnfoldConcaveCells.H" -#include "renameBoundaryPatches.H" -#include "checkMeshDict.H" - -//#define DEBUG -//#define DEBUGfpma - -# ifdef DEBUG -#include "writeMeshEnsight.H" -#include "writeMeshFPMA.H" -# endif - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * Private member functions * * * * * * * * * * * * // - -void dualMeshGenerator::generateDualMesh() -{ - //- create polyMesh from octree boxes - dualMeshExtractor dme(*octreePtr_, meshDict_, mesh_); - dme.createMesh(); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "dualMesh"); - # else - writeMeshEnsight(mesh_, "dualMesh"); - # endif - //::exit(EXIT_FAILURE); - # endif -} - -void dualMeshGenerator::surfacePreparation() -{ - //- removes unnecessary cells and morph the boundary - //- such that there is only one boundary face per cell - //- It also checks topology of cells after morphing is performed - do - { - surfaceMorpherCells* cmPtr = new surfaceMorpherCells(mesh_); - cmPtr->morphMesh(); - deleteDemandDrivenData(cmPtr); - } while( topologicalCleaner(mesh_).cleanTopology() ); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterTopoCleaning"); - # else - writeMeshEnsight(mesh_, "afterTopoCleaning"); - # endif - //::exit(EXIT_FAILURE); - # endif -} - -void dualMeshGenerator::mapMeshToSurface() -{ - //- calculate mesh surface - meshSurfaceEngine* msePtr = new meshSurfaceEngine(mesh_); - - //- map mesh surface on the geometry surface - meshSurfaceMapper(*msePtr, *octreePtr_).mapVerticesOntoSurface(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterMapping"); - # else - writeMeshEnsight(mesh_, "afterMapping"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif - - //- untangle surface faces - meshSurfaceOptimizer(*msePtr, *octreePtr_).preOptimizeSurface(); - - # ifdef DEBUG - //meshOptimizer(*octreePtr_, mesh_).preOptimize(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterSurfaceSmoothing"); - # else - writeMeshEnsight(mesh_, "afterSurfaceSmoothing"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif - - deleteDemandDrivenData(msePtr); - - //- extract edges and corners - meshSurfaceEdgeExtractorNonTopo(mesh_, *octreePtr_); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "withEdges"); - # else - writeMeshEnsight(mesh_, "withEdges"); - #endif - //::exit(EXIT_FAILURE); - # endif -} - -void dualMeshGenerator::optimiseMeshSurface() -{ - meshSurfaceEngine mse(mesh_); - meshSurfaceOptimizer(mse, *octreePtr_).optimizeSurface(); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "optSurfaceWithEdges"); - # else - writeMeshEnsight(mesh_, "optSurfaceWithEdges"); - #endif - //::exit(EXIT_FAILURE); - # endif -} - -void dualMeshGenerator::checkConcaveEdges() -{ - //- optimize surface to get rid of nearby vertices - meshSurfaceEngine* msePtr = new meshSurfaceEngine(mesh_); - meshSurfaceOptimizer(*msePtr, *octreePtr_).optimizeSurface(); - deleteDemandDrivenData(msePtr); - - //- repair mesh near concave edges - dualUnfoldConcaveCells(mesh_, *octreePtr_).unfoldInvalidCells(); - - # ifdef DEBUG - mesh_.write(); - //meshOptimizer(*octreePtr_, mesh_).preOptimize(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "correctedEdges"); - # else - writeMeshEnsight(mesh_, "correctedEdges"); - #endif - //::exit(EXIT_FAILURE); - # endif -} - -void dualMeshGenerator::generateBoudaryLayers() -{ - boundaryLayers bl(mesh_); - - if( meshDict_.found("boundaryLayers") ) - { - wordList createLayers(meshDict_.lookup("boundaryLayers")); - - forAll(createLayers, patchI) - bl.addLayerForPatch(createLayers[patchI]); - } - else - { - //bl.createOTopologyLayers(); - bl.addLayerForAllPatches(); - } - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "meshWithBndLayer"); - # else - writeMeshEnsight(mesh_, "meshWithBndLayer"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif -} - -void dualMeshGenerator::optimiseFinalMesh() -{ - //- final optimisation - meshOptimizer optimizer(mesh_); - - optimizer.optimizeSurface(*octreePtr_); - - deleteDemandDrivenData(octreePtr_); - - optimizer.optimizeMeshFV(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"optimisedMesh"); - # else - writeMeshEnsight(mesh_, "optimisedMesh"); - #endif - # endif -} - -void dualMeshGenerator::replaceBoundaries() -{ - renameBoundaryPatches rbp(mesh_, meshDict_); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"renamedPatchesMesh"); - # else - writeMeshEnsight(mesh_, "renamedPatchesMesh"); - #endif - # endif -} - -void dualMeshGenerator::renumberMesh() -{ - polyMeshGenModifier(mesh_).renumberMesh(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"renumberedMesh"); - # else - writeMeshEnsight(mesh_, "renumberedMesh"); - #endif - # endif -} - -void dualMeshGenerator::generateMesh() -{ - generateDualMesh(); - - surfacePreparation(); - - mapMeshToSurface(); - - optimiseMeshSurface(); - - checkConcaveEdges(); - - generateBoudaryLayers(); - - optimiseFinalMesh(); - - renumberMesh(); - - replaceBoundaries(); -} - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from objectRegistry -dualMeshGenerator::dualMeshGenerator -( - const Time& runTime -) -: - runTime_(runTime), - surfacePtr_(NULL), - meshDict_ - ( - IOobject - ( - "meshDict", - runTime.system(), - runTime, - IOobject::MUST_READ, - IOobject::NO_WRITE - ) - ), - octreePtr_(NULL), - mesh_(runTime) -{ - if( true ) - checkMeshDict cmd(meshDict_); - - const fileName surfaceFile = meshDict_.lookup("surfaceFile"); - - surfacePtr_ = new triSurf(runTime_.path()/surfaceFile); - - if( meshDict_.found("subsetFileName") ) - { - const fileName subsetFileName = meshDict_.lookup("subsetFileName"); - surfacePtr_->readFaceSubsets(runTime_.path()/subsetFileName); - } - - octreePtr_ = new meshOctree(*surfacePtr_); - - meshOctreeCreator(*octreePtr_, meshDict_).createOctreeBoxes(); - - generateMesh(); -} - -/* -dualMeshGenerator::dualMeshGenerator -( - const Time& runTime, - const volScalarField& localCellSize -) -: - runTime_(runTime), - surfacePtr_(NULL), - meshDict_ - ( - IOobject - ( - "meshDict", - runTime.constant(), - runTime, - IOobject::MUST_READ, - IOobject::NO_WRITE - ) - ), - octreePtr_(NULL), - mesh_(time) -{ - fileName surfaceFile = meshDict_.lookup("surfaceFile"); - - surfacePtr_ = new triSurface(db_.path()/surfaceFile); - - octreePtr_ = new meshOctree(*surfacePtr_); - - meshOctreeCreator(*octreePtr_, meshDict_).createOctreeBoxes(); - - generateMesh(); -} -*/ - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -dualMeshGenerator::~dualMeshGenerator() -{ - deleteDemandDrivenData(surfacePtr_); - deleteDemandDrivenData(octreePtr_); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void dualMeshGenerator::writeMesh() const -{ - # ifdef DEBUG - mesh_.addressingData().checkCellsZipUp(true); - mesh_.addressingData().checkCellVolumes(true); - # endif - - mesh_.write(); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCells.C b/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCells.C deleted file mode 100644 index a0d788d802e011bc527eb859465138cc2c9e9d11..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCells.C +++ /dev/null @@ -1,144 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "demandDrivenData.H" -#include "dualUnfoldConcaveCells.H" -#include "meshSurfaceEngine.H" -#include "meshSurfaceMapper.H" -#include "correctEdgesBetweenPatches.H" - -//#define DEBUGEdges - -# ifdef DEBUGEdges -#include "writeMeshEnsight.H" -#include "primitiveMesh.H" -# endif - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void dualUnfoldConcaveCells::replaceBoundary() -{ - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - wordList patchNames(boundaries.size()); - forAll(boundaries, patchI) - patchNames[patchI] = boundaries[patchI].patchName(); - - polyMeshGenModifier meshModifier(mesh_); - meshModifier.replaceBoundary - ( - patchNames, - newBoundaryFaces_, - newBoundaryOwners_, - newBoundaryPatches_ - ); - - newBoundaryFaces_.setSize(0); - newBoundaryOwners_.setSize(0); -} - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from polyMeshGen -dualUnfoldConcaveCells::dualUnfoldConcaveCells -( - polyMeshGen& mesh, - const meshOctree& octree -) -: - mesh_(mesh), - octree_(octree), - typeOfCell_(mesh.cells().size(), INTERNALCELL), - typeOfVertex_(mesh.points().size(), NONE), - newBoundaryFaces_(), - newBoundaryOwners_(), - newBoundaryPatches_() -{ - mesh_.clearAddressingData(); -} - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -dualUnfoldConcaveCells::~dualUnfoldConcaveCells() -{ -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void dualUnfoldConcaveCells::unfoldInvalidCells() -{ - const meshSurfaceEngine* msePtr = new meshSurfaceEngine(mesh_); - - if( findConcaveEdges(*msePtr) ) - { - markVertexTypes(*msePtr); - - storeAndMergeBoundaryFaces(*msePtr); - - createNeighbouringBoundaryFaces(*msePtr); - - storeRemainingBoundaryFaces(*msePtr); - - removeConcaveVerticesFromIntFaces(*msePtr); - - deleteDemandDrivenData(msePtr); - - replaceBoundary(); - - checkAndRepairBoundary(); - - polyMeshGenModifier(mesh_).removeUnusedVertices(); - - # ifdef DEBUGEdges - mesh_.addressingData().checkMesh(true); - mesh_.write(); - ::exit(EXIT_FAILURE); - # endif - - correctEdgesBetweenPatches correctEdges(mesh_); - meshSurfaceMapper(*msePtr, octree_).mapCornersAndEdges(); - - # ifdef DEBUGEdges - mesh_.addressingData().checkMesh(); - # endif - } - else - { - deleteDemandDrivenData(msePtr); - } -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCells.H b/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCells.H deleted file mode 100644 index 10bc57dba17b7c0e2f43ed484b27f36751e24e1a..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCells.H +++ /dev/null @@ -1,159 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Class - dualUnfoldConcaveCells - -Description - Checks for concave cells near surface edges. Removes vertices and merges - faces in order to untangle the mesh - -SourceFiles - dualUnfoldConcaveCells.C - -\*---------------------------------------------------------------------------*/ - -#ifndef dualUnfoldConcaveCells_H -#define dualUnfoldConcaveCells_H - -#include "polyMeshGenModifier.H" -#include "labelListPMG.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -class meshSurfaceEngine; -class meshOctree; - -/*---------------------------------------------------------------------------*\ - Class dualUnfoldConcaveCells Declaration -\*---------------------------------------------------------------------------*/ - -class dualUnfoldConcaveCells -{ - // Private data - //- reference to the mesh - polyMeshGen& mesh_; - - //- reference to the octree - const meshOctree& octree_; - - //- list containing classification of cell type - List<direction> typeOfCell_; - - //- list containing classification of vertex type - List<direction> typeOfVertex_; - - //- new boundary faces and owner cells - VRWGraph newBoundaryFaces_; - labelListPMG newBoundaryOwners_; - labelListPMG newBoundaryPatches_; - - // Private member functions - //- find edges to remove - bool findConcaveEdges(const meshSurfaceEngine& mse); - - //- mark vertices according to their type - void markVertexTypes(const meshSurfaceEngine& mse); - - //- merge boundary faces of the given cell - label mergeBoundaryFacesOfCell(const label cellI); - - //- merge boundary faces of concave cells - void storeAndMergeBoundaryFaces(const meshSurfaceEngine& mse); - - //- create boundary faces for cells next to concave ones - void createNeighbouringBoundaryFaces(const meshSurfaceEngine& mse); - - //- store remaining boundary faces which have not been altered - void storeRemainingBoundaryFaces(const meshSurfaceEngine& mse); - - //- remove concave vertices from internal faces - void removeConcaveVerticesFromIntFaces(const meshSurfaceEngine& mse); - - //- replace mesh boundary with the newly created boundary faces - void replaceBoundary(); - - //- perform a check to determine if all vertices have been removed - //- correctly, and that all treated cells are topologically closed - void checkAndRepairBoundary(); - - // Enumerations - - enum vertexType_ - { - NONE = 0, - CONCAVE = 1, - EDGE = 2, - CORNER = 4, - MOVED = 8, - REMOVE = 16 - }; - - enum cellType_ - { - INTERNALCELL = 0, - BOUNDARYCELL = 1, - CONCAVECELL = 2, - TREATEDCELL = 4, - MERGEDCELL = 8 - }; - - //- Disallow default bitwise copy construct - dualUnfoldConcaveCells(const dualUnfoldConcaveCells&); - - //- Disallow default bitwise assignment - void operator=(const dualUnfoldConcaveCells&); - -public: - - // Constructors - //- Construct from polyMeshGen - dualUnfoldConcaveCells - ( - polyMeshGen& mesh, - const meshOctree& octree - ); - - // Destructor - - ~dualUnfoldConcaveCells(); - - // Member Functions - //- clean topologically problematic cells - void unfoldInvalidCells(); -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCellsMergeFaces.C b/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCellsMergeFaces.C deleted file mode 100644 index ffcda4a54ec9760778fdccdb0cefa23bb9b806c3..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCellsMergeFaces.C +++ /dev/null @@ -1,315 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "demandDrivenData.H" -#include "dualUnfoldConcaveCells.H" -#include "helperFunctions.H" -#include "meshSurfaceEngine.H" -#include "primitiveMesh.H" -#include "tetrahedron.H" - -//#define DEBUGEdges - -# ifdef DEBUGEdges -#include "cellSet.H" -#include "objectRegistry.H" -#include "Time.H" -# endif - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -bool dualUnfoldConcaveCells::findConcaveEdges(const meshSurfaceEngine& mse) -{ - const pointFieldPMG& points = mesh_.points(); - const faceList::subList& bFaces = mse.boundaryFaces(); - const edgeList& edges = mse.edges(); - const VRWGraph& edgeFaces = mse.edgeFaces(); - const labelList& faceOwner = mse.faceOwners(); - const labelList& facePatch = mse.boundaryFacePatches(); - - //- mark all boundary cells - forAll(faceOwner, bfI) - typeOfCell_[faceOwner[bfI]] |= BOUNDARYCELL; - - //- find concave cells - bool foundConcave(false); - forAll(edgeFaces, edgeI) - { - const label fOwn = edgeFaces(edgeI, 0); - const label fNei = edgeFaces(edgeI, 1); - - if( - (faceOwner[fOwn] == faceOwner[fNei]) && - (facePatch[fOwn] != facePatch[fNei]) - ) - { - if( !help::isSharedEdgeConvex(points, bFaces[fOwn], bFaces[fNei]) ) - { - foundConcave = true; - - const edge& e = edges[edgeI]; - typeOfVertex_[e.start()] |= CONCAVE; - typeOfVertex_[e.end()] |= CONCAVE; - - typeOfCell_[faceOwner[fOwn]] |= CONCAVECELL; - } - } - } - - # ifdef DEBUGEdges - cellSet badCells - ( - IOobject - ( - "concaveCells", - mesh_.returnRegistry().time().constant(), - "polyMesh/sets", - mesh_.returnRegistry() - ) - ); - - forAll(typeOfCell_, cI) - if( typeOfCell_[cI] & CONCAVECELL ) - badCells.insert(cI); - - badCells.write(); - //::exit(1); - # endif - - return foundConcave; -} - -void dualUnfoldConcaveCells::markVertexTypes(const meshSurfaceEngine& mse) -{ - const labelList& bPoints = mse.boundaryPoints(); - const VRWGraph& pointFaces = mse.pointFaces(); - const labelList& facePatch = mse.boundaryFacePatches(); - - forAll(pointFaces, bpI) - { - DynList<label> patches(5); - forAllRow(pointFaces, bpI, pfI) - patches.appendIfNotIn(facePatch[pointFaces(bpI, pfI)]); - - if( patches.size() > 2 ) - { - typeOfVertex_[bPoints[bpI]] |= CORNER; - } - else if( patches.size() == 2 ) - { - typeOfVertex_[bPoints[bpI]] |= EDGE; - } - } -} - -label dualUnfoldConcaveCells::mergeBoundaryFacesOfCell(const label cellI) -{ - if( typeOfCell_[cellI] & MERGEDCELL ) - { - FatalErrorIn - ( - "label dualUnfoldConcaveCells::" - "mergeBoundaryFacesOfCell(const label cellI)" - ) << "Cell " << cellI << " has already been merged!" - << abort(FatalError); - } - else - { - typeOfCell_[cellI] |= MERGEDCELL; - } - - const pointFieldPMG& points = mesh_.points(); - const faceListPMG& faces = mesh_.faces(); - const cell& c = mesh_.cells()[cellI]; - - DynList<face> bFaces(5); - DynList<label> facePatch(5); - - //- find boundary faces and corresponding patches - forAll(c, fI) - { - const label fPatch = mesh_.faceIsInPatch(c[fI]); - - if( fPatch != -1 ) - { - bFaces.append(faces[c[fI]]); - facePatch.append(fPatch); - } - } - - # ifdef DEBUGEdges - Info << "Boundary faces for cell " << cellI << " are " << bFaces << endl; - Info << "Patches for boundary faces are " << facePatch << endl; - # endif - - //- merge all boundary faces into one face - //- this assumes that there was originally only one - //- boundary face per cell. This is the cases after running - //- surface morpher and topological cleaner - boolList isFaceMerged(bFaces.size(), false); - face mf(bFaces[0]); - isFaceMerged[0] = true; - bool merged; - do - { - merged = false; - for(label i=1;i<bFaces.size();++i) - if( - !isFaceMerged[i] && - help::shareAnEdge(mf, bFaces[i]) - ) - { - merged = true; - isFaceMerged[i] = true; - mf = help::mergeTwoFaces(mf, bFaces[i]); - } - } while( merged ); - - # ifdef DEBUGEdges - Info << "Merged face for cell is " << mf << endl; - # endif - - DynList<label> shrinkedFace(mf.size()); - forAll(mf, pI) - if( !(typeOfVertex_[mf[pI]] & EDGE) ) - { - shrinkedFace.append(mf[pI]); - } - else - { - # ifdef DEBUGEdges - Info << "Marking vertex " << mf[pI] << " for removal!" << endl; - # endif - - typeOfVertex_[mf[pI]] |= REMOVE; - } - - shrinkedFace.shrink(); - - //- face will be stored into a patch corresponding - //- to the largest face - label fPatch(facePatch[0]); - scalar size(0.0); - forAll(bFaces, bfI) - { - # ifdef DEBUGEdges - Info << "Sizes of bundary face " << bfI << " is " - << bFaces[bfI].mag(points) << endl; - # endif - - if( bFaces[bfI].mag(points) > size ) - { - fPatch = facePatch[bfI]; - size = bFaces[bfI].mag(points); - } - } - - //- store shrinked face - # ifdef DEBUGEdges - Info << "Storing face " << shrinkedFace << " in patch" - << fPatch << endl; - #endif - - newBoundaryFaces_.appendList(face(shrinkedFace)); - newBoundaryOwners_.append(cellI); - newBoundaryPatches_.append(fPatch); - - return fPatch; -} - -void dualUnfoldConcaveCells::storeAndMergeBoundaryFaces -( - const meshSurfaceEngine& mse -) -{ - bool addSelected; - do - { - addSelected = false; - - //- merge boundary faces for concave cells - forAll(typeOfCell_, cellI) - if( (typeOfCell_[cellI] & CONCAVECELL) && - !(typeOfCell_[cellI] & TREATEDCELL) - ) - { - # ifdef DEBUGEdges - Info << "Merging faces of concave cell " << cellI << endl; - # endif - - mergeBoundaryFacesOfCell(cellI); - - //- set flag that the cell has been treated - typeOfCell_[cellI] |= TREATEDCELL; - } - - const VRWGraph& edgeFaces = mse.edgeFaces(); - const edgeList& edges = mse.edges(); - const labelList& faceOwner = mse.faceOwners(); - const labelList& facePatch = mse.boundaryFacePatches(); - forAll(edgeFaces, edgeI) - { - const label fOwn = edgeFaces(edgeI, 0); - const label fNei = edgeFaces(edgeI, 1); - - if( - (faceOwner[fOwn] == faceOwner[fNei]) && - (facePatch[fOwn] != facePatch[fNei]) - ) - { - const edge& e = edges[edgeI]; - if( - (typeOfVertex_[e[0]] & REMOVE) && - (typeOfVertex_[e[1]] & REMOVE) && - !(typeOfCell_[faceOwner[fOwn]] & CONCAVECELL) - ) - { - typeOfCell_[faceOwner[fOwn]] |= CONCAVECELL; - addSelected = true; - - # ifdef DEBUGEdges - Info << "Cell " << faceOwner[fOwn] << " is also concave" - << endl; - # endif - } - } - } - } - while( addSelected ); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCellsMergeFacesConsistency.C b/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCellsMergeFacesConsistency.C deleted file mode 100644 index 3aad4c25eefeeac9203be9dc29858113f8fce760..0000000000000000000000000000000000000000 --- a/meshLibrary/dualMesh/dualUnfoldConcaveCells/dualUnfoldConcaveCellsMergeFacesConsistency.C +++ /dev/null @@ -1,408 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "demandDrivenData.H" -#include "dualUnfoldConcaveCells.H" -#include "helperFunctions.H" -#include "meshSurfaceEngine.H" -#include "polyMeshGenAddressing.H" -#include "tetrahedron.H" - -//#define DEBUGEdges - -# ifdef DEBUGEdges -#include "cellSet.H" -#include "objectRegistry.H" -#include "Time.H" -# endif - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void dualUnfoldConcaveCells::createNeighbouringBoundaryFaces -( - const meshSurfaceEngine& mse -) -{ - const labelList& bPoints = mse.boundaryPoints(); - const VRWGraph& pointFaces = mse.pointFaces(); - const labelList& faceOwner = mse.faceOwners(); - const labelList& bp = mse.bp(); - - //- find the patch for merged faces which belong to the given cell - //- this here assumes that the original cell before edge extraction - //- has only one boundary face!! This is the case if surface preparation - //- is applied before edge extraction - labelListPMG newPatchForCell(mesh_.cells().size(), -1); - forAll(newBoundaryFaces_, faceI) - { - if( newPatchForCell[newBoundaryOwners_[faceI]] == -1 ) - { - newPatchForCell[newBoundaryOwners_[faceI]] = - newBoundaryPatches_[faceI]; - } - else - { - FatalErrorIn - ( - "void dualUnfoldConcaveCells::" - "createNeighbouringBoundaryFaces(const meshSurfaceEngine&)" - ) << "Cell " << newBoundaryOwners_[faceI] - << " has more than one " - << " boundary face! Cannot proceed!" << abort(FatalError); - } - } - - //- create a list of possible candidates to store - labelListPMG front; - forAll(bPoints, bpI) - if( typeOfVertex_[bPoints[bpI]] & REMOVE ) - { - front.append(bpI); - } - - # ifdef DEBUGEdges - Info << "Front points " << front << endl; - # endif - - //- start creating new boundary faces - const cellListPMG& cells = mesh_.cells(); - const faceListPMG& faces = mesh_.faces(); - - while( front.size() != 0 ) - { - labelListPMG newFront; - - forAll(front, fpI) - { - const label fLabel = front[fpI]; - - label cellI(-1), patchOfTreated(-1); - forAllRow(pointFaces, fLabel, pfI) - { - const label pfLabel = pointFaces(fLabel, pfI); - - if( - typeOfCell_[faceOwner[pfLabel]] == - BOUNDARYCELL - ) - { - cellI = faceOwner[pfLabel]; - - } - else if( newPatchForCell[faceOwner[pfLabel]] != -1 ) - { - patchOfTreated = newPatchForCell[faceOwner[pfLabel]]; - } - } - - if( cellI == -1 ) - continue; - - typeOfCell_[cellI] |= TREATEDCELL; - - # ifdef DEBUGEdges - Info << "Checking cell " << cellI << endl; - Info << "Patch of treated " << patchOfTreated << endl; - Info << "Front point " << bPoints[front[fpI]] << endl; - # endif - - //- find boundary faces for the given cell - DynList<face> bFaces(5); - DynList<label> facePatch(5); - forAll(cells[cellI], fI) - { - const label patch = mesh_.faceIsInPatch(cells[cellI][fI]); - if( patch != -1 ) - { - bFaces.append(faces[cells[cellI][fI]]); - facePatch.append(patch); - } - } - - # ifdef DEBUGEdges - Info << "Boundary faces " << bFaces << endl; - Info << "Face patches " << facePatch << endl; - # endif - - //- check if faces have to be merged - bool merge(false); - forAll(bFaces, bfI) - { - const face& f = bFaces[bfI]; - direction nPointsInFace(0); - - # ifdef DEBUGEdges - DynList<label> removePoint(2); - # endif - - forAll(f, pI) - if( !(typeOfVertex_[f[pI]] & REMOVE) ) - { - ++nPointsInFace; - } - # ifdef DEBUGEdges - else - { - removePoint.append(f[pI]); - } - # endif - - # ifdef DEBUGEdges - Info << "Vertices removed from boundary face " << bfI - << " are " << removePoint << endl; - # endif - - if( nPointsInFace < 3 ) - { - merge = true; - break; - } - } - - if( (patchOfTreated == -1) || !facePatch.contains(patchOfTreated) ) - merge = true; - - if( merge ) - { - # ifdef DEBUGEdges - Info << "Merging boundary faces of cell" << endl; - # endif - //- merge boundary faces of the given cell - newPatchForCell[cellI] = mergeBoundaryFacesOfCell(cellI); - - forAll(bFaces, bfI) - { - const face& f = bFaces[bfI]; - forAll(f, pI) - if( typeOfVertex_[f[pI]] & REMOVE ) - newFront.append(bp[f[pI]]); - } - } - else - { - # ifdef DEBUGEdges - Info << "Changing boundary faces" << endl; - # endif - - //- change boundary faces - face triF(3); - forAll(bFaces, bfI) - if( facePatch[bfI] != patchOfTreated ) - { - const face& bf = bFaces[bfI]; - //- remove edge vertex from face not it the same patch - //- as already treated cell - face newBf(bf.size() - 1); - label rpos(-1), pJ(0); - forAll(bf, pI) - if( typeOfVertex_[bf[pI]] & REMOVE ) - { - rpos = pI; - } - else - { - newBf.newElmt(pJ++) = bf[pI]; - } - - //- store shrinked boundary face - newBf.setSize(pJ); - newBoundaryFaces_.appendList(newBf); - newBoundaryOwners_.append(cellI); - newBoundaryPatches_.append(facePatch[bfI]); - - if( rpos != -1 ) - { - triF[0] = bf.prevLabel(rpos); - triF[1] = bf[rpos]; - triF[2] = bf.nextLabel(rpos); - - # ifdef DEBUGEdges - Info << "triF " << triF << endl; - # endif - } - } - - forAll(bFaces, bfI) - if( facePatch[bfI] == patchOfTreated ) - { - //- merge face with triF and store it - const face mf = help::mergeTwoFaces(bFaces[bfI], triF); - - # ifdef DEBUGEdges - Info << "Merged face " << mf << endl; - # endif - - face shrinkedFace(mf.size() -1); - direction i(0); - forAll(mf, pI) - if( !(typeOfVertex_[mf[pI]] & REMOVE) ) - shrinkedFace[i++] = mf[pI]; - - # ifdef DEBUGEdges - Info << "Storing face " << shrinkedFace << " into patch" - << patchOfTreated << endl; - # endif - - newBoundaryFaces_.appendList(shrinkedFace); - newBoundaryOwners_.append(cellI); - newBoundaryPatches_.append(patchOfTreated); - } - } - } - - front = newFront; - } -} - -void dualUnfoldConcaveCells::storeRemainingBoundaryFaces -( - const meshSurfaceEngine& mse -) -{ - const faceList::subList& bFaces = mse.boundaryFaces(); - const labelList& faceOwner = mse.faceOwners(); - const labelList& facePatch = mse.boundaryFacePatches(); - - forAll(bFaces, bfI) - if( !(typeOfCell_[faceOwner[bfI]] & TREATEDCELL) ) - { - newBoundaryFaces_.appendList(bFaces[bfI]); - newBoundaryOwners_.append(faceOwner[bfI]); - newBoundaryPatches_.append(facePatch[bfI]); - } -} - -void dualUnfoldConcaveCells::removeConcaveVerticesFromIntFaces -( - const meshSurfaceEngine& mse -) -{ - const label nIntFaces = mesh_.nInternalFaces(); - polyMeshGenModifier meshModifier(mesh_); - faceListPMG& faces = meshModifier.facesAccess(); - - const VRWGraph& pointFaces = mesh_.addressingData().pointFaces(); - forAll(pointFaces, pI) - if( (typeOfVertex_[pI] & REMOVE) ) - { - # ifdef DEBUGEdges - Info << "Removing vertex " << pI << " from internal faces" << endl; - # endif - - forAllRow(pointFaces, pI, pfI) - { - const label pointFaceI = pointFaces(pI, pfI); - if( pointFaceI < nIntFaces ) - { - const face& f = faces[pointFaceI]; - - DynList<label> newF(f.size()-1); - forAll(f, pJ) - if( f[pJ] != pI ) - newF.append(f[pJ]); - - if( newF.size() > 2 ) - { - # ifdef DEBUGEdges - Info << "Internal face " << f << " is shrinked to" - << newF << endl; - # endif - newF.shrink(); - faces[pointFaceI] = face(newF); - } - } - } - } - - mesh_.clearAddressingData(); -} - -void dualUnfoldConcaveCells::checkAndRepairBoundary() -{ - const faceListPMG& faces = mesh_.faces(); - const labelList& owner = mesh_.owner(); - - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - - newBoundaryFaces_.setSize(boundaries.size()); - newBoundaryOwners_.setSize(boundaries.size()); - - boolList touchedOwner(mesh_.cells().size(), false); - - bool changed(false); - - forAll(boundaries, patchI) - { - const label start = boundaries[patchI].patchStart(); - const label end = start + boundaries[patchI].patchSize(); - - for(label faceI=start;faceI<end;++faceI) - { - const face& f = faces[faceI]; - const label own = owner[faceI]; - - bool merge(false); - - forAll(f, pI) - if( typeOfVertex_[f[pI]] & REMOVE ) - { - merge = true; - break; - } - - if( merge && (typeOfCell_[own] & TREATEDCELL) ) - { - changed = true; - if( touchedOwner[own] ) continue; - - touchedOwner[own] = true; - mergeBoundaryFacesOfCell(own); - } - else - { - newBoundaryFaces_.appendList(f); - newBoundaryOwners_.append(own); - newBoundaryPatches_.append(patchI); - } - } - } - - if( changed ) - replaceBoundary(); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.C b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.C index 08f3cc7ed36d581bb6960fa77f528be277d8712f..a2b43555e9d0915e4bc774920a71b3f693e67355 100644 --- a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.C +++ b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,10 +36,10 @@ namespace Foam { // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void hexMeshExtractor::clearOut() { - deleteDemandDrivenData(centreNodeLabelPtr_); + deleteDemandDrivenData(centreNodeLabelPtr_); deleteDemandDrivenData(subVerticesPtr_); } @@ -76,19 +75,19 @@ void hexMeshExtractor::createMesh() Info << "Extracting hex mesh" << endl; classifyOctreePoints(); - + createPoints(); createHexMesh(); - + polyMeshGenModifier(mesh_).removeUnusedVertices(); polyMeshGenModifier(mesh_).reorderBoundaryFaces(); - + Info << "Mesh has :" << nl - << mesh_.points().size() << " vertices " << nl - << mesh_.faces().size() << " faces" << nl - << mesh_.cells().size() << " cells" << endl; - + << mesh_.points().size() << " vertices " << nl + << mesh_.faces().size() << " faces" << nl + << mesh_.cells().size() << " cells" << endl; + Info << "Finished extracting hex template" << endl; } diff --git a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.H b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.H index f8401bf08d56b8ab6def159bcaa57347ebef538b..31faf651fe23e0cd7ab6ccf96992fd0a2201e598 100644 --- a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.H +++ b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractor.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class hexMeshExtractor @@ -56,12 +55,12 @@ class hexMeshExtractor // Private data //- octree and addressing meshOctreeAddressing octreeAddressing_; - + //- reference to the mesh polyMeshGen& mesh_; - + //- centre node labels - labelListPMG* centreNodeLabelPtr_; + labelLongList* centreNodeLabelPtr_; //- subvertices generated inside octree leaves VRWGraph* subVerticesPtr_; @@ -75,7 +74,7 @@ class hexMeshExtractor //- classify octree points (CORNER, EDGECENTRE, FACECENTRE) void classifyOctreePoints(); - + //- create mesh points and pointLeaves addressing void createPoints(); @@ -101,9 +100,9 @@ class hexMeshExtractor //- const reference to the octree const meshOctree& octree_; - + //- centre node labels - const labelListPMG& centreNodeLabel_; + const labelLongList& centreNodeLabel_; //- subvertices generated inside octree leaves const VRWGraph& subVertices_; @@ -150,7 +149,7 @@ class hexMeshExtractor ( polyMeshGen& mesh, const meshOctree& octree, - const labelListPMG& centreNodeLabel, + const labelLongList& centreNodeLabel, const VRWGraph& subVertices, const List<direction>& octreeVertexType, const VRWGraph& nodeLabels, @@ -203,7 +202,7 @@ public: // Member Functions - void createMesh(); + void createMesh(); }; diff --git a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorHexMesh.C b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorHexMesh.C index 37fcbc40fe2c7b52b5abadab34782c0be099cead..432260ada7df60233dda740d62a8f2141614576d 100644 --- a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorHexMesh.C +++ b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorHexMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,15 +29,10 @@ Description #include "demandDrivenData.H" #include "meshOctree.H" #include "polyMeshGenModifierAddCellByCell.H" -#include "labelListPMG.H" +#include "labelLongList.H" //#define DEBUGHex -# ifdef DEBUGHex -#include "writeMeshFPMA.H" -#include "writeMeshFLMA.H" -# endif - // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam @@ -51,38 +45,38 @@ void hexMeshExtractor::classifyOctreePoints() const VRWGraph& nodeLabels = octreeAddressing_.nodeLabels(); const FRWGraph<label, 8>& nl = octreeAddressing_.nodeLeaves(); const meshOctree& octree = octreeAddressing_.octree(); - + octreeVertexType_.setSize(nl.size()); octreeVertexType_ = NONE; - + forAll(nl, pointI) { if( octreeVertexType_[pointI] ) continue; - + direction maxLevel(0), minLevel(255); - + bool boundaryNode(false); forAllRow(nl, pointI, nlI) { const label leafI = nl(pointI, nlI); - + if( leafI < 0 ) { boundaryNode = true; continue; } - + maxLevel = Foam::max(maxLevel, octree.returnLeaf(leafI).level()); minLevel = Foam::min(minLevel, octree.returnLeaf(leafI).level()); } - + if( boundaryNode ) { octreeVertexType_[pointI] = BOUNDARY; continue; } - + if( maxLevel == minLevel ) { //- all octree leaves are at the same level. Point is a corner @@ -95,16 +89,16 @@ void hexMeshExtractor::classifyOctreePoints() forAllRow(nl, pointI, nlI) { const label leafI = nl(pointI, nlI); - + Info << "Leaf at position " << nlI << " is " << nl(pointI, nlI) << endl; - + if( leafI >= 0 ) Info << "Leaf coordinates " << octree.returnLeaf(leafI) << endl; } #endif - + //- check if the octree point is at a face centre of a father //- cube of the boxes found in the directions of a face //- there must exist 4 different boxes at minLevel @@ -112,16 +106,16 @@ void hexMeshExtractor::classifyOctreePoints() for(label fI=0;fI<6;++fI) { const label* fNodes = meshOctreeCubeCoordinates::faceNodes_[fI]; - + //- check if the vertex is a centre over a single face or edge - if( + if( (nl(pointI, fNodes[0]) == nl(pointI, fNodes[1])) || (nl(pointI, fNodes[1]) == nl(pointI, fNodes[2])) || (nl(pointI, fNodes[2]) == nl(pointI, fNodes[0])) || (nl(pointI, fNodes[0]) == nl(pointI, fNodes[3])) ) continue; - + //- check if all cubes are at minLevel and the nodes //- of the opposite face shall be at maxLevel bool check(false); @@ -129,26 +123,26 @@ void hexMeshExtractor::classifyOctreePoints() { const meshOctreeCubeBasic& oca = octree.returnLeaf(nl(pointI, fNodes[i])); - + if( oca.level() != minLevel ) { check = true; break; } - + const meshOctreeCubeBasic& ocb = octree.returnLeaf(nl(pointI, 7-fNodes[i])); - + if( ocb.level() != maxLevel ) { check = true; break; } } - + if( check ) continue; - + //- check if the cubes have the same father box check = true; const meshOctreeCubeBasic& oc = @@ -158,22 +152,22 @@ void hexMeshExtractor::classifyOctreePoints() { const meshOctreeCubeBasic& oca = octree.returnLeaf(nl(pointI, fNodes[i])); - + if( oca.reduceLevelBy(1) != father ) { check = false; break; } } - + if( check ) { # ifdef DEBUGHex Info << "Point " << pointI << " is a face centre" << endl; # endif - + octreeVertexType_[pointI] = FACECENTRE; - + //- mark opposite vertices at all 4 faces as NOSUBVERTICES const label ofI = meshOctreeCubeCoordinates::oppositeFace_[fI]; @@ -182,7 +176,7 @@ void hexMeshExtractor::classifyOctreePoints() for(label i=0;i<4;++i) { const label leafJ = nl(pointI, fNodes[i]); - + label pos(-1); for(label j=0;j<4;++j) if( nodeLabels(leafJ, ofNodes[j]) == pointI ) @@ -190,85 +184,85 @@ void hexMeshExtractor::classifyOctreePoints() pos = j; break; } - + if( pos == -1 ) FatalErrorIn ( "void hexMeshExtractor::classifyOctreePoints()" ) << "Cannot find vertex" << abort(FatalError); - + const label pJ = nodeLabels(leafJ, ofNodes[(pos+2)%4]); octreeVertexType_[pJ] = NOSUBVERTICES; } } } - + if( !octreeVertexType_[pointI] ) { # ifdef DEBUGHex Info << "Point " << pointI << " is of type MIXED" << endl; # endif - + octreeVertexType_[pointI] = MIXED; } } } - + # ifdef DEBUGHex Info << "Writting debug mesh" << endl; Info << "Number of octree leaves is " << octree.numberOfLeaves() << endl; polyMeshGen pmg(mesh_.returnTime()); - + const List<direction>& boxType = octreeAddressing_.boxType(); const pointField& octreePoints = octreeAddressing_.octreePoints(); const VRWGraph& octreeFaces = octreeAddressing_.octreeFaces(); const VRWGraph& boxFaces = octreeAddressing_.leafFaces(); - const labelListPMG& neighbour = octreeAddressing_.octreeFaceNeighbour(); - + const labelLongList& neighbour = octreeAddressing_.octreeFaceNeighbour(); + pointFieldPMG& points = polyMeshGenModifier(pmg).pointsAccess(); points.setSize(octreePoints.size()); forAll(octreePoints, pI) points[pI] = octreePoints[pI]; - + polyMeshGenModifierAddCellByCell* bModPtr = new polyMeshGenModifierAddCellByCell(pmg); forAll(boxType, leafI) { if( !(boxType[leafI] & meshOctreeAddressing::MESHCELL) ) continue; - + faceList c(boxFaces.sizeOfRow(leafI)); - + forAllRow(boxFaces, leafI, fI) { const label faceI = boxFaces(leafI, fI); - + face f(octreeFaces.sizeOfRow(faceI)); forAll(f, pI) f[pI] = octreeFaces(faceI, pI); - + if( neighbour[faceI] == leafI ) f = f.reverseFace(); - + c[fI].transfer(f); } - + bModPtr->addCell(c); } - + deleteDemandDrivenData(bModPtr); - + Info << "Mesh has " << pmg.faces().size() << " faces" << endl; Info << "Mesh has " << pmg.cells().size() << " cells" << endl; - + polyMeshGenModifier(pmg).reorderBoundaryFaces(); - + const label cornerID = pmg.addPointSubset("CORNER"); const label faceID = pmg.addPointSubset("FACECENTRE"); const label edgeID = pmg.addPointSubset("NOSUBVERTICES"); const label bndVrt = pmg.addPointSubset("BOUNDARY"); - + forAll(octreeVertexType_, pI) { switch( octreeVertexType_[pI] ) @@ -291,11 +285,11 @@ void hexMeshExtractor::classifyOctreePoints() } break; }; } - - writeMeshFPMA(pmg, "markedPoints"); + + mesh_.write(); # endif } - + void hexMeshExtractor::createPoints() { clearOut(); @@ -304,8 +298,8 @@ void hexMeshExtractor::createPoints() const meshOctree& octree = octreeAddressing_.octree(); const VRWGraph& nodeLabels = octreeAddressing_.nodeLabels(); const FRWGraph<label, 8>& nodeLeaves = octreeAddressing_.nodeLeaves(); - centreNodeLabelPtr_ = new labelListPMG(boxType.size(), -1); - labelListPMG& centreNode = *centreNodeLabelPtr_; + centreNodeLabelPtr_ = new labelLongList(boxType.size(), -1); + labelLongList& centreNode = *centreNodeLabelPtr_; subVerticesPtr_ = new VRWGraph(boxType.size()); VRWGraph& subVertices = *subVerticesPtr_; @@ -324,23 +318,23 @@ void hexMeshExtractor::createPoints() forAllRow(nodeLabels, leafI, nI) { const label nodeI = nodeLabels(leafI, nI); - + //- find the maximum level of octree cubes at this node direction maxLevel(0); - + forAllRow(nodeLeaves, nodeI, i) { const label leafLabel = nodeLeaves(nodeI, i); - + if( leafLabel < 0 ) continue; - + const meshOctreeCubeBasic& oc = octree.returnLeaf(leafLabel); - + maxLevel = Foam::max(maxLevel, oc.level()); } - + if( maxLevel != octree.returnLeaf(leafI).level() ) { if( subVertices.sizeOfRow(leafI) == 0 ) @@ -349,20 +343,20 @@ void hexMeshExtractor::createPoints() for(label i=0;i<8;++i) subVertices(leafI, i) = -1; } - + if( octreeVertexType_[nodeI] & NOSUBVERTICES ) continue; - + subVertices(leafI, nI) = nPoints++; } } } } - + //- set the number of points pointFieldPMG& points = mesh_.points(); points.setSize(nPoints); - + //- create points forAll(centreNode, leafI) { @@ -371,19 +365,19 @@ void hexMeshExtractor::createPoints() //- create centre node points[centreNode[leafI]] = octree.returnLeaf(leafI).centre(rootBox); - + forAllRow(subVertices, leafI, i) { const label svI = subVertices(leafI, i); - + if( svI < 0 ) continue; - + //- create the subvertex const meshOctreeCubeCoordinates cc = octree.returnLeaf(leafI).refineForPosition(i); points[svI] = cc.centre(rootBox); - + if( octreeVertexType_[nodeLabels(leafI, i)] & FACECENTRE ) { const label* pFaces = @@ -397,11 +391,11 @@ void hexMeshExtractor::createPoints() pFaces[j], neighs ); - + if( neighs.size() == 4 ) { const scalar disp = 0.5 * cc.size(rootBox); - + switch( pFaces[j] ) { case 0: @@ -435,10 +429,10 @@ void hexMeshExtractor::createPoints() } } } - + # ifdef DEBUGHex polyMeshGen pmg(mesh_.returnTime()); - + const FixedList<Vector<label>, 8>& octantVectors = octree.octantVectors(); polyMeshGenModifier meshModifier(pmg); const label centID = pmg.addCellSubset("centrePoints"); @@ -447,86 +441,86 @@ void hexMeshExtractor::createPoints() { if( centreNode[leafI] < 0 ) continue; - + const scalar s = 0.1 * octree.returnLeaf(leafI).size(rootBox); const point cent = octree.returnLeaf(leafI).centre(rootBox); label nPoints = pmg.points().size(); label nFaces = pmg.faces().size(); label nCells = pmg.cells().size(); - + forAll(octree.octantVectors(), ovI) { point p; for(direction i=0;i<Vector<label>::nComponents;++i) p[i] = cent[i] + s * octantVectors[ovI][i]; - + meshModifier.pointsAccess().append(p); } - + cell c(6); - + forAll(c, fI) { face f(4); const label* fNodes = meshOctreeCubeCoordinates::faceNodes_[fI]; - + forAll(f, pI) f[pI] = nPoints + fNodes[pI]; - + meshModifier.facesAccess().append(f); c[fI] = nFaces + fI; } - + meshModifier.cellsAccess().append(c); pmg.addCellToSubset(centID, nCells); - + forAllRow(subVertices, leafI, svI) { const label pI = subVertices(leafI, svI); - + if( pI < 0 ) continue; - + // add vertices nPoints = pmg.points().size(); nFaces = pmg.faces().size(); nCells = pmg.cells().size(); - + const meshOctreeCubeCoordinates cc = octree.returnLeaf(leafI).refineForPosition(svI); const scalar s = 0.1 * cc.size(rootBox); const point cent = cc.centre(rootBox); - + forAll(octree.octantVectors(), ovI) { point p; for(direction i=0;i<Vector<label>::nComponents;++i) p[i] = cent[i] + s * octantVectors[ovI][i]; - + meshModifier.pointsAccess().append(p); } - + cell c(6); - + forAll(c, fI) { face f(4); const label* fNodes = meshOctreeCubeCoordinates::faceNodes_[fI]; - + forAll(f, pI) f[pI] = nPoints + fNodes[pI]; - + meshModifier.facesAccess().append(f); c[fI] = nFaces + fI; } - + meshModifier.cellsAccess().append(c); pmg.addCellToSubset(setID, nCells); } } meshModifier.reorderBoundaryFaces(); - - writeMeshFLMA(pmg, "subVerticesAndCentres"); + + mesh_.write(); # endif } @@ -542,7 +536,7 @@ void hexMeshExtractor::createHexMesh() octreeAddressing_.nodeLabels(), octreeAddressing_.nodeLeaves() ); - + hexCells.generateCells(); } @@ -552,7 +546,7 @@ hexMeshExtractor::createHexCells::createHexCells ( polyMeshGen& mesh, const meshOctree& octree, - const labelListPMG& centreNodeLabel, + const labelLongList& centreNodeLabel, const VRWGraph& subVertices, const List<direction>& octreeVertexType, const VRWGraph& nodeLabels, @@ -586,9 +580,9 @@ void hexMeshExtractor::createHexCells::generateCells() forAll(nodeLeaves_, nodeI) { createFaceCentreHexes(nodeI); - + createHexesAtOctreePoints(nodeI); - + createEdgeHexes(nodeI); } } diff --git a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorI.H b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorI.H index 5d91f754af854b520e0cb62d98719b8a3f5ea01a..419f274288162d525d691f3b9a9982f6ea2c2f19 100644 --- a/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorI.H +++ b/meshLibrary/hexMesh/hexMeshExtractor/hexMeshExtractorI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.C b/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.C index 71fac0983aa0b8558883300629ad0a63c3a9c1f2..81ed4b96d54f243f3412c233b595981fda32eb2c 100644 --- a/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.C +++ b/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -44,14 +43,10 @@ Description #include "boundaryLayers.H" #include "renameBoundaryPatches.H" #include "checkMeshDict.H" +#include "triSurfacePatchManipulator.H" +#include "refineBoundaryLayers.H" //#define DEBUG -//#define DEBUGflma - -# ifdef DEBUG -#include "writeMeshEnsight.H" -#include "writeMeshFLMA.H" -# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -64,7 +59,7 @@ void hexMeshGenerator::generateOctree() { if( !octreePtr_ ) octreePtr_ = new meshOctree(*surfacePtr_); - + meshOctreeCreator creator(*octreePtr_, meshDict_); creator.activateHexRefinement(); creator.createOctreeBoxes(); @@ -78,11 +73,6 @@ void hexMeshGenerator::generateDualMesh() # ifdef DEBUG mesh_.write(); - # ifdef DEBUGflma - writeMeshFLMA(mesh_, "hexMesh"); - # else - writeMeshEnsight(mesh_, "hexMesh"); - # endif //::exit(EXIT_FAILURE); # endif } @@ -100,25 +90,20 @@ void hexMeshGenerator::surfacePreparation() checkIrregularSurfaceConnections checkConnections(mesh_); if( checkConnections.checkAndFixIrregularConnections() ) changed = true; - + if( checkNonMappableCellConnections(mesh_).removeCells() ) changed = true; - + if( checkCellConnectionsOverFaces(mesh_).checkCellGroups() ) changed = true; - } while( changed ); + } while( changed ); # ifdef DEBUG mesh_.write(); - # ifdef DEBUGflma - writeMeshFLMA(mesh_, "afterTopoCleaning"); - # else - writeMeshEnsight(mesh_, "afterTopoCleaning"); - # endif //::exit(EXIT_FAILURE); # endif } - + void hexMeshGenerator::mapMeshToSurface() { //- calculate mesh surface @@ -130,41 +115,25 @@ void hexMeshGenerator::mapMeshToSurface() mapper.mapVerticesOntoSurface(); # ifdef DEBUG - # ifdef DEBUGflma - writeMeshFLMA(mesh_, "afterMapping"); - # else - writeMeshEnsight(mesh_, "afterMapping"); - # endif mesh_.write(); //::exit(EXIT_FAILURE); # endif //- untangle surface faces - meshSurfaceOptimizer(*msePtr, *octreePtr_).preOptimizeSurface(); + meshSurfaceOptimizer(*msePtr, *octreePtr_).untangleSurface(); # ifdef DEBUG - //meshOptimizer(*octreePtr_, mesh_).preOptimize(); - # ifdef DEBUGflma - writeMeshFLMA(mesh_, "afterSurfaceSmoothing"); - # else - writeMeshEnsight(mesh_, "afterSurfaceSmoothing"); - # endif mesh_.write(); //::exit(EXIT_FAILURE); # endif - + deleteDemandDrivenData(msePtr); //- extract edges and corners meshSurfaceEdgeExtractorFUN(mesh_, *octreePtr_); - + # ifdef DEBUG mesh_.write(); - # ifdef DEBUGflma - writeMeshFLMA(mesh_, "withEdges"); - # else - writeMeshEnsight(mesh_, "withEdges"); - #endif //::exit(EXIT_FAILURE); # endif } @@ -173,44 +142,41 @@ void hexMeshGenerator::optimiseMeshSurface() { meshSurfaceEngine mse(mesh_); meshSurfaceOptimizer(mse, *octreePtr_).optimizeSurface(); - + # ifdef DEBUG mesh_.write(); - # ifdef DEBUGflma - writeMeshFLMA(mesh_, "optSurfaceWithEdges"); - # else - writeMeshEnsight(mesh_, "optSurfaceWithEdges"); - #endif + //::exit(0); # endif } - + void hexMeshGenerator::generateBoundaryLayers() { boundaryLayers bl(mesh_); - - if( meshDict_.found("boundaryLayers") ) - { - wordList createLayers(meshDict_.lookup("boundaryLayers")); - - forAll(createLayers, patchI) - bl.addLayerForPatch(createLayers[patchI]); - } - else - { - //bl.createOTopologyLayers(); - bl.addLayerForAllPatches(); - } + + bl.addLayerForAllPatches(); # ifdef DEBUG - # ifdef DEBUGflma - writeMeshFLMA(mesh_, "meshWithBndLayer"); - # else - writeMeshEnsight(mesh_, "meshWithBndLayer"); - # endif mesh_.write(); + //::exit(0); # endif } - + +void hexMeshGenerator::refBoundaryLayers() +{ + if( meshDict_.isDict("boundaryLayers") ) + { + refineBoundaryLayers refLayers(mesh_); + + refineBoundaryLayers::readSettings(meshDict_, refLayers); + + refLayers.refineLayers(); + + meshOptimizer optimizer(mesh_); + + optimizer.untangleMeshFV(); + } +} + void hexMeshGenerator::optimiseFinalMesh() { //- final optimisation @@ -221,39 +187,30 @@ void hexMeshGenerator::optimiseFinalMesh() deleteDemandDrivenData(octreePtr_); optimizer.optimizeMeshFV(); - + # ifdef DEBUG - # ifdef DEBUGflma - writeMeshFLMA(mesh_,"optimisedMesh"); - # else - writeMeshEnsight(mesh_, "optimisedMesh"); - #endif + mesh_.write(); + //::exit(0); # endif } void hexMeshGenerator::replaceBoundaries() { renameBoundaryPatches rbp(mesh_, meshDict_); - + # ifdef DEBUG - # ifdef DEBUGflma - writeMeshFLMA(mesh_,"renamedPatchesMesh"); - # else - writeMeshEnsight(mesh_, "renamedPatchesMesh"); - #endif + mesh_.write(); + //::exit(0); # endif } void hexMeshGenerator::renumberMesh() { polyMeshGenModifier(mesh_).renumberMesh(); - + # ifdef DEBUG - # ifdef DEBUGflma - writeMeshFLMA(mesh_,"renumberedMesh"); - # else - writeMeshEnsight(mesh_, "renumberedMesh"); - #endif + mesh_.write(); + //::exit(0); # endif } @@ -266,7 +223,7 @@ void hexMeshGenerator::generateMesh() mapMeshToSurface(); optimiseMeshSurface(); - + generateBoundaryLayers(); optimiseFinalMesh(); @@ -304,22 +261,30 @@ hexMeshGenerator::hexMeshGenerator { FatalError << "Cannot run in parallel" << exit(FatalError); } - + if( true ) checkMeshDict cmd(meshDict_); - + const fileName surfaceFile = meshDict_.lookup("surfaceFile"); surfacePtr_ = new triSurf(runTime_.path()/surfaceFile); - - if( meshDict_.found("subsetFileName") ) + + if( surfacePtr_->featureEdges().size() != 0 ) { - const fileName subsetFileName = meshDict_.lookup("subsetFileName"); - surfacePtr_->readFaceSubsets(runTime_.path()/subsetFileName); + //- create surface patches based on the feature edges + //- and update the meshDict based on the given data + triSurfacePatchManipulator manipulator(*surfacePtr_); + + const triSurf* surfaceWithPatches = + manipulator.surfaceWithPatches(&meshDict_); + + //- delete the old surface and assign the new one + deleteDemandDrivenData(surfacePtr_); + surfacePtr_ = surfaceWithPatches; } - + generateOctree(); - + generateMesh(); } @@ -344,7 +309,7 @@ hexMeshGenerator::hexMeshGenerator ) ), octreePtr_(NULL), - mesh_(time) + mesh_(time) { fileName surfaceFile = meshDict_.lookup("surfaceFile"); diff --git a/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.H b/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.H index 29f680be810d236837efa7e220331c6dd519209d..0557ff7cf25c81a06a08755bdd0201bf2f62def3 100644 --- a/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.H +++ b/meshLibrary/hexMesh/hexMeshGenerator/hexMeshGenerator.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class hexMeshGenerator @@ -61,45 +60,48 @@ class hexMeshGenerator const Time& runTime_; //- pointer to the surface - triSurf* surfacePtr_; + const triSurf* surfacePtr_; //- IOdictionary containing information about cell sizes, etc.. IOdictionary meshDict_; //- pointer to the octree meshOctree* octreePtr_; - - //- mesh - polyMeshGen mesh_; + + //- mesh + polyMeshGen mesh_; // Private member functions //- generate octree based on user's refinement settings void generateOctree(); - - //- generate dual mesh - void generateDualMesh(); - - //- prepare mesh surface - void surfacePreparation(); - - //- map mesh to the surface and untangle surface - void mapMeshToSurface(); - - //- optimise surface of the mesh - void optimiseMeshSurface(); - - //- add boundary layers - void generateBoundaryLayers(); - - //- mesh optimisation - void optimiseFinalMesh(); - + + //- generate dual mesh + void generateDualMesh(); + + //- prepare mesh surface + void surfacePreparation(); + + //- map mesh to the surface and untangle surface + void mapMeshToSurface(); + + //- optimise surface of the mesh + void optimiseMeshSurface(); + + //- add boundary layers + void generateBoundaryLayers(); + + //- mesh optimisation + void optimiseFinalMesh(); + + //- refine boundary layers + void refBoundaryLayers(); + //- replace boundaries void replaceBoundaries(); - - //- renumber the mesh - void renumberMesh(); - + + //- renumber the mesh + void renumberMesh(); + //- generate mesh void generateMesh(); diff --git a/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.C b/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.C index e00f53afab5278dc3508bab81fcba8bcbd8a1169..98791ea27fb60f881a8415883a7032f7ddb449f6 100644 --- a/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.C +++ b/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.H b/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.H index 4384e213dce07c3d2ca86bc6c3dc226bd0f6d058..30f8a51f3d3cccd947a3ffbffe82f5418a9d58a2 100644 --- a/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.H +++ b/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractor.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class tetMeshExtractor diff --git a/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractorPointsAndCells.C b/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractorPointsAndCells.C index f240f23568bc95cd9ff5442d2ef7676c8ff24e0f..2249a5d06057cda8c6d4929ff4271a6582f9b409 100644 --- a/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractorPointsAndCells.C +++ b/meshLibrary/tetMesh/tetMeshExtractor/tetMeshExtractorPointsAndCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.C b/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.C index d58ac5990347d8aa0a408bc4477f40ec1c17a6d9..a34b37a0f898e6a3dac5480b2c49a84f1e6d2e44 100644 --- a/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.C +++ b/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -34,7 +33,9 @@ Description #include "tessellationDimSpace.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif // #define DEBUGTets @@ -52,11 +53,13 @@ void tetMeshExtractorOctree::createPoints() const LongList<point>& tetPoints = tetCreator_.tetPoints(); - points.setSize ( tetPoints.size() ); + points.setSize(tetPoints.size()); -# pragma omp parallel for - forAll ( tetPoints, pointI ) - points[pointI] = tetPoints[pointI]; + # ifdef USE_OMP + # pragma omp parallel for + # endif + forAll(tetPoints, pointI) + points[pointI] = tetPoints[pointI]; } void tetMeshExtractorOctree::createPolyMesh() @@ -71,41 +74,47 @@ void tetMeshExtractorOctree::createPolyMesh() const LongList<partTet>& tets = tetCreator_.tets(); VRWGraph pTets; - pTets.reverseAddressing ( mesh_.points().size(), tets ); + pTets.reverseAddressing(mesh_.points().size(), tets); //- set the number of cells - cells.setSize ( tets.size() ); + cells.setSize(tets.size()); //- all faces of tetrahedral cells - faces.setSize ( 4*tets.size() ); - boolList removeFace ( faces.size() ); + faces.setSize(4*tets.size()); + boolList removeFace(faces.size()); -# pragma omp parallel if( tets.size() > 1000 ) + # ifdef USE_OMP + # pragma omp parallel if( tets.size() > 1000 ) + # endif { //- set face labels -# pragma omp for - forAll ( removeFace, faceI ) - removeFace[faceI] = false; + # ifdef USE_OMP + # pragma omp for + # endif + forAll(removeFace, faceI) + removeFace[faceI] = false; //- set sizes of cells and create all faces -# pragma omp for schedule(dynamic, 20) - forAll ( tets, elmtI ) + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 20) + # endif + forAll(tets, elmtI) { - cells[elmtI].setSize ( 4 ); + cells[elmtI].setSize(4); const partTet& elmt = tets[elmtI]; - tessellationElement telmt ( elmt[0], elmt[1], elmt[2], elmt[3] ); + tessellationElement telmt(elmt[0], elmt[1], elmt[2], elmt[3]); label faceI = 4 * elmtI; - for ( label i=0;i<4;++i ) + for(label i=0;i<4;++i) { cells[elmtI][i] = faceI; face& f = faces[faceI]; f.setSize ( 3 ); - const triFace tf = telmt.face ( i ); + const triFace tf = telmt.face(i); f[0] = tf[0]; f[1] = tf[2]; f[2] = tf[1]; @@ -114,38 +123,42 @@ void tetMeshExtractorOctree::createPolyMesh() } } -# pragma omp barrier + # ifdef USE_OMP + # pragma omp barrier + # endif //- find duplicate faces -# pragma omp for schedule(dynamic, 20) - forAll ( cells, cellI ) + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 20) + # endif + forAll(cells, cellI) { cell& c = cells[cellI]; - forAll ( c, fI ) + forAll(c, fI) { const face& f = faces[c[fI]]; const label pointI = f[0]; - forAllRow ( pTets, pointI, ptI ) + forAllRow(pTets, pointI, ptI) { //- do not check cells with greater labels //- they cannot be face owners - if ( pTets ( pointI, ptI ) >= cellI ) + if( pTets(pointI, ptI) >= cellI ) continue; - const cell& otherTet = cells[pTets ( pointI, ptI ) ]; + const cell& otherTet = cells[pTets(pointI, ptI)]; //- check faces created from a tet - forAll ( otherTet, ofI ) + forAll(otherTet, ofI) { //- do not compare faces with greater labels //- they shall not be removed here - if ( otherTet[ofI] >= c[fI] ) + if( otherTet[ofI] >= c[fI] ) continue; //- check if the faces are equal - if ( f == faces[otherTet[ofI]] ) + if( f == faces[otherTet[ofI]] ) { removeFace[c[fI]] = true; c[fI] = otherTet[ofI]; @@ -157,15 +170,15 @@ void tetMeshExtractorOctree::createPolyMesh() } //- remove duplicate faces - label nFaces ( 0 ); - labelListPMG newFaceLabel ( faces.size(), -1 ); + label nFaces(0); + labelLongList newFaceLabel(faces.size(), -1); - forAll ( faces, faceI ) + forAll(faces, faceI) { - if ( !removeFace[faceI] ) + if( !removeFace[faceI] ) { - if ( nFaces < faceI ) - faces[nFaces].transfer ( faces[faceI] ); + if( nFaces < faceI ) + faces[nFaces].transfer(faces[faceI]); newFaceLabel[faceI] = nFaces; ++nFaces; @@ -173,24 +186,26 @@ void tetMeshExtractorOctree::createPolyMesh() } //- set the size of faces - faces.setSize ( nFaces ); + faces.setSize(nFaces); //- change cells -# pragma omp for schedule(dynamic, 40) - forAll ( cells, cellI ) + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(cells, cellI) { cell& c = cells[cellI]; DynList<label> newC; - forAll ( c, fI ) + forAll(c, fI) { - if ( newFaceLabel[c[fI]] != -1 ) - newC.append ( newFaceLabel[c[fI]] ); + if( newFaceLabel[c[fI]] != -1 ) + newC.append(newFaceLabel[c[fI]]); } - c.setSize ( newC.size() ); - forAll ( c, fI ) + c.setSize(newC.size()); + forAll(c, fI) c[fI] = newC[fI]; } } @@ -204,17 +219,15 @@ tetMeshExtractorOctree::tetMeshExtractorOctree const IOdictionary& meshDict, polyMeshGen& mesh ) - : - tetCreator_ ( octree, meshDict ), - mesh_ ( mesh ) -{ -} +: + tetCreator_(octree, meshDict), + mesh_(mesh) +{} // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // tetMeshExtractorOctree::~tetMeshExtractorOctree() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -228,8 +241,8 @@ void tetMeshExtractorOctree::createMesh() //- create the mesh createPolyMesh(); - polyMeshGenModifier ( mesh_ ).reorderBoundaryFaces(); - polyMeshGenModifier ( mesh_ ).removeUnusedVertices(); + polyMeshGenModifier(mesh_).reorderBoundaryFaces(); + polyMeshGenModifier(mesh_).removeUnusedVertices(); Info << "Mesh has :" << nl << mesh_.points().size() << " vertices " << nl diff --git a/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.H b/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.H index 2e54148ec1f6ae7d8b4b7adc4e58b74990588d08..cb70ffbc5851826ace991a94b118b20564f5099b 100644 --- a/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.H +++ b/meshLibrary/tetMesh/tetMeshExtractorOctree/tetMeshExtractorOctree.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class tetMeshExtractorOctree diff --git a/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.C b/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.C index 988b39dcfd3d0329403df980e7f7f8f71e8b9098..10abdbe76d5b8c7ef653ab4b2c9ec81eafe89eb9 100644 --- a/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.C +++ b/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -45,14 +44,11 @@ Description #include "boundaryLayers.H" #include "renameBoundaryPatches.H" #include "checkMeshDict.H" +#include "triSurfacePatchManipulator.H" +#include "refineBoundaryLayers.H" +#include "triSurfaceMetaData.H" //#define DEBUG -//#define DEBUGfpma - -# ifdef DEBUG -#include "writeMeshEnsight.H" -#include "writeMeshFPMA.H" -# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -64,19 +60,14 @@ namespace Foam void tetMeshGenerator::createTetMesh() { //- create tet Mesh from octree and Delaunay tets - tetMeshExtractorOctree tme ( *octreePtr_, meshDict_, mesh_ ); + tetMeshExtractorOctree tme(*octreePtr_, meshDict_, mesh_); tme.createMesh(); -# ifdef DEBUG + # ifdef DEBUG mesh_.write(); -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_, "tetMesh" ); -# else - writeMeshEnsight ( mesh_, "tetMesh" ); -# endif - ::exit ( EXIT_FAILURE ); -# endif + //::exit(0); + # endif } void tetMeshGenerator::surfacePreparation() @@ -86,150 +77,148 @@ void tetMeshGenerator::surfacePreparation() //- It also checks topology of cells after morphing is performed do { - surfaceMorpherCells* cmPtr = new surfaceMorpherCells ( mesh_ ); + surfaceMorpherCells* cmPtr = new surfaceMorpherCells(mesh_); cmPtr->morphMesh(); - deleteDemandDrivenData ( cmPtr ); + deleteDemandDrivenData(cmPtr); } - while ( topologicalCleaner ( mesh_ ).cleanTopology() ); + while( topologicalCleaner(mesh_).cleanTopology() ); -# ifdef DEBUG + # ifdef DEBUG mesh_.write(); -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_, "afterTopoCleaning" ); -# else - writeMeshEnsight ( mesh_, "afterTopoCleaning" ); -# endif - //::exit(EXIT_FAILURE); -# endif + //::exit(0); + # endif } void tetMeshGenerator::mapMeshToSurface() { //- calculate mesh surface - meshSurfaceEngine* msePtr = new meshSurfaceEngine ( mesh_ ); + meshSurfaceEngine* msePtr = new meshSurfaceEngine(mesh_); //- map mesh surface on the geometry surface - meshSurfaceMapper ( *msePtr, *octreePtr_ ).mapVerticesOntoSurface(); -# ifdef DEBUG -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_, "afterMapping" ); -# else - writeMeshEnsight ( mesh_, "afterMapping" ); -# endif + meshSurfaceMapper(*msePtr, *octreePtr_).mapVerticesOntoSurface(); + + # ifdef DEBUG mesh_.write(); - //::exit(EXIT_FAILURE); -# endif + //::exit(0); + # endif //- untangle surface faces - meshSurfaceOptimizer ( *msePtr, *octreePtr_ ).preOptimizeSurface(); - -# ifdef DEBUG -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_, "afterSurfaceSmoothing" ); -# else - writeMeshEnsight ( mesh_, "afterSurfaceSmoothing" ); -# endif + meshSurfaceOptimizer(*msePtr, *octreePtr_).untangleSurface(); + + # ifdef DEBUG mesh_.write(); - //::exit(EXIT_FAILURE); -# endif - deleteDemandDrivenData ( msePtr ); + //::exit(0); + # endif + + deleteDemandDrivenData(msePtr); } void tetMeshGenerator::mapEdgesAndCorners() { - meshSurfaceEdgeExtractorNonTopo ( mesh_, *octreePtr_ ); + meshSurfaceEdgeExtractorNonTopo(mesh_, *octreePtr_); -# ifdef DEBUG + # ifdef DEBUG mesh_.write(); - //meshOptimizer(*octreePtr_, mesh_).preOptimize(); -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_, "withEdges" ); -# else - writeMeshEnsight ( mesh_, "withEdges" ); -#endif - //::exit(EXIT_FAILURE); -# endif + //::exit(0); + # endif } void tetMeshGenerator::optimiseMeshSurface() { - meshSurfaceEngine mse ( mesh_ ); - meshSurfaceOptimizer ( mse, *octreePtr_ ).optimizeSurface(); + meshSurfaceEngine mse(mesh_); + meshSurfaceOptimizer(mse, *octreePtr_).optimizeSurface(); -# ifdef DEBUG + # ifdef DEBUG mesh_.write(); -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_, "optSurfaceWithEdges" ); -# else - writeMeshEnsight ( mesh_, "optSurfaceWithEdges" ); -#endif - //::exit(EXIT_FAILURE); -# endif + //::exit(0); + # endif } void tetMeshGenerator::generateBoudaryLayers() { - boundaryLayers bl ( mesh_ ); - - if ( meshDict_.found ( "boundaryLayers" ) ) + if( meshDict_.found("boundaryLayers") ) { - wordList createLayers ( meshDict_.lookup ( "boundaryLayers" ) ); - - forAll ( createLayers, patchI ) - bl.addLayerForPatch ( createLayers[patchI] ); + boundaryLayers bl(mesh_); + + const dictionary& bndLayers = meshDict_.subDict("boundaryLayers"); + + if( bndLayers.found("nLayers") ) + { + const label nLayers = readLabel(bndLayers.lookup("nLayers")); + + if( nLayers > 0 ) + bl.addLayerForAllPatches(); + } + else if( bndLayers.found("patchBoundaryLayers") ) + { + const dictionary& patchLayers = + bndLayers.subDict("patchBoundaryLayers"); + const wordList createLayers = patchLayers.toc(); + + forAll(createLayers, patchI) + bl.addLayerForPatch(createLayers[patchI]); + } } -# ifdef DEBUG - writeMeshEnsight ( mesh_, "meshWithBndLayer" ); + # ifdef DEBUG mesh_.write(); - //::exit(EXIT_FAILURE); -# endif + //::exit(0); + # endif } void tetMeshGenerator::optimiseFinalMesh() { //- final optimisation - meshOptimizer optimizer ( mesh_ ); + meshOptimizer optimizer(mesh_); - optimizer.optimizeSurface ( *octreePtr_ ); + optimizer.optimizeSurface(*octreePtr_); - deleteDemandDrivenData ( octreePtr_ ); + deleteDemandDrivenData(octreePtr_); + optimizer.optimizeMeshFV(); + optimizer.optimizeLowQualityFaces(); optimizer.optimizeMeshFV(); -# ifdef DEBUG -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_,"optimisedMesh" ); -# else - writeMeshEnsight ( mesh_, "optimisedMesh" ); -#endif -# endif + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif +} + +void tetMeshGenerator::refBoundaryLayers() +{ + if( meshDict_.isDict("boundaryLayers") ) + { + refineBoundaryLayers refLayers(mesh_); + + refineBoundaryLayers::readSettings(meshDict_, refLayers); + + refLayers.refineLayers(); + + meshOptimizer optimizer(mesh_); + + optimizer.untangleMeshFV(); + } } void tetMeshGenerator::replaceBoundaries() { - renameBoundaryPatches rbp ( mesh_, meshDict_ ); - -# ifdef DEBUG -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_,"renamedPatchesMesh" ); -# else - writeMeshEnsight ( mesh_, "renamedPatchesMesh" ); -#endif -# endif + renameBoundaryPatches rbp(mesh_, meshDict_); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif } void tetMeshGenerator::renumberMesh() { - polyMeshGenModifier ( mesh_ ).renumberMesh(); - -# ifdef DEBUG -# ifdef DEBUGfpma - writeMeshFPMA ( mesh_,"renumberedMesh" ); -# else - writeMeshEnsight ( mesh_, "renumberedMesh" ); -#endif -# endif + polyMeshGenModifier(mesh_).renumberMesh(); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif } void tetMeshGenerator::generateMesh() @@ -248,6 +237,8 @@ void tetMeshGenerator::generateMesh() optimiseFinalMesh(); + refBoundaryLayers(); + renumberMesh(); replaceBoundaries(); @@ -256,55 +247,7 @@ void tetMeshGenerator::generateMesh() // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // Construct from Time -tetMeshGenerator::tetMeshGenerator -( - const Time& time -) - : - runTime_ ( time ), - surfacePtr_ ( NULL ), - meshDict_ - ( - IOobject - ( - "meshDict", - runTime_.system(), - runTime_, - IOobject::MUST_READ, - IOobject::NO_WRITE - ) - ), - octreePtr_ ( NULL ), - mesh_ ( time ) -{ - if ( true ) - { - checkMeshDict cmd ( meshDict_ ); - } - - const fileName surfaceFile = meshDict_.lookup ( "surfaceFile" ); - - surfacePtr_ = new triSurf ( runTime_.path() /surfaceFile ); - - if ( meshDict_.found ( "subsetFileName" ) ) - { - const fileName subsetFileName = meshDict_.lookup ( "subsetFileName" ); - surfacePtr_->readFaceSubsets ( runTime_.path() /subsetFileName ); - } - - octreePtr_ = new meshOctree ( *surfacePtr_ ); - - meshOctreeCreator ( *octreePtr_, meshDict_ ).createOctreeBoxes(); - - generateMesh(); -} - -/* -tetMeshGenerator::tetMeshGenerator -( - const Time& time, - const volScalarField& localCellSize -) +tetMeshGenerator::tetMeshGenerator(const Time& time) : runTime_(time), surfacePtr_(NULL), @@ -313,31 +256,64 @@ tetMeshGenerator::tetMeshGenerator IOobject ( "meshDict", - runTime_.constant(), + runTime_.system(), runTime_, IOobject::MUST_READ, IOobject::NO_WRITE ) ), octreePtr_(NULL), - mesh_(time) + mesh_(time) { - fileName surfaceFile = meshDict_.lookup("surfaceFile"); + if( true ) + { + checkMeshDict cmd(meshDict_); + } + + const fileName surfaceFile = meshDict_.lookup("surfaceFile"); + + surfacePtr_ = new triSurf(runTime_.path()/surfaceFile); + + if( true ) + { + //- save meta data with the mesh (surface mesh + its topology info) + triSurfaceMetaData sMetaData(*surfacePtr_); + const dictionary& surfMetaDict = sMetaData.metaData(); + + mesh_.metaData().add("surfaceFile", surfaceFile); + mesh_.metaData().add("surfaceMeta", surfMetaDict); + } + + if( surfacePtr_->featureEdges().size() != 0 ) + { + //- create surface patches based on the feature edges + //- and update the meshDict based on the given data + triSurfacePatchManipulator manipulator(*surfacePtr_); - surfacePtr_ = new triSurface(runTime_.path()/surfaceFile); + const triSurf* surfaceWithPatches = + manipulator.surfaceWithPatches(&meshDict_); + + //- delete the old surface and assign the new one + deleteDemandDrivenData(surfacePtr_); + surfacePtr_ = surfaceWithPatches; + } octreePtr_ = new meshOctree(*surfacePtr_); + meshOctreeCreator* octreeCreatorPtr = + new meshOctreeCreator(*octreePtr_, meshDict_); + octreeCreatorPtr->createOctreeBoxes(); + deleteDemandDrivenData(octreeCreatorPtr); + generateMesh(); } -*/ // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // tetMeshGenerator::~tetMeshGenerator() { - deleteDemandDrivenData ( surfacePtr_ ); - deleteDemandDrivenData ( octreePtr_ ); + deleteDemandDrivenData(surfacePtr_); + deleteDemandDrivenData(octreePtr_); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.H b/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.H index 0c938724f084b26e07fa030e2bec9b8a2263c472..3a27d4ff128bb8c5878c5f3f9fc9c696410c12f1 100644 --- a/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.H +++ b/meshLibrary/tetMesh/tetMeshGenerator/tetMeshGenerator.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class tetMeshGenerator @@ -57,77 +56,77 @@ class Time; class tetMeshGenerator { // Private data - //- reference to Time - const Time& runTime_; + //- reference to Time + const Time& runTime_; - //- pointer to the surface - triSurf* surfacePtr_; + //- pointer to the surface + const triSurf* surfacePtr_; - //- IOdictionary containing information about cell sizes, etc.. - IOdictionary meshDict_; + //- IOdictionary containing information about cell sizes, etc.. + IOdictionary meshDict_; - //- pointer to the octree - meshOctree* octreePtr_; + //- pointer to the octree + meshOctree* octreePtr_; - //- mesh - polyMeshGen mesh_; + //- mesh + polyMeshGen mesh_; // Private member functions - //- create cartesian mesh - void createTetMesh(); + //- create cartesian mesh + void createTetMesh(); - //- prepare mesh surface - void surfacePreparation(); + //- prepare mesh surface + void surfacePreparation(); - //- map mesh to the surface and untangle surface - void mapMeshToSurface(); + //- map mesh to the surface and untangle surface + void mapMeshToSurface(); - //- capture edges and corners - void mapEdgesAndCorners(); + //- capture edges and corners + void mapEdgesAndCorners(); - //- optimise surface mesh - void optimiseMeshSurface(); + //- optimise surface mesh + void optimiseMeshSurface(); - //- add boundary layers - void generateBoudaryLayers(); + //- add boundary layers + void generateBoudaryLayers(); - //- mesh optimisation - void optimiseFinalMesh(); + //- mesh optimisation + void optimiseFinalMesh(); - //- replace boundaries - void replaceBoundaries(); + //- refine boundary layers + void refBoundaryLayers(); - //- renumber the mesh - void renumberMesh(); + //- replace boundaries + void replaceBoundaries(); - //- generate mesh - void generateMesh(); + //- renumber the mesh + void renumberMesh(); - //- Disallow default bitwise copy construct - tetMeshGenerator ( const tetMeshGenerator& ); + //- generate mesh + void generateMesh(); - //- Disallow default bitwise assignment - void operator= ( const tetMeshGenerator& ); + //- Disallow default bitwise copy construct + tetMeshGenerator(const tetMeshGenerator&); + + //- Disallow default bitwise assignment + void operator=(const tetMeshGenerator&); public: // Constructors - //- Construct from time - tetMeshGenerator ( const Time& ); - - //- Construct from time and desired cell size - //tetMeshGenerator(const Time&, const volScalarField&); + //- Construct from time + tetMeshGenerator(const Time&); // Destructor - ~tetMeshGenerator(); + ~tetMeshGenerator(); // Member Functions - //- write the mesh - void writeMesh() const; + //- write the mesh + void writeMesh() const; }; diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayerCells.C b/meshLibrary/utilities/boundaryLayers/boundaryLayerCells.C index 9071bdbeb7b027893ba59af5eee5be268ace6998..c9e20e166de0fe4e84e20e12862ffc6a9dae39d9 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayerCells.C +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayerCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -53,92 +52,100 @@ namespace Foam void boundaryLayers::createLayerCells(const labelList& patchLabels) { - Info << "Starting creating layer cells" << endl; - + Info << "Starting creating layer cells" << endl; + const meshSurfaceEngine& mse = surfaceEngine(); - const faceList::subList& bFaces = mse.boundaryFaces(); - const VRWGraph& faceEdges = mse.faceEdges(); - const VRWGraph& edgeFaces = mse.edgeFaces(); - const labelList& boundaryFacePatches = mse.boundaryFacePatches(); - const labelList& faceOwners = mse.faceOwners(); - - boolList treatPatches(mesh_.boundaries().size(), false); - forAll(patchLabels, patchI) - { - const label pLabel = patchLabels[patchI]; - forAll(treatPatchesWithPatch_[pLabel], i) - treatPatches[treatPatchesWithPatch_[pLabel][i]] = true; - } - - //- create new faces at parallel boundaries - const Map<label>* otherProcPatchPtr(NULL); - const Map<label>* otherFaceProcPtr(NULL); - + const faceList::subList& bFaces = mse.boundaryFaces(); + const edgeList& edges = mse.edges(); + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const labelList& boundaryFacePatches = mse.boundaryFacePatches(); + const labelList& faceOwners = mse.faceOwners(); + const labelList& bp = mse.bp(); + const VRWGraph& pointFaces = mse.pointFaces(); + + const meshSurfacePartitioner& mPart = surfacePartitioner(); + const VRWGraph& pointPatches = mPart.pointPatches(); + + //- mark patches which will be extruded into layer cells + boolList treatPatches(mesh_.boundaries().size(), false); + forAll(patchLabels, patchI) + { + const label pLabel = patchLabels[patchI]; + forAll(treatPatchesWithPatch_[pLabel], i) + treatPatches[treatPatchesWithPatch_[pLabel][i]] = true; + } + + //- create new faces at parallel boundaries + const Map<label>* otherProcPatchPtr(NULL); + const Map<label>* otherFaceProcPtr(NULL); + if( Pstream::parRun() ) { createNewFacesParallel(treatPatches); - + otherProcPatchPtr = &mse.otherEdgeFacePatch(); otherFaceProcPtr = &mse.otherEdgeFaceAtProc(); } - - //- create lists for new boundary faces - VRWGraph newBoundaryFaces; - labelListPMG newBoundaryOwners; - labelListPMG newBoundaryPatches; - + + //- create lists for new boundary faces + VRWGraph newBoundaryFaces; + labelLongList newBoundaryOwners; + labelLongList newBoundaryPatches; + //- create storage for new cells - VRWGraphList cellsToAdd; - - //- create layer cells and store boundary faces - const label nOldCells = mesh_.cells().size(); - forAll(bFaces, bfI) - if( treatPatches[boundaryFacePatches[bfI]] ) - { - const face& f = bFaces[bfI]; - const label pKey = patchKey_[boundaryFacePatches[bfI]]; - - DynList<DynList<label> > cellFaces; - + VRWGraphList cellsToAdd; + + //- create layer cells and store boundary faces + const label nOldCells = mesh_.cells().size(); + forAll(bFaces, bfI) + { + if( treatPatches[boundaryFacePatches[bfI]] ) + { + const face& f = bFaces[bfI]; + const label pKey = patchKey_[boundaryFacePatches[bfI]]; + + DynList<DynList<label> > cellFaces; + DynList<label> newF; - //- store boundary face + + //- store the current boundary face newF.clear(); newF.append(f[0]); for(label pI=f.size()-1;pI>0;--pI) newF.append(f[pI]); - cellFaces.append(newF); - - //- create parallel face - newF.clear(); - forAll(f, pI) - newF.append(findNewNodeLabel(f[pI], pKey)); - - cellFaces.append(newF); - - newBoundaryFaces.appendList(newF); - newBoundaryOwners.append(cellsToAdd.size() + nOldCells); - newBoundaryPatches.append(boundaryFacePatches[bfI]); - - //- create quad faces - newF.setSize(4); - forAll(f, pI) - { - newF[0] = f[pI]; - newF[1] = f.nextLabel(pI); - newF[2] = findNewNodeLabel(newF[1], pKey); - newF[3] = findNewNodeLabel(f[pI], pKey); - - cellFaces.append(newF); - - //- check if the face is at the boundary + cellFaces.append(newF); + + //- create parallel face + forAll(f, pI) + newF[pI] = findNewNodeLabel(f[pI], pKey); + + cellFaces.append(newF); + + newBoundaryFaces.appendList(newF); + newBoundaryOwners.append(cellsToAdd.size() + nOldCells); + newBoundaryPatches.append(boundaryFacePatches[bfI]); + + //- create quad faces + newF.setSize(4); + forAll(f, pI) + { + newF[0] = f[pI]; + newF[1] = f.nextLabel(pI); + newF[2] = findNewNodeLabel(newF[1], pKey); + newF[3] = findNewNodeLabel(f[pI], pKey); + + cellFaces.append(newF); + + //- check if the face is at the boundary //- of the treated partitions - const label edgeI = faceEdges(bfI, pI); + const label edgeI = faceEdges(bfI, pI); if( edgeFaces.sizeOfRow(edgeI) == 2 ) { label neiFace = edgeFaces(edgeI, 0); if( neiFace == bfI ) neiFace = edgeFaces(edgeI, 1); - + if( !treatPatches[boundaryFacePatches[neiFace]] ) { newBoundaryFaces.appendList(newF); @@ -146,228 +153,291 @@ void boundaryLayers::createLayerCells(const labelList& patchLabels) newBoundaryPatches.append(boundaryFacePatches[neiFace]); } } - else if( edgeFaces.sizeOfRow(edgeI) == 1 ) + else if( edgeFaces.sizeOfRow(edgeI) == 1 ) { const Map<label>& otherProcPatch = *otherProcPatchPtr; if( !treatPatches[otherProcPatch[edgeI]] ) { - //- face is a new boundary face + //- face is a new boundary face newBoundaryFaces.appendList(newF); newBoundaryOwners.append(cellsToAdd.size() + nOldCells); newBoundaryPatches.append(otherProcPatch[edgeI]); } } - } - - # ifdef DEBUGLayer - Info << "Adding cell " << cellFaces << endl; - # endif - + } + + # ifdef DEBUGLayer + Info << "Adding cell " << cellFaces << endl; + # endif + cellsToAdd.appendGraph(cellFaces); - } - else - { - # ifdef DEBUGLayer - Info << "Storing original boundary face " - << bfI << " into patch " << boundaryFacePatches[bfI] << endl; - # endif - - newBoundaryFaces.appendList(bFaces[bfI]); - newBoundaryOwners.append(faceOwners[bfI]); - newBoundaryPatches.append(boundaryFacePatches[bfI]); - } - - //- data for parallel execution - boolList procPoint; - LongList<DynList<label, 4> > pointProcFaces; - LongList<labelPair> faceAtPatches; - if( Pstream::parRun() ) - { - procPoint.setSize(nPoints_); - procPoint = false; - + } + else + { + # ifdef DEBUGLayer + Info << "Storing original boundary face " + << bfI << " into patch " << boundaryFacePatches[bfI] << endl; + # endif + + newBoundaryFaces.appendList(bFaces[bfI]); + newBoundaryOwners.append(faceOwners[bfI]); + newBoundaryPatches.append(boundaryFacePatches[bfI]); + } + } + + //- data for parallel execution + boolList procPoint; + LongList<DynList<label, 4> > pointProcFaces; + LongList<labelPair> faceAtPatches; + if( Pstream::parRun() ) + { + procPoint.setSize(nPoints_); + procPoint = false; + const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - const labelList& bPoints = mse.boundaryPoints(); - + const labelList& bPoints = mse.boundaryPoints(); + for ( Map<label>::const_iterator iter=globalToLocal.begin(); iter!=globalToLocal.end(); ++iter ) - { + { const label bpI = iter(); procPoint[bPoints[bpI]] = true; - } - } - - //- create cells at edges - const edgeList& edges = mse.edges(); - forAll(edgeFaces, edgeI) - { - //- do not consider edges with no faces attached to it - if( edgeFaces.sizeOfRow(edgeI) == 0 ) - continue; - - //- cells are generated at the processor with the lowest label - if( - (edgeFaces.sizeOfRow(edgeI) == 1) && - (otherFaceProcPtr->operator[](edgeI) < Pstream::myProcNo()) - ) - continue; - - //- check if the edge is a feature edge - const label patchI = boundaryFacePatches[edgeFaces(edgeI, 0)]; - - label patchJ; - if( otherProcPatchPtr && otherProcPatchPtr->found(edgeI) ) - { - patchJ = otherProcPatchPtr->operator[](edgeI); - } - else - { - patchJ = boundaryFacePatches[edgeFaces(edgeI, 1)]; - } - - if( patchI == patchJ ) - continue; - - //- check if the faces attached to the edge have different keys - const label pKeyI = patchKey_[patchI]; - const label pKeyJ = patchKey_[patchJ]; - - if( pKeyI == pKeyJ ) - continue; - - const edge& e = edges[edgeI]; - if( otherVrts_.find(e.start()) == otherVrts_.end() ) - continue; - if( otherVrts_.find(e.end()) == otherVrts_.end() ) - continue; - - DynList<DynList<label, 4>, 6> cellFaces; - createNewCellFromEdge(e, pKeyI, pKeyJ, cellFaces); - - //- store boundary faces - newBoundaryFaces.appendList(cellFaces[1]); - newBoundaryOwners.append(nOldCells+cellsToAdd.size()); - newBoundaryPatches.append(patchJ); - - newBoundaryFaces.appendList(cellFaces[3]); - newBoundaryOwners.append(nOldCells+cellsToAdd.size()); - newBoundaryPatches.append(patchI); - - if( Pstream::parRun() ) - { - if( procPoint[e.start()] ) - { - pointProcFaces.append(cellFaces[5]); - faceAtPatches.append(labelPair(patchI, patchJ)); - } - if( procPoint[e.end()] ) - { - pointProcFaces.append(cellFaces[4]); - faceAtPatches.append(labelPair(patchI, patchJ)); - } - } - - //- append cell to the queue - cellsToAdd.appendGraph(cellFaces); - } - - //- create cells for corner nodes - const VRWGraph& pointFaces = mse.pointFaces(); - const labelList& bp = mse.bp(); - - std::map<label, DynList<label, 3> > nodePatches; - labelHashSet parPoint; - if( Pstream::parRun() ) - { - const labelList& bPoints = mse.boundaryPoints(); - const VRWGraph& pProcs = mse.bpAtProcs(); - const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); - const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - - std::map<label, labelListPMG> facesToSend; - std::map<label, DynList<face, 8> > parPointFaces; - std::map<label, DynList<label, 3> > parPointPatches; - for - ( - std::map< - label, std::map<std::pair<label, label>, label> - >::const_iterator iter=otherVrts_.begin(); - iter!=otherVrts_.end(); - ++iter - ) - { - if( iter->second.size() == 2 ) - continue; - - const label bpI = bp[iter->first]; - - if( pProcs.sizeOfRow(bpI) != 0 ) - { - parPoint.insert(iter->first); - - //- point is at a parallel boundary - label pMin = pProcs(bpI, 0); - forAllRow(pProcs, bpI, i) - { - const label prI = pProcs(bpI, i); - - if( facesToSend.find(prI) == facesToSend.end() ) - facesToSend.insert(std::make_pair(prI, labelListPMG())); - - if( prI < pMin ) - pMin = prI; - } - - if( Pstream::myProcNo() == pMin ) - { - DynList<face, 8> pFaces(3); - DynList<label, 3> pPatches(3); - forAllRow(pointFaces, bpI, fI) - { - const label bfI = pointFaces(bpI, fI); - pPatches.append(boundaryFacePatches[bfI]); - - face bf; - bf.setSize(bFaces[bfI].size()); - forAll(bf, pI) - bf[pI] = globalPointLabel[bp[bf[pI]]]; - pFaces.append(bf); - } - parPointFaces.insert(std::make_pair(bpI, pFaces)); - parPointPatches.insert(std::make_pair(bpI, pPatches)); - continue; - } - - labelListPMG& stp = facesToSend[pMin]; - - //- send the data to the processor with the lowest label - //- data is flatenned as follows - //- 1. the number of faces and global point label - //- 2. number of points in the face - //- 3. patch label - //- 4. global labels of face points - stp.append(globalPointLabel[bpI]); - stp.append(pointFaces.sizeOfRow(bpI)); - forAllRow(pointFaces, bpI, fI) - { - const label bfI = pointFaces(bpI, fI); - const face& bf = bFaces[bfI]; - stp.append(bf.size()); - stp.append(boundaryFacePatches[bfI]); - forAll(bf, pI) - stp.append(globalPointLabel[bf[pI]]); - } - } - } - - //- exchange data with other processors - labelListPMG receivedData; + } + } + + //- create cells at edges + forAll(edgeFaces, edgeI) + { + //- do not consider edges with no faces attached to it + if( edgeFaces.sizeOfRow(edgeI) == 0 ) + continue; + + //- cells are generated at the processor with the lowest label + if( + (edgeFaces.sizeOfRow(edgeI) == 1) && + (otherFaceProcPtr->operator[](edgeI) < Pstream::myProcNo()) + ) + continue; + + //- check if the edge is a feature edge + const label patchI = boundaryFacePatches[edgeFaces(edgeI, 0)]; + + label patchJ; + if( otherProcPatchPtr && otherProcPatchPtr->found(edgeI) ) + { + patchJ = otherProcPatchPtr->operator[](edgeI); + } + else + { + patchJ = boundaryFacePatches[edgeFaces(edgeI, 1)]; + } + + if( patchI == patchJ ) + continue; + + //- check if the faces attached to the edge have different keys + const label pKeyI = patchKey_[patchI]; + const label pKeyJ = patchKey_[patchJ]; + + if( pKeyI == pKeyJ ) + continue; + + const edge& e = edges[edgeI]; + if( otherVrts_.find(e.start()) == otherVrts_.end() ) + continue; + if( otherVrts_.find(e.end()) == otherVrts_.end() ) + continue; + + //- generate faces of the bnd layer cell + FixedList<FixedList<label, 4>, 6> cellFaces; + createNewCellFromEdge(e, pKeyI, pKeyJ, cellFaces); + + //- store boundary faces + newBoundaryFaces.appendList(cellFaces[1]); + newBoundaryOwners.append(nOldCells+cellsToAdd.size()); + newBoundaryPatches.append(patchJ); + + newBoundaryFaces.appendList(cellFaces[3]); + newBoundaryOwners.append(nOldCells+cellsToAdd.size()); + newBoundaryPatches.append(patchI); + + //- check if face 5 is a boundary face or at an inter-processor boundary + const label bps = bp[e.start()]; + label unusedPatch(-1); + forAllRow(pointPatches, bps, i) + { + const label ptchI = pointPatches(bps, i); + + if( ptchI == patchI ) + continue; + if( ptchI == patchJ ) + continue; + if( unusedPatch != -1 ) + { + unusedPatch = -1; + break; + } + + unusedPatch = ptchI; + } + + if( unusedPatch != -1 && treatedPatch_[unusedPatch] ) + { + //- add a face in the empty patch in case of 2D layer generation + newBoundaryFaces.appendList(cellFaces[5]); + newBoundaryOwners.append(nOldCells+cellsToAdd.size()); + newBoundaryPatches.append(unusedPatch); + } + else if( Pstream::parRun() && procPoint[e.start()] ) + { + //- add a face at inter-pocessor boundary + pointProcFaces.append(cellFaces[5]); + faceAtPatches.append(labelPair(patchI, patchJ)); + } + + //- check if face 4 is a boundary face or at an inter-processor boundary + const label bpe = bp[e.end()]; + unusedPatch = -1; + forAllRow(pointPatches, bpe, i) + { + const label ptchI = pointPatches(bpe, i); + + if( ptchI == patchI ) + continue; + if( ptchI == patchJ ) + continue; + if( unusedPatch != -1 ) + { + unusedPatch = -1; + break; + } + + unusedPatch = ptchI; + } + + if( unusedPatch != -1 && treatedPatch_[unusedPatch] ) + { + //- add a face in the empty patch in case of 2D layer generation + newBoundaryFaces.appendList(cellFaces[4]); + newBoundaryOwners.append(nOldCells+cellsToAdd.size()); + newBoundaryPatches.append(unusedPatch); + } + else if( Pstream::parRun() && procPoint[e.end()] ) + { + //- add a face at inter-pocessor boundary + pointProcFaces.append(cellFaces[4]); + faceAtPatches.append(labelPair(patchI, patchJ)); + } + + //- append cell to the queue + cellsToAdd.appendGraph(cellFaces); + } + + //- create cells for corner nodes + typedef std::map<std::pair<label, label>, label> mPairToLabelType; + typedef std::map<label, mPairToLabelType> mPointsType; + typedef std::map<label, DynList<label, 3> > ppType; + + ppType nodePatches; + labelHashSet parPoint; + + if( Pstream::parRun() ) + { + const labelList& bPoints = mse.boundaryPoints(); + const VRWGraph& pProcs = mse.bpAtProcs(); + const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); + const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); + + std::map<label, labelLongList> facesToSend; + + typedef std::map<label, DynList<DynList<label, 8>, 8> > ppfType; + + ppfType parPointFaces; + ppType parPointPatches; + + forAllConstIter(mPointsType, otherVrts_, iter) + { + //- skip points on feature edges + if( iter->second.size() == 2 ) + continue; + + const label bpI = bp[iter->first]; + + if( pProcs.sizeOfRow(bpI) != 0 ) + { + parPoint.insert(iter->first); + + //- point is at a parallel boundary + label pMin = pProcs(bpI, 0); + forAllRow(pProcs, bpI, i) + { + const label prI = pProcs(bpI, i); + + if( facesToSend.find(prI) == facesToSend.end() ) + facesToSend.insert + ( + std::make_pair(prI, labelLongList()) + ); + + if( prI < pMin ) + pMin = prI; + } + + if( Pstream::myProcNo() == pMin ) + { + DynList<label, 3>& pPatches = parPointPatches[bpI]; + pPatches.setSize(pointFaces.sizeOfRow(bpI)); + + DynList<DynList<label, 8>, 8>& pFaces = parPointFaces[bpI]; + pFaces.setSize(pPatches.size()); + + forAllRow(pointFaces, bpI, pfI) + { + const label bfI = pointFaces(bpI, pfI); + const face& bf = bFaces[bfI]; + + pPatches[pfI] = boundaryFacePatches[bfI]; + + DynList<label, 8>& bfCopy = pFaces[pfI]; + bfCopy.setSize(bf.size()); + forAll(bf, pI) + bfCopy[pI] = globalPointLabel[bp[bf[pI]]]; + } + + continue; + } + + labelLongList& stp = facesToSend[pMin]; + + //- send the data to the processor with the lowest label + //- data is flatenned as follows + //- 1. the number of faces and global point label + //- 2. number of points in the face + //- 3. patch label + //- 4. global labels of face points + stp.append(globalPointLabel[bpI]); + stp.append(pointFaces.sizeOfRow(bpI)); + forAllRow(pointFaces, bpI, pfI) + { + const label bfI = pointFaces(bpI, pfI); + const face& bf = bFaces[bfI]; + + stp.append(bf.size()); + stp.append(boundaryFacePatches[bfI]); + forAll(bf, pI) + stp.append(globalPointLabel[bp[bf[pI]]]); + } + } + } + + //- exchange data with other processors + labelLongList receivedData; help::exchangeMap(facesToSend, receivedData); - + label counter(0); while( counter < receivedData.size() ) { @@ -375,274 +445,266 @@ void boundaryLayers::createLayerCells(const labelList& patchLabels) const label nFaces = receivedData[counter++]; for(label fI=0;fI<nFaces;++fI) { - face f(receivedData[counter++]); + DynList<label, 8> f(receivedData[counter++]); parPointPatches[bpI].append(receivedData[counter++]); forAll(f, pI) f[pI] = receivedData[counter++]; parPointFaces[bpI].append(f); } } - - //- sort faces sharing corners at the parallel boundaries - for - ( - std::map<label, DynList<face, 8> >::iterator iter=parPointFaces.begin(); - iter!=parPointFaces.end(); - ++iter - ) - { - DynList<face, 8>& pFaces = iter->second; - DynList<label, 3>& fPatches = parPointPatches[iter->first]; - const label gpI = globalPointLabel[iter->first]; - - for(label i=0;i<pFaces.size();++i) - { - const face& bf = pFaces[i]; - const edge e = bf.faceEdge(bf.which(gpI)); - - for(label j=i+1;j<pFaces.size();++j) - { - const face& obf = pFaces[j]; - if( - (obf.which(e.start()) >= 0) && - (obf.which(e.end()) >= 0) - ) - { - face add; - add.transfer(pFaces[i+1]); - pFaces[i+1].transfer(pFaces[j]); - pFaces[j].transfer(add); - const label pAdd = fPatches[i+1]; - fPatches[i+1] = fPatches[j]; - fPatches[j] = pAdd; - break; - } - } - } - - DynList<label, 3> patchIDs(fPatches.size()); - forAll(fPatches, fpI) - patchIDs.appendIfNotIn(fPatches[fpI]); - - nodePatches.insert(std::make_pair(bPoints[iter->first], patchIDs)); - } - } - - //- sort out vertices at one processor - for - ( - std::map< - label, std::map<std::pair<label, label>, label> - >::const_iterator iter=otherVrts_.begin(); - iter!=otherVrts_.end(); - ++iter - ) - { - if( iter->second.size() == 2 ) - continue; - - if( parPoint.found(iter->first) ) - continue; - - const label bpI = bp[iter->first]; - - //- ensure correct orientation - labelList pFaces(pointFaces.sizeOfRow(bpI)); - forAll(pFaces, fI) - pFaces[fI] = pointFaces(bpI, fI); - - for(label i=0;i<pFaces.size();++i) - { - const face& bf = bFaces[pFaces[i]]; - const edge e = bf.faceEdge(bf.which(iter->first)); - - for(label j=i+1;j<pFaces.size();++j) - { - const face& obf = bFaces[pFaces[j]]; - if( - (obf.which(e.start()) >= 0) && - (obf.which(e.end()) >= 0) - ) - { - const label add = pFaces[i+1]; - pFaces[i+1] = pFaces[j]; - pFaces[j] = add; - break; - } - } - } - - DynList<label, 3> patchIDs; - forAll(pFaces, patchI) - { - patchIDs.appendIfNotIn(boundaryFacePatches[pFaces[patchI]]); - } - - nodePatches.insert(std::make_pair(iter->first, patchIDs)); - } - - //- create layer cells for corner nodes - for - ( - std::map<label, DynList<label, 3> >::iterator iter=nodePatches.begin(); - iter!=nodePatches.end(); - ++iter - ) - { - const DynList<label, 3>& patchIDs = iter->second; - DynList<label, 3> pKeys; - forAll(patchIDs, patchI) - { - pKeys.appendIfNotIn(patchKey_[patchIDs[patchI]]); - } - - if( pKeys.size() != 3 ) - continue; - - DynList<DynList<label, 4>, 6> cellFaces; - createNewCellFromNode(iter->first, pKeys, cellFaces); - - //- store boundary faces - newBoundaryFaces.appendList(cellFaces[1]); - newBoundaryOwners.append(nOldCells+cellsToAdd.size()); - newBoundaryPatches.append(patchIDs[0]); - - newBoundaryFaces.appendList(cellFaces[3]); - newBoundaryOwners.append(nOldCells+cellsToAdd.size()); - newBoundaryPatches.append(patchIDs[1]); - - newBoundaryFaces.appendList(cellFaces[5]); - newBoundaryOwners.append(nOldCells+cellsToAdd.size()); - newBoundaryPatches.append(patchIDs[2]); - - if( Pstream::parRun() ) - { - if( procPoint[iter->first] ) - { - pointProcFaces.append(cellFaces[0]); - faceAtPatches.append(labelPair(patchIDs[1], patchIDs[2])); - - pointProcFaces.append(cellFaces[2]); - faceAtPatches.append(labelPair(patchIDs[0], patchIDs[2])); - - pointProcFaces.append(cellFaces[4]); - faceAtPatches.append(labelPair(patchIDs[0], patchIDs[1])); - } - } - - # ifdef DEBUGLayer - Info << "Adding corner cell " << cellFaces << endl; - # endif - - //- append cell to the queue - cellsToAdd.appendGraph(cellFaces); - } - - if( Pstream::parRun() ) - { - //- create faces at parallel boundaries created from - //- points at parallel boundaries - createNewFacesFromPointsParallel - ( - pointProcFaces, - faceAtPatches - ); - } - + + //- sort faces sharing corners at the parallel boundaries + forAllIter(ppfType, parPointFaces, iter) + { + DynList<DynList<label, 8>, 8>& pFaces = iter->second; + DynList<label, 3>& fPatches = parPointPatches[iter->first]; + const label gpI = globalPointLabel[iter->first]; + + for(label i=0;i<pFaces.size();++i) + { + const DynList<label, 8>& bf = pFaces[i]; + const label pos = bf.containsAtPosition(gpI); + const edge e(bf[pos], bf[bf.fcIndex(pos)]); + + for(label j=i+1;j<pFaces.size();++j) + { + const DynList<label, 8>& obf = pFaces[j]; + if( obf.contains(e.start()) && obf.contains(e.end()) ) + { + DynList<label, 8> add; + add = pFaces[i+1]; + pFaces[i+1] = pFaces[j]; + pFaces[j] = add; + + const label pAdd = fPatches[i+1]; + fPatches[i+1] = fPatches[j]; + fPatches[j] = pAdd; + break; + } + } + } + + DynList<label, 3> patchIDs; + forAll(fPatches, fpI) + patchIDs.appendIfNotIn(fPatches[fpI]); + + nodePatches.insert(std::make_pair(bPoints[iter->first], patchIDs)); + } + } + + //- sort out point which are not at inter-processor boundaries + forAllConstIter(mPointsType, otherVrts_, iter) + { + if( iter->second.size() == 2 ) + continue; + + if( parPoint.found(iter->first) ) + continue; + + const label bpI = bp[iter->first]; + + //- ensure correct orientation + DynList<label> pFaces(pointFaces.sizeOfRow(bpI)); + forAll(pFaces, fI) + pFaces[fI] = pointFaces(bpI, fI); + + for(label i=0;i<pFaces.size();++i) + { + const face& bf = bFaces[pFaces[i]]; + const edge e = bf.faceEdge(bf.which(iter->first)); + + for(label j=i+1;j<pFaces.size();++j) + { + const face& obf = bFaces[pFaces[j]]; + if( + (obf.which(e.start()) >= 0) && + (obf.which(e.end()) >= 0) + ) + { + const label add = pFaces[i+1]; + pFaces[i+1] = pFaces[j]; + pFaces[j] = add; + break; + } + } + } + + DynList<label, 3> patchIDs; + forAll(pFaces, patchI) + { + patchIDs.appendIfNotIn(boundaryFacePatches[pFaces[patchI]]); + } + + nodePatches.insert(std::make_pair(iter->first, patchIDs)); + } + + //- create layer cells for corner nodes + forAllIter(ppType, nodePatches, iter) + { + const DynList<label, 3>& patchIDs = iter->second; + DynList<label, 3> pKeys; + forAll(patchIDs, patchI) + { + const label pKey = patchKey_[patchIDs[patchI]]; + + if( pKey < 0 ) + continue; + + pKeys.appendIfNotIn(pKey); + } + + if( pKeys.size() != 3 ) + continue; + + # ifdef DEBUGLayer + Pout << "Creating corner cell at point " << iter->first << endl; + # endif + + FixedList<FixedList<label, 4>, 6> cellFaces; + createNewCellFromNode(iter->first, pKeys, cellFaces); + + //- store boundary faces + newBoundaryFaces.appendList(cellFaces[1]); + newBoundaryOwners.append(nOldCells+cellsToAdd.size()); + newBoundaryPatches.append(patchIDs[0]); + + newBoundaryFaces.appendList(cellFaces[3]); + newBoundaryOwners.append(nOldCells+cellsToAdd.size()); + newBoundaryPatches.append(patchIDs[1]); + + newBoundaryFaces.appendList(cellFaces[5]); + newBoundaryOwners.append(nOldCells+cellsToAdd.size()); + newBoundaryPatches.append(patchIDs[2]); + + if( Pstream::parRun() ) + { + if( procPoint[iter->first] ) + { + pointProcFaces.append(cellFaces[0]); + faceAtPatches.append(labelPair(patchIDs[1], patchIDs[2])); + + pointProcFaces.append(cellFaces[2]); + faceAtPatches.append(labelPair(patchIDs[0], patchIDs[2])); + + pointProcFaces.append(cellFaces[4]); + faceAtPatches.append(labelPair(patchIDs[0], patchIDs[1])); + } + } + + # ifdef DEBUGLayer + Info << "Adding corner cell " << cellFaces << endl; + # endif + + //- append cell to the queue + cellsToAdd.appendGraph(cellFaces); + } + + if( Pstream::parRun() ) + { + //- create faces at parallel boundaries created from + //- points at parallel boundaries + createNewFacesFromPointsParallel + ( + pointProcFaces, + faceAtPatches + ); + } + //- create mesh modifier - polyMeshGenModifier meshModifier(mesh_); - + polyMeshGenModifier meshModifier(mesh_); + meshModifier.addCells(cellsToAdd); + cellsToAdd.clear(); - meshModifier.reorderBoundaryFaces(); - meshModifier.replaceBoundary - ( - patchNames_, - newBoundaryFaces, - newBoundaryOwners, - newBoundaryPatches - ); + meshModifier.reorderBoundaryFaces(); + meshModifier.replaceBoundary + ( + patchNames_, + newBoundaryFaces, + newBoundaryOwners, + newBoundaryPatches + ); //- delete meshSurfaceEngine this->clearOut(); - # ifdef DEBUGLayer - mesh_.addressingData().checkMesh(true); - # endif + # ifdef DEBUGLayer + mesh_.addressingData().checkMesh(true); + # endif - Info << "Finished creating layer cells" << endl; + Info << "Finished creating layer cells" << endl; } void boundaryLayers::createNewFacesFromPointsParallel ( - const LongList<DynList<label, 4> >& faceCandidates, - const LongList<labelPair>& candidatePatches + const LongList<DynList<label, 4> >& faceCandidates, + const LongList<labelPair>& candidatePatches ) { - const meshSurfaceEngine& mse = this->surfaceEngine(); - const labelList& bPoints = mse.boundaryPoints(); - const labelList& bp = mse.bp(); - const VRWGraph& bpAtProcs = mse.bpAtProcs(); - const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); - const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - - labelList otherFaceProc(faceCandidates.size(), -1); - //- some faces may appear more than once - //- such faces are ordinary internal faces - VRWGraph pointFaceCandidates(nPoints_); - forAll(faceCandidates, fI) - { - forAll(faceCandidates[fI], pI) - pointFaceCandidates.append(faceCandidates[fI][pI], fI); - } - - boolList duplicateFace(faceCandidates.size(), false); - List<labelledPair> pointOfOrigin(faceCandidates.size()); - std::map<labelledPair, label> pointOfOriginToFaceLabel; - forAll(faceCandidates, fI) - { - const DynList<label, 4>& f = faceCandidates[fI]; - - const label pointI = f[0]; - - const labelledPair lp - ( - globalPointLabel[bp[pointI]], - Pair<label> + const meshSurfaceEngine& mse = this->surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const labelList& bp = mse.bp(); + const VRWGraph& bpAtProcs = mse.bpAtProcs(); + const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); + const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); + + labelList otherFaceProc(faceCandidates.size(), -1); + //- some faces may appear more than once + //- such faces are ordinary internal faces + VRWGraph pointFaceCandidates(nPoints_); + forAll(faceCandidates, fI) + { + forAll(faceCandidates[fI], pI) + pointFaceCandidates.append(faceCandidates[fI][pI], fI); + } + + boolList duplicateFace(faceCandidates.size(), false); + List<labelledPair> pointOfOrigin(faceCandidates.size()); + std::map<labelledPair, label> pointOfOriginToFaceLabel; + forAll(faceCandidates, fI) + { + const DynList<label, 4>& f = faceCandidates[fI]; + + const label pointI = f[0]; + + const labelledPair lp + ( + globalPointLabel[bp[pointI]], + Pair<label> ( patchKey_[candidatePatches[fI][0]], patchKey_[candidatePatches[fI][1]] ) - ); - - if( - pointOfOriginToFaceLabel.find(lp) != pointOfOriginToFaceLabel.end() - ) - { - duplicateFace[fI] = true; - pointOfOrigin[fI] = lp; - duplicateFace[pointOfOriginToFaceLabel[lp]] = true; - continue; - } - - pointOfOrigin[fI] = lp; - - pointOfOriginToFaceLabel.insert(std::make_pair(lp, fI)); - } - - //- find the processor patch for each processor boundary face - //- the key of the algorithm is the point from which the face was created - //- by sending the point label and the associated patches, it will be - //- possible to find the other processor containing that face - std::map<label, LongList<labelledPair> > exchangeData; + ); + + if( + pointOfOriginToFaceLabel.find(lp) != pointOfOriginToFaceLabel.end() + ) + { + duplicateFace[fI] = true; + pointOfOrigin[fI] = lp; + duplicateFace[pointOfOriginToFaceLabel[lp]] = true; + continue; + } + + pointOfOrigin[fI] = lp; + + pointOfOriginToFaceLabel.insert(std::make_pair(lp, fI)); + } + + //- find the processor patch for each processor boundary face + //- the key of the algorithm is the point from which the face was created + //- by sending the point label and the associated patches, it will be + //- possible to find the other processor containing that face + std::map<label, LongList<labelledPair> > exchangeData; const DynList<label>& neiProcs = mse.bpNeiProcs(); forAll(neiProcs, procI) { const label neiProcI = neiProcs[procI]; - + if( neiProcI == Pstream::myProcNo() ) continue; - + if( exchangeData.find(neiProcI) == exchangeData.end() ) exchangeData.insert ( @@ -650,108 +712,114 @@ void boundaryLayers::createNewFacesFromPointsParallel ); } - forAll(faceCandidates, fI) - { - if( duplicateFace[fI] ) - continue; - - const label bpI = bp[faceCandidates[fI][0]]; - - forAllRow(bpAtProcs, bpI, procI) - { - const label neiProcNo = bpAtProcs(bpI, procI); - if( neiProcNo == Pstream::myProcNo() ) - continue; - - LongList<labelledPair>& dataToSend = exchangeData[neiProcNo]; - dataToSend.append(pointOfOrigin[fI]); - } - } - - //- exchange the data with other processors + forAll(faceCandidates, fI) + { + if( duplicateFace[fI] ) + continue; + + const label bpI = bp[faceCandidates[fI][0]]; + + forAllRow(bpAtProcs, bpI, procI) + { + const label neiProcNo = bpAtProcs(bpI, procI); + if( neiProcNo == Pstream::myProcNo() ) + continue; + + LongList<labelledPair>& dataToSend = exchangeData[neiProcNo]; + dataToSend.append(pointOfOrigin[fI]); + } + } + + //- exchange the data with other processors std::map<label, List<labelledPair> > receivedMap; help::exchangeMap(exchangeData, receivedMap); exchangeData.clear(); - - for - ( - std::map<label, List<labelledPair> >::const_iterator - iter=receivedMap.begin(); - iter!=receivedMap.end(); - ++iter - ) - { - const List<labelledPair>& receivedData = iter->second; - - forAll(receivedData, i) - { - const labelledPair& lpp = receivedData[i]; - const label gpI = lpp.pairLabel(); - const label pointI = bPoints[globalToLocal[gpI]]; - const labelPair& lp = lpp.pair(); - - forAllRow(pointFaceCandidates, pointI, i) - { - const label fI = pointFaceCandidates(pointI, i); - const DynList<label, 4>& f = faceCandidates[fI]; - - Pair<label> pk + + for + ( + std::map<label, List<labelledPair> >::const_iterator + iter=receivedMap.begin(); + iter!=receivedMap.end(); + ++iter + ) + { + const List<labelledPair>& receivedData = iter->second; + + forAll(receivedData, i) + { + const labelledPair& lpp = receivedData[i]; + const label gpI = lpp.pairLabel(); + const label pointI = bPoints[globalToLocal[gpI]]; + const labelPair& lp = lpp.pair(); + + forAllRow(pointFaceCandidates, pointI, i) + { + const label fI = pointFaceCandidates(pointI, i); + const DynList<label, 4>& f = faceCandidates[fI]; + + const labelPair pk ( patchKey_[candidatePatches[fI][0]], patchKey_[candidatePatches[fI][1]] ); - - if( - (f[0] == pointI) && ((pk == lp) || (pk.reversePair() == lp)) - ) - { - //- found the processor containing other face - otherFaceProc[pointOfOriginToFaceLabel[lpp]] = iter->first; - } - } - } - } + + const labelPair rpk + ( + patchKey_[candidatePatches[fI][1]], + patchKey_[candidatePatches[fI][0]] + ); + + if( + (f[0] == pointI) && ((pk == lp) || (rpk == lp)) + ) + { + //- found the processor containing other face + otherFaceProc[pointOfOriginToFaceLabel[lpp]] = iter->first; + } + } + } + } receivedMap.clear(); - - //- sort the points in ascending order - //- this ensures the correct order of faces at the processor boundaries - sort(pointOfOrigin); - - Map<label> otherProcToProcPatch; + + //- sort the points in ascending order + //- this ensures the correct order of faces at the processor boundaries + sort(pointOfOrigin); + + Map<label> otherProcToProcPatch; forAll(mesh_.procBoundaries(), patchI) { - const writeProcessorPatch& wp = mesh_.procBoundaries()[patchI]; + const processorBoundaryPatch& wp = mesh_.procBoundaries()[patchI]; otherProcToProcPatch.insert(wp.neiProcNo(), patchI); } - - //- store processor faces - VRWGraph newProcFaces; - labelListPMG newProc; - - forAll(pointOfOrigin, i) - { - const label fI = pointOfOriginToFaceLabel[pointOfOrigin[i]]; - - if( duplicateFace[fI] || (otherFaceProc[fI] == -1) ) - continue; - - if( !otherProcToProcPatch.found(otherFaceProc[fI]) ) - { - otherProcToProcPatch.insert - ( - otherFaceProc[fI], - polyMeshGenModifier(mesh_).addProcessorPatch - ( - otherFaceProc[fI] - ) - ); + + //- store processor faces + VRWGraph newProcFaces; + labelLongList newProc; + + forAll(pointOfOrigin, i) + { + const label fI = pointOfOriginToFaceLabel[pointOfOrigin[i]]; + + if( duplicateFace[fI] || (otherFaceProc[fI] == -1) ) + continue; + + if( !otherProcToProcPatch.found(otherFaceProc[fI]) ) + { + otherProcToProcPatch.insert + ( + otherFaceProc[fI], + polyMeshGenModifier(mesh_).addProcessorPatch + ( + otherFaceProc[fI] + ) + ); } - - newProcFaces.appendList(faceCandidates[fI]); - newProc.append(otherProcToProcPatch[otherFaceProc[fI]]); - } - polyMeshGenModifier(mesh_).addProcessorFaces(newProcFaces, newProc); + newProcFaces.appendList(faceCandidates[fI]); + newProc.append(otherProcToProcPatch[otherFaceProc[fI]]); + } + + polyMeshGenModifier(mesh_).addProcessorFaces(newProcFaces, newProc); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayers.C b/meshLibrary/utilities/boundaryLayers/boundaryLayers.C index 2154ee9048b47d8bcb03b356288d71e9b84c7883..3c7bdfe155f1eb8756e2b4a532bf8bf68d4f7106 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayers.C +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayers.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,108 +32,125 @@ Description #include "helperFunctionsPar.H" #include "meshSurfaceCheckInvertedVertices.H" #include "meshSurfacePartitioner.H" +#include "polyMeshGen2DEngine.H" #include "labelledPoint.H" #include <map> #include <set> +# ifdef USE_OMP +#include <omp.h> +# endif + //#define DEBUGLayer // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + const meshSurfaceEngine& boundaryLayers::surfaceEngine() const { if( !msePtr_ ) msePtr_ = new meshSurfaceEngine(mesh_); - + return *msePtr_; } +const meshSurfacePartitioner& boundaryLayers::surfacePartitioner() const +{ + if( !meshPartitionerPtr_ ) + meshPartitionerPtr_ = new meshSurfacePartitioner(surfaceEngine()); + + return *meshPartitionerPtr_; +} + void boundaryLayers::findPatchesToBeTreatedTogether() { - forAll(treatPatchesWithPatch_, patchI) - treatPatchesWithPatch_[patchI].append(patchI); - - const meshSurfaceEngine& mse = surfaceEngine(); - - const VRWGraph& pPatches = mse.pointPatches(); - const pointFieldPMG& points = mesh_.points(); - const faceList::subList& bFaces = mse.boundaryFaces(); + if( geometryAnalysed_ ) + return; + + forAll(treatPatchesWithPatch_, patchI) + treatPatchesWithPatch_[patchI].append(patchI); + + const meshSurfaceEngine& mse = surfaceEngine(); + + const pointFieldPMG& points = mesh_.points(); + const faceList::subList& bFaces = mse.boundaryFaces(); const edgeList& edges = mse.edges(); - const VRWGraph& eFaces = mse.edgeFaces(); - const labelList& boundaryFacePatches = mse.boundaryFacePatches(); - - //- patches must be treated together if there exist a corner where - //- more than three patches meet - meshSurfacePartitioner mPart(mse); + const VRWGraph& eFaces = mse.edgeFaces(); + const labelList& boundaryFacePatches = mse.boundaryFacePatches(); + + const meshSurfacePartitioner& mPart = surfacePartitioner(); + const VRWGraph& pPatches = mPart.pointPatches(); + + //- patches must be treated together if there exist a corner where + //- more than three patches meet const labelHashSet& corners = mPart.corners(); - forAllConstIter(labelHashSet, corners, it) + forAllConstIter(labelHashSet, corners, it) { const label bpI = it.key(); - - if( mPart.numberOfFeatureEdgesAtPoint(bpI) != 3 ) - { + + if( mPart.numberOfFeatureEdgesAtPoint(bpI) != 3 ) + { labelHashSet commonPatches; DynList<label> allPatches; - - forAllRow(pPatches, bpI, patchI) - { + + forAllRow(pPatches, bpI, patchI) + { const DynList<label>& tpwp = treatPatchesWithPatch_[pPatches(bpI, patchI)]; - - forAll(tpwp, pJ) + + forAll(tpwp, pJ) { if( commonPatches.found(tpwp[pJ]) ) continue; - + commonPatches.insert(tpwp[pJ]); - allPatches.append(tpwp[pJ]); + allPatches.append(tpwp[pJ]); } - } - - forAllRow(pPatches, bpI, patchI) - treatPatchesWithPatch_[pPatches(bpI, patchI)] = allPatches; - - # ifdef DEBUGLayer - Info << "Corner " << bpI << " is shared by patches " - << pPatches[bpI] << endl; - Info << "All patches " << allPatches << endl; - # endif - } + } + + forAllRow(pPatches, bpI, patchI) + treatPatchesWithPatch_[pPatches(bpI, patchI)] = allPatches; + + # ifdef DEBUGLayer + Info << "Corner " << bpI << " is shared by patches " + << pPatches[bpI] << endl; + Info << "All patches " << allPatches << endl; + # endif + } } - - //- patches must be treated together for concave geometries + + //- patches must be treated together for concave geometries //- edgeClassification map counts the number of convex and concave edges //- for a given patch. The first counts convex edges and the second counts //- concave ones. If the number of concave edges is of the considerable //- percentage, it is treated as O-topology meshSurfaceCheckInvertedVertices vertexCheck(mse); const labelHashSet& invertedVertices = vertexCheck.invertedVertices(); - + std::map<std::pair<label, label>, Pair<label> > edgeClassification; - labelListPMG procEdges; - forAll(eFaces, eI) - { + labelLongList procEdges; + forAll(eFaces, eI) + { if( eFaces.sizeOfRow(eI) != 2 ) { procEdges.append(eI); continue; } - + //- check if the any of the face vertices is tangled const edge& e = edges[eI]; if( invertedVertices.found(e[0]) || invertedVertices.found(e[1]) ) continue; - - const label patch0 = boundaryFacePatches[eFaces(eI, 0)]; - const label patch1 = boundaryFacePatches[eFaces(eI, 1)]; - if( patch0 != patch1 ) - { + + const label patch0 = boundaryFacePatches[eFaces(eI, 0)]; + const label patch1 = boundaryFacePatches[eFaces(eI, 1)]; + if( patch0 != patch1 ) + { std::pair<label, label> pp ( Foam::min(patch0, patch1), @@ -145,38 +161,38 @@ void boundaryLayers::findPatchesToBeTreatedTogether() ( std::make_pair(pp, Pair<label>(0, 0)) ); - - const face& f1 = bFaces[eFaces(eI, 0)]; - const face& f2 = bFaces[eFaces(eI, 1)]; - if( !help::isSharedEdgeConvex(points, f1, f2) ) - { + + const face& f1 = bFaces[eFaces(eI, 0)]; + const face& f2 = bFaces[eFaces(eI, 1)]; + if( !help::isSharedEdgeConvex(points, f1, f2) ) + { ++edgeClassification[pp].second(); - } + } else { ++edgeClassification[pp].first(); } - } - } - + } + } + if( Pstream::parRun() ) { //- check faces over processor edges const labelList& globalEdgeLabel = mse.globalBoundaryEdgeLabel(); const VRWGraph& beAtProcs = mse.beAtProcs(); const Map<label>& globalToLocal = mse.globalToLocalBndEdgeAddressing(); - + const DynList<label>& neiProcs = mse.beNeiProcs(); const Map<label>& otherProcPatches = mse.otherEdgeFacePatch(); const Map<label>& otherFaceProc = mse.otherEdgeFaceAtProc(); - + //- send faces sharing processor edges to other processors //- faces are flattened into a single contiguous array const labelList& bp = mse.bp(); const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); const Map<label>& globalPointToLocal = mse.globalToLocalBndPointAddressing(); - + std::map<label, LongList<labelledPoint> > exchangePoints; forAll(neiProcs, procI) { @@ -185,31 +201,31 @@ void boundaryLayers::findPatchesToBeTreatedTogether() std::make_pair(neiProcs[procI], LongList<labelledPoint>()) ); } - + //- store faces for sending forAll(procEdges, eI) { const label beI = procEdges[eI]; if( eFaces.sizeOfRow(beI) == 0 ) continue; - + const edge& e = edges[beI]; if( invertedVertices.found(e[0]) || invertedVertices.found(e[1]) ) continue; - + //- do not send data if the face on other processor //- is in the same patch if( otherProcPatches[beI] == boundaryFacePatches[eFaces(beI, 0)] ) continue; - + const face& f = bFaces[eFaces(beI, 0)]; - + forAllRow(beAtProcs, beI, procI) { const label neiProc = beAtProcs(beI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + //- each face is sent as follows //- 1. global edge label //- 2. number of face nodes @@ -230,13 +246,13 @@ void boundaryLayers::findPatchesToBeTreatedTogether() } } } - + LongList<labelledPoint> receivedData; help::exchangeMap(exchangePoints, receivedData); - + //- receive faces from other processors Map<label> transferredPointToLocal; - + label counter(0); while( counter < receivedData.size() ) { @@ -266,14 +282,14 @@ void boundaryLayers::findPatchesToBeTreatedTogether() ); mesh_.points().append(lp.coordinates()); } - + f[pI] = transferredPointToLocal[lp.pointLabel()]; } } - + const label patch0 = boundaryFacePatches[eFaces(beI, 0)]; const label patch1 = otherProcPatches[beI]; - + std::pair<label, label> pp ( Foam::min(patch0, patch1), @@ -284,7 +300,7 @@ void boundaryLayers::findPatchesToBeTreatedTogether() ( std::make_pair(pp, Pair<label>(0, 0)) ); - + if( (otherFaceProc[beI] > Pstream::myProcNo()) && !help::isSharedEdgeConvex(points, bFaces[eFaces(beI, 0)], f) @@ -297,59 +313,63 @@ void boundaryLayers::findPatchesToBeTreatedTogether() ++edgeClassification[pp].first(); } } - + //- set the size of points back to their original number mesh_.points().setSize(nPoints_); } - + std::map<std::pair<label, label>, Pair<label> >::const_iterator it; for(it=edgeClassification.begin();it!=edgeClassification.end();++it) { const std::pair<label, label>& edgePair = it->first; const Pair<label>& nConvexAndConcave = it->second; - + if( nConvexAndConcave.second() != 0 ) { //- number of concave edges is greater than the number //- of the convex ones. Treat patches together. const label patch0 = edgePair.first; const label patch1 = edgePair.second; - + + //- avoid adding unused patches in case of 2D meshing + if( treatedPatch_[patch0] || treatedPatch_[patch1] ) + continue; + treatPatchesWithPatch_[patch0].append(patch1); treatPatchesWithPatch_[patch1].append(patch0); } } - + if( Pstream::parRun() ) { //- make sure that all processors have the same graph - labelListPMG flattenedPatches; + labelLongList flattenedPatches; forAll(treatPatchesWithPatch_, patchI) { if( treatPatchesWithPatch_[patchI].size() <= 1 ) continue; - + flattenedPatches.append(patchI); flattenedPatches.append(treatPatchesWithPatch_[patchI].size()); forAll(treatPatchesWithPatch_[patchI], itemI) flattenedPatches.append(treatPatchesWithPatch_[patchI][itemI]); } - + labelListList procPatches(Pstream::nProcs()); procPatches[Pstream::myProcNo()].setSize(flattenedPatches.size()); forAll(flattenedPatches, i) procPatches[Pstream::myProcNo()][i] = flattenedPatches[i]; Pstream::gatherList(procPatches); Pstream::scatterList(procPatches); - + forAll(procPatches, procI) { if( procI == Pstream::myProcNo() ) continue; - + const labelList& cPatches = procPatches[procI]; label counter(0); - + while( counter < cPatches.size() ) { const label patchI = cPatches[counter++]; @@ -362,7 +382,7 @@ void boundaryLayers::findPatchesToBeTreatedTogether() } } } - + //- final adjusting of patches which shall be treated together boolList confirmed(treatPatchesWithPatch_.size(), false); forAll(treatPatchesWithPatch_, patchI) @@ -372,28 +392,28 @@ void boundaryLayers::findPatchesToBeTreatedTogether() confirmed[patchI] = true; continue; } - + if( confirmed[patchI] ) continue; - + std::set<label> commonPatches; commonPatches.insert(patchI); - + DynList<label> front; front.append(patchI); confirmed[patchI] = true; - + while( front.size() ) { const label fPatch = front.removeLastElement(); - + forAll(treatPatchesWithPatch_[fPatch], i) { const label patchJ = treatPatchesWithPatch_[fPatch][i]; - + if( confirmed[patchJ] ) continue; - + front.append(patchJ); confirmed[patchJ] = true; commonPatches.insert(patchJ); @@ -401,18 +421,18 @@ void boundaryLayers::findPatchesToBeTreatedTogether() commonPatches.insert(treatPatchesWithPatch_[patchJ][j]); } } - + forAllConstIter(std::set<label>, commonPatches, it) { const label patchJ = *it; - + treatPatchesWithPatch_[patchJ].clear(); forAllConstIter(std::set<label>, commonPatches, iter) treatPatchesWithPatch_[patchJ].append(*iter); } } - - # ifdef DEBUGLayer + + # ifdef DEBUGLayer for(it=edgeClassification.begin();it!=edgeClassification.end();++it) { const std::pair<label, label>& edgePair = it->first; @@ -420,47 +440,49 @@ void boundaryLayers::findPatchesToBeTreatedTogether() Info << "Pair of patches " << edgePair.first << " " << edgePair.second << " is " << nConvexAndConcave << endl; } - - Info << "Patch names " << patchNames_ << endl; - Info << "Treat patches with patch " << treatPatchesWithPatch_ << endl; - # endif + + Info << "Patch names " << patchNames_ << endl; + Info << "Treat patches with patch " << treatPatchesWithPatch_ << endl; + # endif + + geometryAnalysed_ = true; } void boundaryLayers::addLayerForPatch(const label patchLabel) { - if( treatedPatch_[patchLabel] ) + if( treatedPatch_[patchLabel] ) return; - - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - - if( returnReduce(boundaries[patchLabel].patchSize(), sumOp<label>()) == 0 ) + + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + + if( returnReduce(boundaries[patchLabel].patchSize(), sumOp<label>()) == 0 ) return; - - boolList treatPatches(boundaries.size(), false); - if( patchWiseLayers_ ) - { - forAll(treatPatchesWithPatch_[patchLabel], pI) - treatPatches[treatPatchesWithPatch_[patchLabel][pI]] = true; - } - else - { - forAll(treatedPatch_, patchI) - if( !treatedPatch_[patchI] ) - treatPatches[patchI] = true; - } - - newLabelForVertex_.setSize(nPoints_); - newLabelForVertex_ = -1; - otherVrts_.clear(); - patchKey_.clear(); - - createNewVertices(treatPatches); - - createNewFacesAndCells(treatPatches); - - forAll(treatPatches, patchI) - if( treatPatches[patchI] ) - treatedPatch_[patchI] = true; + + boolList treatPatches(boundaries.size(), false); + if( patchWiseLayers_ ) + { + forAll(treatPatchesWithPatch_[patchLabel], pI) + treatPatches[treatPatchesWithPatch_[patchLabel][pI]] = true; + } + else + { + forAll(treatedPatch_, patchI) + if( !treatedPatch_[patchI] ) + treatPatches[patchI] = true; + } + + newLabelForVertex_.setSize(nPoints_); + newLabelForVertex_ = -1; + otherVrts_.clear(); + patchKey_.clear(); + + createNewVertices(treatPatches); + + createNewFacesAndCells(treatPatches); + + forAll(treatPatches, patchI) + if( treatPatches[patchI] ) + treatedPatch_[patchI] = true; } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -471,29 +493,29 @@ boundaryLayers::boundaryLayers polyMeshGen& mesh ) : - mesh_(mesh), + mesh_(mesh), msePtr_(NULL), - patchWiseLayers_(true), + meshPartitionerPtr_(NULL), + patchWiseLayers_(true), terminateLayersAtConcaveEdges_(false), - patchNames_(), - treatedPatch_(), - treatPatchesWithPatch_(), - newLabelForVertex_(), - otherVrts_(), - patchKey_(), - nPoints_(mesh.points().size()) + patchNames_(), + treatedPatch_(), + treatPatchesWithPatch_(), + newLabelForVertex_(), + otherVrts_(), + patchKey_(), + nPoints_(mesh.points().size()), + geometryAnalysed_(false) { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - patchNames_.setSize(boundaries.size()); - forAll(boundaries, patchI) - patchNames_[patchI] = boundaries[patchI].patchName(); - - treatedPatch_.setSize(boundaries.size()); - treatedPatch_ = false; - - treatPatchesWithPatch_.setSize(boundaries.size()); - - findPatchesToBeTreatedTogether(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + patchNames_.setSize(boundaries.size()); + forAll(boundaries, patchI) + patchNames_[patchI] = boundaries[patchI].patchName(); + + treatedPatch_.setSize(boundaries.size()); + treatedPatch_ = false; + + treatPatchesWithPatch_.setSize(boundaries.size()); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // @@ -501,7 +523,7 @@ boundaryLayers::boundaryLayers boundaryLayers::~boundaryLayers() { clearOut(); - + if( Pstream::parRun() ) polyMeshGenModifier(mesh_).removeUnusedVertices(); } @@ -510,47 +532,110 @@ boundaryLayers::~boundaryLayers() void boundaryLayers::addLayerForPatch(const word& patchName) { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - - forAll(boundaries, patchI) - if( boundaries[patchI].patchName() == patchName ) - addLayerForPatch(patchI); + if( !geometryAnalysed_ ) + findPatchesToBeTreatedTogether(); + + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + + forAll(boundaries, patchI) + if( boundaries[patchI].patchName() == patchName ) + addLayerForPatch(patchI); } - + void boundaryLayers::createOTopologyLayers() { - patchWiseLayers_ = false; + patchWiseLayers_ = false; } void boundaryLayers::terminateLayersAtConcaveEdges() { terminateLayersAtConcaveEdges_ = true; } - + +void boundaryLayers::activate2DMode() +{ + polyMeshGen2DEngine mesh2DEngine(mesh_); + const boolList& zMinPoint = mesh2DEngine.zMinPoints(); + const boolList& zMaxPoint = mesh2DEngine.zMaxPoints(); + + const faceList::subList& bFaces = surfaceEngine().boundaryFaces(); + const labelList& facePatch = surfaceEngine().boundaryFacePatches(); + + boolList allZMax(mesh_.boundaries().size(), true); + boolList allZMin(mesh_.boundaries().size(), true); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + { + if( !zMinPoint[bf[pI]] ) + allZMin[facePatch[bfI]] = false; + if( !zMaxPoint[bf[pI]] ) + allZMax[facePatch[bfI]] = false; + } + } + + //- mark empty patches as already used + forAll(allZMin, patchI) + { + if( allZMin[patchI] ^ allZMax[patchI] ) + { + treatedPatch_[patchI] = true; + } + } + + forAll(treatPatchesWithPatch_, patchI) + { + DynList<label>& patches = treatPatchesWithPatch_[patchI]; + + for(label i=patches.size()-1;i>=0;--i) + if( treatedPatch_[patches[i]] ) + patches.removeElement(i); + } +} + void boundaryLayers::addLayerForAllPatches() { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - - if( !patchWiseLayers_ ) - { - forAll(boundaries, patchI) - addLayerForPatch(patchI); - } - else - { - newLabelForVertex_.setSize(nPoints_); - newLabelForVertex_ = -1; - otherVrts_.clear(); - patchKey_.clear(); - - labelList treatedPatches(boundaries.size()); - forAll(treatedPatches, i) - treatedPatches[i] = i; - - createNewVertices(treatedPatches); - - createLayerCells(treatedPatches); - } + if( !geometryAnalysed_ ) + findPatchesToBeTreatedTogether(); + + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + + if( !patchWiseLayers_ ) + { + forAll(boundaries, patchI) + addLayerForPatch(patchI); + } + else + { + newLabelForVertex_.setSize(nPoints_); + newLabelForVertex_ = -1; + otherVrts_.clear(); + patchKey_.clear(); + + //- avoid generating bnd layer at empty patches in case of 2D meshing + label counter(0); + forAll(treatedPatch_, patchI) + if( !treatedPatch_[patchI] ) + ++counter; + + labelList treatedPatches(counter); + counter = 0; + forAll(treatedPatch_, i) + if( !treatedPatch_[i] ) + treatedPatches[counter++] = i; + + //- create bnd layer vertices + createNewVertices(treatedPatches); + + //- create bnd layer cells + createLayerCells(treatedPatches); + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayers.H b/meshLibrary/utilities/boundaryLayers/boundaryLayers.H index dc98f2c164af40e6391a67a69c980b2b9ea2b366..ef83edcea840c7517bc59a6c1116d7ceed115811 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayers.H +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayers.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class boundaryLayers @@ -38,8 +37,9 @@ SourceFiles #include "polyMeshGenModifier.H" #include "meshSurfaceEngine.H" +#include "meshSurfacePartitioner.H" #include "DynList.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "Map.H" #include "labelPair.H" @@ -49,9 +49,10 @@ SourceFiles namespace Foam { - + // Forward declarations class meshSurfaceEngine; +class meshSurfacePartitioner; /*---------------------------------------------------------------------------*\ Class boundaryLayers Declaration @@ -59,159 +60,169 @@ class meshSurfaceEngine; class boundaryLayers { - //- Reference to the mesh - polyMeshGen& mesh_; - + //- Reference to the mesh + polyMeshGen& mesh_; + //- pointer to mesh surface engine mutable meshSurfaceEngine* msePtr_; - - //- shall I create patch-wise layers (true) - //- O-topology layer (false) - bool patchWiseLayers_; - + + //- poiner to meshSurfacePartitioner + mutable meshSurfacePartitioner* meshPartitionerPtr_; + + //- shall I create patch-wise layers (true) + //- O-topology layer (false) + bool patchWiseLayers_; + //- shall the layers be terminated at concave edges (true) bool terminateLayersAtConcaveEdges_; - - //- patch names - wordList patchNames_; - - //- helper which contains information if a boundary layer - //- has already been extruded for a given patch - boolList treatedPatch_; - - //- extrude patches with patch - List<DynList<label> > treatPatchesWithPatch_; - - //- label of a new node (helper) - labelListPMG newLabelForVertex_; - - //- map storing labels of new vertices created at node - //- and corner vertices - std::map<label, std::map<std::pair<label, label>, label> > otherVrts_; - - //- a key assigned to each patch. It is needed to search in otherVrts_ - labelList patchKey_; - - //- number of vertices in the mesh - label nPoints_; - - // Private member functions - //- Return reference to meshSurfaceEngine + + //- patch names + wordList patchNames_; + + //- helper which contains information if a boundary layer + //- has already been extruded for a given patch + boolList treatedPatch_; + + //- extrude patches with patch + List<DynList<label> > treatPatchesWithPatch_; + + //- label of a new node (helper) + labelLongList newLabelForVertex_; + + //- map storing labels of new vertices created at node + //- and corner vertices + std::map<label, std::map<std::pair<label, label>, label> > otherVrts_; + + //- a key assigned to each patch. It is needed to search in otherVrts_ + labelList patchKey_; + + //- number of vertices in the mesh + label nPoints_; + + //- has the geometry been analysed + bool geometryAnalysed_; + + // Private member functions + //- Return const reference to meshSurfaceEngine const meshSurfaceEngine& surfaceEngine() const; - - //- find if any other patches need to be treated together - //- with the given one - void findPatchesToBeTreatedTogether(); - - //- find vertices of the selected patches - void findPatchVertices - ( - const boolList& treatPatches, - List<direction>& patchVertex - ) const; - + + //- return const reference to meshSurfacePartitioner + const meshSurfacePartitioner& surfacePartitioner() const; + + //- find if any other patches need to be treated together + //- with the given one + void findPatchesToBeTreatedTogether(); + + //- find vertices of the selected patches + void findPatchVertices + ( + const boolList& treatPatches, + List<direction>& patchVertex + ) const; + //- check and correct the topology of boundary faces where //- the layers terminate void checkTopologyOfBoundaryFaces(const labelList& patchLabels); - - //- create new vertex - point createNewVertex - ( - const label bpI, - const boolList& treatPatches, - const List<direction>& pVertices - ) const; - - //- create new vertices for the selected patches - void createNewVertices - ( - const boolList& treatPatches - ); - - //- create new vertices such that layers for selected patches - //- are generated in a single run - void createNewVertices - ( - const labelList& patchLabels - ); - + + //- create new vertex + point createNewVertex + ( + const label bpI, + const boolList& treatPatches, + const List<direction>& pVertices + ) const; + + //- create new vertices for the selected patches + void createNewVertices + ( + const boolList& treatPatches + ); + + //- create new vertices such that layers for selected patches + //- are generated in a single run + void createNewVertices + ( + const labelList& patchLabels + ); + //- creates new vertices for vertices at parallel boundaries void createNewPartitionVerticesParallel ( - const labelListPMG& procPoints, + const labelLongList& procPoints, const List<direction>& pVertices, const boolList& treatPatches ); - + //- creates new vertices from vertices at parallel boundaries //- which are also at the border of the treated partitions void createNewEdgeVerticesParallel ( - const labelListPMG& procPoints, + const labelLongList& procPoints, const List<direction>& pVertices, const boolList& treatPatches ); - - //- create a layer of cells - void createNewFacesAndCells - ( - const boolList& treatPatches - ); - + + //- create a layer of cells + void createNewFacesAndCells + ( + const boolList& treatPatches + ); + + //- create new faces at parallel boundaries + //- faces are extruded from edges + void createNewFacesParallel + ( + const boolList& treatPatches + ); + //- create new faces at parallel boundaries - //- faces are extruded from edges - void createNewFacesParallel - ( - const boolList& treatPatches - ); - - //- create new faces at parallel boundaries - //- faces are created from points at parallel boundaries - //- the function takes a reference to the faces which are the candidates - //- to create faces at parallel boundaries - void createNewFacesFromPointsParallel - ( - const LongList<DynList<label, 4> >& faceCandidates, - const LongList<labelPair>& candidatePatches - ); - - //- create layer cells in one go - //- this is much faster than layer by layer - void createLayerCells(const labelList& patchLabels); - - //- helper function finding a new face label for multiply extruded nodes - inline label findNewNodeLabel - ( - const label pointI, - const label pKey - ) const; - - //- creating hex cells near feature edges - inline void createNewCellFromEdge - ( - const edge& e, - const label pKeyI, - const label pKeyJ, - DynList<DynList<label, 4>, 6>& cellFaces - ) const; - - //- creating hex cells near corners - inline void createNewCellFromNode - ( - const label pointI, - const DynList<label, 3>& pKeys, - DynList<DynList<label, 4>, 6>& cellFaces - ) const; - - //- create a bnd layer for a given patch - void addLayerForPatch(const label patchLabel); - + //- faces are created from points at parallel boundaries + //- the function takes a reference to the faces which are the candidates + //- to create faces at parallel boundaries + void createNewFacesFromPointsParallel + ( + const LongList<DynList<label, 4> >& faceCandidates, + const LongList<labelPair>& candidatePatches + ); + + //- create layer cells in one go + //- this is much faster than layer by layer + void createLayerCells(const labelList& patchLabels); + + //- helper function finding a new face label for multiply extruded nodes + inline label findNewNodeLabel + ( + const label pointI, + const label pKey + ) const; + + //- creating hex cells near feature edges + inline void createNewCellFromEdge + ( + const edge& e, + const label pKeyI, + const label pKeyJ, + FixedList<FixedList<label, 4>, 6>& cellFaces + ) const; + + //- creating hex cells near corners + inline void createNewCellFromNode + ( + const label pointI, + const DynList<label, 3>& pKeys, + FixedList<FixedList<label, 4>, 6>& cellFaces + ) const; + + //- create a bnd layer for a given patch + void addLayerForPatch(const label patchLabel); + //- delete meshSurfaceEngine inline void clearOut() { deleteDemandDrivenData(msePtr_); + deleteDemandDrivenData(meshPartitionerPtr_); } - + // Enumerators enum vertexTypes { @@ -221,33 +232,43 @@ class boundaryLayers CORNERNODE = 4, PARALLELBOUNDARY = 8 }; - - public: - - // Constructors - - //- Construct from mesh reference - boundaryLayers(polyMeshGen& mesh); - - // Destructor - ~boundaryLayers(); - - // Public member functions - //- adds layer for a given patch - void addLayerForPatch(const word& patchName); - - //- create O-topology layers (used as flag) - void createOTopologyLayers(); - + + //- Disallow bitwise copy construct + boundaryLayers(const boundaryLayers&); + + //- Disallow bitwise assignment + void operator=(const boundaryLayers&); + +public: + + // Constructors + + //- Construct from mesh reference + boundaryLayers(polyMeshGen& mesh); + + // Destructor + ~boundaryLayers(); + + // Public member functions + //- adds layer for a given patch + void addLayerForPatch(const word& patchName); + + //- create O-topology layers (used as flag) + void createOTopologyLayers(); + //- terminate boundary layers at concave edges (used as a flag) void terminateLayersAtConcaveEdges(); - - //- add layers for all patches - void addLayerForAllPatches(); - - //- add wrapper layer - //- this function is intended for usage before surface recovery - void addWrapperLayer(); + + //- avoid generating layers for empty patches in case of a 2D mesh + //- used as a flag prior to addLayerForAllPatches + void activate2DMode(); + + //- add layers for all patches + void addLayerForAllPatches(); + + //- add wrapper layer + //- this function is intended for usage before surface recovery + void addWrapperLayer(); }; diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayersCheckTopologyOfBndFaces.C b/meshLibrary/utilities/boundaryLayers/boundaryLayersCheckTopologyOfBndFaces.C index ac7749beca4275f5c29d33bd52317ef825690005..d78f97d494a8220220186016c8fefdb5d87d3e15 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayersCheckTopologyOfBndFaces.C +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayersCheckTopologyOfBndFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -95,8 +94,8 @@ void boundaryLayers::checkTopologyOfBoundaryFaces(const labelList& patchLabels) const Map<label>& otherProcPatch = mse.otherEdgeFacePatch(); VRWGraph newBoundaryFaces; - labelListPMG newBoundaryOwners; - labelListPMG newBoundaryPatches; + labelLongList newBoundaryOwners; + labelLongList newBoundaryPatches; forAll(bFaces, bfI) { diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayersCreateVertices.C b/meshLibrary/utilities/boundaryLayers/boundaryLayersCreateVertices.C index 89b48fb1e89562871a0753929298f36091af579e..1803bc32c300e958e1e851a5c64b7fe7e175219e 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayersCreateVertices.C +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayersCreateVertices.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,7 +35,10 @@ Description #include "labelledScalar.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGLayer @@ -49,23 +51,26 @@ namespace Foam void boundaryLayers::findPatchVertices ( - const boolList& treatPatches, - List<direction>& pVertices + const boolList& treatPatches, + List<direction>& pVertices ) const { const meshSurfaceEngine& mse = surfaceEngine(); - const VRWGraph& pPatches = mse.pointPatches(); - + const meshSurfacePartitioner& mPart = surfacePartitioner(); + const VRWGraph& pPatches = mPart.pointPatches(); + pVertices.setSize(pPatches.size()); - pVertices = NONE; - + pVertices = NONE; + + # ifdef USE_OMP # pragma omp parallel for if( pPatches.size() > 1000 ) \ schedule(dynamic, Foam::max(10, pPatches.size()/(2*omp_get_num_threads()))) + # endif forAll(pPatches, bpI) { bool hasTreated(false); bool hasNotTreated(false); - + forAllRow(pPatches, bpI, patchI) { const label patch = pPatches(bpI, patchI); @@ -78,16 +83,16 @@ void boundaryLayers::findPatchVertices hasNotTreated = true; } } - + if( hasTreated ) { pVertices[bpI] |= PATCHNODE; - + if( hasNotTreated ) pVertices[bpI] |= EDGENODE; } } - + if( Pstream::parRun() ) { const VRWGraph& bpAtProcs = mse.bpAtProcs(); @@ -95,258 +100,262 @@ void boundaryLayers::findPatchVertices if( pVertices[bpI] && (bpAtProcs.sizeOfRow(bpI) != 0) ) pVertices[bpI] |= PARALLELBOUNDARY; } - } point boundaryLayers::createNewVertex ( - const label bpI, - const boolList& treatPatches, - const List<direction>& patchVertex + const label bpI, + const boolList& treatPatches, + const List<direction>& patchVertex ) const { - const meshSurfaceEngine& mse = surfaceEngine(); - const labelList& bPoints = mse.boundaryPoints(); - const faceList::subList& bFaces = mse.boundaryFaces(); - const vectorField& pNormals = mse.pointNormals(); - const VRWGraph& pFaces = mse.pointFaces(); - const VRWGraph& pPatches = mse.pointPatches(); - const labelList& boundaryFacePatches = mse.boundaryFacePatches(); - const VRWGraph& pointPoints = mse.pointPoints(); - - const pointFieldPMG& points = mesh_.points(); - - # ifdef DEBUGLayer - Info << "Creating new vertex for boundary vertex " << bpI << endl; - Info << "Global vertex label " << bPoints[bpI] << endl; - # endif - - vector normal(vector::zero); - scalar dist(VGREAT); - const point& p = points[bPoints[bpI]]; - if( patchVertex[bpI] & EDGENODE ) - { - # ifdef DEBUGLayer - Info << "Vertex is on the border" << endl; - # endif - - DynList<label> otherPatches(2); - forAllRow(pPatches, bpI, patchI) - if( !treatPatches[pPatches(bpI, patchI)] ) - otherPatches.appendIfNotIn - ( - pPatches(bpI, patchI) - ); - - if( otherPatches.size() == 1 ) - { - //- vertex is on an edge - # ifdef DEBUGLayer - Info << "Vertex is on an edge" << endl; - # endif - vector v(vector::zero); - - forAllRow(pFaces, bpI, pfI) - { - const face& f = bFaces[pFaces(bpI, pfI)]; - const label patchLabel = - boundaryFacePatches[pFaces(bpI, pfI)]; - - if( treatPatches[patchLabel] ) - { - normal += f.normal(points); - } - else - { - v += f.normal(points); - } - } - - const scalar magV = mag(v); - if( magV > VSMALL ) - v /= magV; - - normal -= (normal & v) * v; - - const scalar magN = mag(normal); - if( magN > VSMALL ) - normal /= magN; - - forAllRow(pointPoints, bpI, ppI) - { - if( patchVertex[pointPoints(bpI, ppI)] ) - continue; - - vector vec = points[bPoints[pointPoints(bpI, ppI)]] - p; - const scalar prod = 0.5 * mag(vec & normal); - - if( prod < dist ) - dist = prod; - } - } - else if( otherPatches.size() == 2 ) - { - # ifdef DEBUGLayer - Info << "Vertex is a corner" << endl; - # endif - - label otherVertex(-1); - forAllRow(pointPoints, bpI, ppI) - { - const label bpJ = pointPoints(bpI, ppI); - - bool found(true); - forAll(otherPatches, opI) - if( !pPatches.contains(bpJ, otherPatches[opI]) ) - { - found = false; - break; - } - - if( found ) - { - otherVertex = bpJ; - break; - } - } - - if( otherVertex == -1 ) - { - FatalErrorIn - ( - "void boundaryLayers::createNewVertices" - "(" - "const boolList& treatPatches," - "labelList& newLabelForVertex" - ")" - ) << "Cannot find moving vertex!" << exit(FatalError); - } - - //- normal vector is co-linear with that edge - normal = p - points[bPoints[otherVertex]]; - dist = 0.5 * mag(normal); - - if( mag(dist) > VSMALL ) - normal /= 2.0 * dist; - } - else - { - FatalErrorIn - ( - "void boundaryLayers::createNewVertices" - "(" - "const boolList& treatPatches," - "labelList& newLabelForVertex" - ") const" - ) << "There are more than 3 patches meeting at this vertex!" - << pPatches[bpI] << abort(FatalError); - } - - //- limit distances - forAllRow(pFaces, bpI, pfI) - { - const label faceLabel = pFaces(bpI, pfI); - if( otherPatches.contains(boundaryFacePatches[faceLabel]) ) - { - const face& f = bFaces[faceLabel]; - const label pos = f.which(bPoints[bpI]); - - if( pos != -1 ) - { - const point& ep1 = points[f.prevLabel(pos)]; - const point& ep2 = points[f.nextLabel(pos)]; - - const scalar dst = - help::distanceOfPointFromTheEdge(ep1, ep2, p); - - if( dst < dist ) - dist = 0.9 * dst; - } - else - { - FatalErrorIn - ( - "void boundaryLayers::createNewVertices" - "(" - "const boolList& treatPatches," - "labelList& newLabelForVertex" - ") const" - ) << "Face does not contains this vertex!" - << abort(FatalError); - } - } - } - } - else - { - normal = pNormals[bpI]; - - forAllRow(pointPoints, bpI, ppI) - { - const scalar d = - 0.5 * mag - ( - points[bPoints[pointPoints(bpI, ppI)]] - - p - ); - - if( d < dist ) - dist = d; - } - } - - //- create new vertex - # ifdef DEBUGLayer - Info << "Normal for vertex " << bpI << " is " << normal << endl; - Info << "Distance is " << dist << endl; - # endif - - return p - dist * normal; + const meshSurfaceEngine& mse = surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const vectorField& pNormals = mse.pointNormals(); + const VRWGraph& pFaces = mse.pointFaces(); + const labelList& boundaryFacePatches = mse.boundaryFacePatches(); + const VRWGraph& pointPoints = mse.pointPoints(); + + const meshSurfacePartitioner& mPart = surfacePartitioner(); + const VRWGraph& pPatches = mPart.pointPatches(); + + const pointFieldPMG& points = mesh_.points(); + + # ifdef DEBUGLayer + Info << "Creating new vertex for boundary vertex " << bpI << endl; + Info << "Global vertex label " << bPoints[bpI] << endl; + # endif + + vector normal(vector::zero); + scalar dist(VGREAT); + const point& p = points[bPoints[bpI]]; + if( patchVertex[bpI] & EDGENODE ) + { + # ifdef DEBUGLayer + Info << "Vertex is on the border" << endl; + # endif + + DynList<label> otherPatches; + forAllRow(pPatches, bpI, patchI) + if( !treatPatches[pPatches(bpI, patchI)] ) + otherPatches.appendIfNotIn + ( + pPatches(bpI, patchI) + ); + + if( otherPatches.size() == 1 ) + { + //- vertex is on an edge + # ifdef DEBUGLayer + Info << "Vertex is on an edge" << endl; + # endif + vector v(vector::zero); + + forAllRow(pFaces, bpI, pfI) + { + const face& f = bFaces[pFaces(bpI, pfI)]; + const label patchLabel = + boundaryFacePatches[pFaces(bpI, pfI)]; + + if( treatPatches[patchLabel] ) + { + normal += f.normal(points); + } + else + { + v += f.normal(points); + } + } + + const scalar magV = mag(v) + VSMALL; + v /= magV; + + normal -= (normal & v) * v; + + const scalar magN = mag(normal) + VSMALL; + normal /= magN; + + forAllRow(pointPoints, bpI, ppI) + { + if( patchVertex[pointPoints(bpI, ppI)] ) + continue; + + const vector vec = points[bPoints[pointPoints(bpI, ppI)]] - p; + const scalar prod = 0.5 * mag(vec & normal); + + if( prod < dist ) + dist = prod; + } + } + else if( otherPatches.size() == 2 ) + { + # ifdef DEBUGLayer + Info << "Vertex is a corner" << endl; + # endif + + label otherVertex(-1); + forAllRow(pointPoints, bpI, ppI) + { + const label bpJ = pointPoints(bpI, ppI); + + bool found(true); + forAll(otherPatches, opI) + if( !pPatches.contains(bpJ, otherPatches[opI]) ) + { + found = false; + break; + } + + if( found ) + { + otherVertex = bpJ; + break; + } + } + + if( otherVertex == -1 ) + { + FatalErrorIn + ( + "void boundaryLayers::createNewVertices" + "(" + "const boolList& treatPatches," + "labelList& newLabelForVertex" + ")" + ) << "Cannot find moving vertex!" << exit(FatalError); + } + + //- normal vector is co-linear with that edge + normal = p - points[bPoints[otherVertex]]; + dist = 0.5 * mag(normal) + VSMALL; + + normal /= 2.0 * dist; + } + else + { + FatalErrorIn + ( + "void boundaryLayers::createNewVertices" + "(" + "const boolList& treatPatches," + "labelList& newLabelForVertex" + ") const" + ) << "There are more than 3 patches meeting at this vertex!" + << pPatches[bpI] << abort(FatalError); + } + + //- limit distances + forAllRow(pFaces, bpI, pfI) + { + const label faceLabel = pFaces(bpI, pfI); + if( otherPatches.contains(boundaryFacePatches[faceLabel]) ) + { + const face& f = bFaces[faceLabel]; + const label pos = f.which(bPoints[bpI]); + + if( pos != -1 ) + { + const point& ep1 = points[f.prevLabel(pos)]; + const point& ep2 = points[f.nextLabel(pos)]; + + const scalar dst = + help::distanceOfPointFromTheEdge(ep1, ep2, p); + + if( dst < dist ) + dist = 0.9 * dst; + } + else + { + FatalErrorIn + ( + "void boundaryLayers::createNewVertices" + "(" + "const boolList& treatPatches," + "labelList& newLabelForVertex" + ") const" + ) << "Face does not contains this vertex!" + << abort(FatalError); + } + } + } + } + else + { + normal = pNormals[bpI]; + + forAllRow(pointPoints, bpI, ppI) + { + const scalar d = + 0.5 * mag + ( + points[bPoints[pointPoints(bpI, ppI)]] - + p + ); + + if( d < dist ) + dist = d; + } + } + + //- create new vertex + # ifdef DEBUGLayer + Info << "Normal for vertex " << bpI << " is " << normal << endl; + Info << "Distance is " << dist << endl; + # endif + + dist = Foam::max(dist, VSMALL); + + const point newP = p - dist * normal; + + if( help::isnan(newP) || help::isinf(newP) ) + return p; + + return newP; } - + void boundaryLayers::createNewVertices(const boolList& treatPatches) { - Info << "Creating vertices for layer cells" << endl; + Info << "Creating vertices for layer cells" << endl; + + List<direction> patchVertex; + findPatchVertices(treatPatches, patchVertex); - List<direction> patchVertex; - findPatchVertices(treatPatches, patchVertex); - const meshSurfaceEngine& mse = surfaceEngine(); - const labelList& bPoints = mse.boundaryPoints(); - - //- the following is needed for parallel runs - //- it is ugly, but must stay for now :( - if( Pstream::parRun() ) - { - mse.pointNormals(); - mse.pointPatches(); + const labelList& bPoints = mse.boundaryPoints(); + + //- the following is needed for parallel runs + //- it is ugly, but must stay for now :( + if( Pstream::parRun() ) + { + mse.pointNormals(); mse.pointPoints(); - } - - pointFieldPMG& points = mesh_.points(); - - label nExtrudedVertices(0); - forAll(patchVertex, bpI) - if( patchVertex[bpI] ) - ++nExtrudedVertices; - - points.setSize(points.size() + nExtrudedVertices); - - labelListPMG procPoints; - forAll(bPoints, bpI) - if( patchVertex[bpI] ) - { + } + + pointFieldPMG& points = mesh_.points(); + + label nExtrudedVertices(0); + forAll(patchVertex, bpI) + if( patchVertex[bpI] ) + ++nExtrudedVertices; + + points.setSize(points.size() + nExtrudedVertices); + + labelLongList procPoints; + forAll(bPoints, bpI) + if( patchVertex[bpI] ) + { if( patchVertex[bpI] & PARALLELBOUNDARY ) { procPoints.append(bpI); continue; } - - points[nPoints_] = createNewVertex(bpI, treatPatches, patchVertex); - newLabelForVertex_[bPoints[bpI]] = nPoints_; - ++nPoints_; - } - + + points[nPoints_] = createNewVertex(bpI, treatPatches, patchVertex); + newLabelForVertex_[bPoints[bpI]] = nPoints_; + ++nPoints_; + } + if( Pstream::parRun() ) { createNewPartitionVerticesParallel @@ -355,7 +364,7 @@ void boundaryLayers::createNewVertices(const boolList& treatPatches) patchVertex, treatPatches ); - + createNewEdgeVerticesParallel ( procPoints, @@ -365,279 +374,317 @@ void boundaryLayers::createNewVertices(const boolList& treatPatches) } //- swap coordinates of new and old points - forAll(bPoints, bpI) - { - const label pLabel = newLabelForVertex_[bPoints[bpI]]; - if( pLabel != -1 ) - { + forAll(bPoints, bpI) + { + const label pLabel = newLabelForVertex_[bPoints[bpI]]; + if( pLabel != -1 ) + { const point p = points[pLabel]; - points[pLabel] = points[bPoints[bpI]]; + points[pLabel] = points[bPoints[bpI]]; points[bPoints[bpI]] = p; - } - } - - if( nPoints_ != points.size() ) - FatalErrorIn - ( - "void boundaryLayers::createNewVertices(" - "const meshSurfaceEngine& mse," - "const boolList& treatPatches," - "labelList& newLabelForVertex)" - ) << "Number of vertices " << nPoints_ - << " does not match the list size " - << abort(FatalError); - - Info << "Finished creating layer vertices" << endl; + } + } + + if( nPoints_ != points.size() ) + FatalErrorIn + ( + "void boundaryLayers::createNewVertices(" + "const meshSurfaceEngine& mse," + "const boolList& treatPatches," + "labelList& newLabelForVertex)" + ) << "Number of vertices " << nPoints_ + << " does not match the list size " + << abort(FatalError); + + Info << "Finished creating layer vertices" << endl; } void boundaryLayers::createNewVertices(const labelList& patchLabels) { - otherVrts_.clear(); - - patchKey_.setSize(mesh_.boundaries().size()); - patchKey_ = -1; - - const meshSurfaceEngine& mse = surfaceEngine(); - const VRWGraph& pPatches = mse.pointPatches(); - const labelList& bPoints = mse.boundaryPoints(); + otherVrts_.clear(); + + patchKey_.setSize(mesh_.boundaries().size()); + patchKey_ = -1; + + const meshSurfaceEngine& mse = surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); const label nBndPts = bPoints.size(); - + + const meshSurfacePartitioner& mPart = surfacePartitioner(); + const VRWGraph& pPatches = mPart.pointPatches(); + //- the following is needed for parallel runs - //- it is ugly, but must stay for now :( - mse.boundaryFaces(); - mse.pointNormals(); - mse.pointFaces(); - mse.boundaryFacePatches(); - mse.pointPoints(); - - pointFieldPMG& points = mesh_.points(); + //- it is ugly, but must stay for now :( + mse.boundaryFaces(); + mse.pointNormals(); + mse.pointFaces(); + mse.pointPoints(); + + pointFieldPMG& points = mesh_.points(); boolList treatPatches(mesh_.boundaries().size()); List<direction> patchVertex(nBndPts); - - //- generate new layer vertices for each patch - forAll(patchLabels, patchI) - { - const label pLabel = patchLabels[patchI]; - treatPatches = false; - - bool treat(true); - forAll(treatPatchesWithPatch_[pLabel], pI) - { - const label otherPatch = treatPatchesWithPatch_[pLabel][pI]; - treatPatches[otherPatch] = true; - - if( patchKey_[otherPatch] == -1 ) - { - patchKey_[otherPatch] = patchI; - } - else - { - treat = false; - } - } - - if( !treat ) - continue; - - const label pKey = patchKey_[pLabel]; - - //- classify vertices belonging to this patch - findPatchVertices(treatPatches, patchVertex); - - //- go throught the vertices and create the new ones - labelListPMG procPoints; - # pragma omp parallel for if( nBndPts > 100 ) \ - schedule(dynamic, Foam::max(10, nBndPts/(2*omp_get_num_threads()))) + + //- make sure than the points are never re-allocated during the process + points.reserve(points.size() + 2 * nBndPts); + + //- generate new layer vertices for each patch + forAll(patchLabels, patchI) + { + const label pLabel = patchLabels[patchI]; + treatPatches = false; + + bool treat(true); + forAll(treatPatchesWithPatch_[pLabel], pI) + { + const label otherPatch = treatPatchesWithPatch_[pLabel][pI]; + treatPatches[otherPatch] = true; + + if( patchKey_[otherPatch] == -1 ) + { + patchKey_[otherPatch] = patchI; + } + else + { + treat = false; + } + } + + if( !treat ) + continue; + + const label pKey = patchKey_[pLabel]; + + //- classify vertices belonging to this patch + findPatchVertices(treatPatches, patchVertex); + + //- go throught the vertices and create the new ones + labelLongList procPoints; + # ifdef USE_OMP + # pragma omp parallel for if( nBndPts > 1000 ) schedule(dynamic, 50) + # endif for(label bpI=0;bpI<nBndPts;++bpI) - { - if( !patchVertex[bpI] ) - continue; - - //- skip vertices at parallel boundaries - if( patchVertex[bpI] & PARALLELBOUNDARY ) - { + { + if( !patchVertex[bpI] ) + continue; + + //- skip vertices at parallel boundaries + if( patchVertex[bpI] & PARALLELBOUNDARY ) + { + # ifdef USE_OMP # pragma omp critical(appendProcPoints) + # endif procPoints.append(bpI); - - continue; - } - - const label pointI = bPoints[bpI]; + + continue; + } + + const label pointI = bPoints[bpI]; label nPoints; + # ifdef USE_OMP # pragma omp critical(incrementNumPoints) + # endif nPoints = nPoints_++; - - //- create new point - const point p = createNewVertex(bpI, treatPatches, patchVertex); - - if( patchVertex[bpI] & EDGENODE ) - { + + //- create new point + const point p = createNewVertex(bpI, treatPatches, patchVertex); + + if( patchVertex[bpI] & EDGENODE ) + { + # ifdef USE_OMP # pragma omp critical(adjustMap) + # endif { if( otherVrts_.find(pointI) == otherVrts_.end() ) { std::map<std::pair<label, label>, label> m; - + otherVrts_.insert(std::make_pair(pointI, m)); } - + std::pair<label, label> pr(pKey, pKey); otherVrts_[pointI].insert(std::make_pair(pr, nPoints)); } - } - else - { - //- this the only new point for a given vertex - newLabelForVertex_[pointI] = nPoints; - } - - //- store the point + } + else + { + //- this the only new point for a given vertex + newLabelForVertex_[pointI] = nPoints; + } + + //- store the point + # ifdef USE_OMP # pragma omp critical(addVertex) + # endif { points.newElmt(nPoints) = p; } - } - - if( Pstream::parRun() ) - { - points.setSize(nPoints_+procPoints.size()); - - createNewPartitionVerticesParallel - ( - procPoints, - patchVertex, - treatPatches - ); - - createNewEdgeVerticesParallel - ( - procPoints, - patchVertex, - treatPatches - ); - } - } - - //- create missing vertices for edge and corner vertices - //- they should be stored in the otherNodes map - forAll(bPoints, bpI) - { - const label pointI = bPoints[bpI]; - - if( otherVrts_.find(pointI) == otherVrts_.end() ) - continue; - - const point& p = points[pointI]; - - std::map<std::pair<label, label>, label>& m = otherVrts_[pointI]; - DynList<label> usedPatches(3); - DynList<label> newNodeLabel(3); - DynList<vector> newPatchPenetrationVector(3); - forAllRow(pPatches, bpI, patchI) - { - const label pKey = patchKey_[pPatches(bpI, patchI)]; - const std::pair<label, label> pr(pKey, pKey); - const std::map<std::pair<label, label>, label>::const_iterator it = - m.find(pr); - if( (it != m.end()) && !usedPatches.contains(pKey) ) - { - usedPatches.append(pKey); - newNodeLabel.append(it->second); - newPatchPenetrationVector.append(points[it->second] - p); - } - } - - if( newNodeLabel.size() == 1 ) - { - //- only one patch is treated - newLabelForVertex_[pointI] = newNodeLabel[0]; - otherVrts_.erase(pointI); - } - else if( newNodeLabel.size() == 2 ) - { - //- point is located at an extrusion edge - //- create the new position for the existing point - point newP(p); - newP += newPatchPenetrationVector[0]; - newP += newPatchPenetrationVector[1]; - - points.append(newP); - newLabelForVertex_[pointI] = nPoints_; - ++nPoints_; - } - else if( newNodeLabel.size() == 3 ) - { - //- point is located at an extrusion corner - //- create 3 points and the new position for the existing point - point newP(p); - for(label i=0;i<3;++i) - { - newP += newPatchPenetrationVector[i]; - for(label j=i+1;j<3;++j) - { - const point np = - p + newPatchPenetrationVector[i] + - newPatchPenetrationVector[j]; - - points.append(np); - m.insert - ( - std::make_pair - ( - std::make_pair(usedPatches[i], usedPatches[j]), + } + + if( Pstream::parRun() ) + { + points.setSize(nPoints_+procPoints.size()); + + createNewPartitionVerticesParallel + ( + procPoints, + patchVertex, + treatPatches + ); + + createNewEdgeVerticesParallel + ( + procPoints, + patchVertex, + treatPatches + ); + } + } + + //- create missing vertices for edge and corner vertices + //- they should be stored in the otherNodes map + forAll(bPoints, bpI) + { + const label pointI = bPoints[bpI]; + + if( otherVrts_.find(pointI) == otherVrts_.end() ) + continue; + + const point& p = points[pointI]; + + std::map<std::pair<label, label>, label>& m = otherVrts_[pointI]; + DynList<label> usedPatches; + DynList<label> newNodeLabel; + DynList<vector> newPatchPenetrationVector; + forAllRow(pPatches, bpI, patchI) + { + const label pKey = patchKey_[pPatches(bpI, patchI)]; + const std::pair<label, label> pr(pKey, pKey); + const std::map<std::pair<label, label>, label>::const_iterator it = + m.find(pr); + if( (it != m.end()) && !usedPatches.contains(pKey) ) + { + usedPatches.append(pKey); + newNodeLabel.append(it->second); + newPatchPenetrationVector.append(points[it->second] - p); + } + } + + if( newNodeLabel.size() == 1 ) + { + //- only one patch is treated + newLabelForVertex_[pointI] = newNodeLabel[0]; + otherVrts_.erase(pointI); + } + else if( newNodeLabel.size() == 2 ) + { + //- point is located at an extrusion edge + //- create the new position for the existing point + point newP(p); + newP += newPatchPenetrationVector[0]; + newP += newPatchPenetrationVector[1]; + + if( !help::isnan(newP) && !help::isinf(newP) ) + { + points.append(newP); + } + else + { + points.append(p); + } + newLabelForVertex_[pointI] = nPoints_; + ++nPoints_; + } + else if( newNodeLabel.size() == 3 ) + { + //- point is located at an extrusion corner + //- create 3 points and the new position for the existing point + point newP(p); + for(label i=0;i<3;++i) + { + newP += newPatchPenetrationVector[i]; + for(label j=i+1;j<3;++j) + { + const point np = + p + newPatchPenetrationVector[i] + + newPatchPenetrationVector[j]; + + if( !help::isnan(np) && !help::isinf(np) ) + { + points.append(np); + } + else + { + points.append(p); + } + + m.insert + ( + std::make_pair + ( + std::make_pair(usedPatches[i], usedPatches[j]), nPoints_ - ) - ); - ++nPoints_; - } - } - - //- create new position for the existing point - points.append(newP); - newLabelForVertex_[pointI] = nPoints_; - ++nPoints_; - } - else - { - FatalErrorIn - ( - "void boundaryLayers::createNewVertices(" - "const labelList& patchLabels, labelListPMG& newLabelForVertex," - "std::map<label, std::map<std::pair<label, label>, label> >&)" - ) << "Boundary node " << bpI << " is not at an edge!" - << abort(FatalError); - } - } - - //- swap coordinates of new and old points + ) + ); + ++nPoints_; + } + } + + //- create new position for the existing point + if( !help::isnan(newP) && !help::isinf(newP) ) + { + points.append(newP); + } + else + { + points.append(p); + } + + newLabelForVertex_[pointI] = nPoints_; + ++nPoints_; + } + else + { + FatalErrorIn + ( + "void boundaryLayers::createNewVertices(" + "const labelList& patchLabels, labelLongList& newLabelForVertex," + "std::map<label, std::map<std::pair<label, label>, label> >&)" + ) << "Boundary node " << bpI << " is not at an edge!" + << abort(FatalError); + } + } + + //- swap coordinates of new and old points + # ifdef USE_OMP # pragma omp parallel for if( bPoints.size() > 1000 ) \ schedule(dynamic, 100) - forAll(bPoints, bpI) - { - const label pLabel = newLabelForVertex_[bPoints[bpI]]; - - if( pLabel != -1 ) - { + # endif + forAll(bPoints, bpI) + { + const label pLabel = newLabelForVertex_[bPoints[bpI]]; + + if( pLabel != -1 ) + { const point p = points[pLabel]; - points[pLabel] = points[bPoints[bpI]]; + points[pLabel] = points[bPoints[bpI]]; points[bPoints[bpI]] = p; - } - } + } + } } void boundaryLayers::createNewPartitionVerticesParallel ( - const labelListPMG& procPoints, + const labelLongList& procPoints, const List<direction>& pVertices, const boolList& treatPatches ) { if( !Pstream::parRun() ) return; - + if( returnReduce(procPoints.size(), sumOp<label>()) == 0 ) return; - + const meshSurfaceEngine& mse = surfaceEngine(); pointFieldPMG& points = mesh_.points(); const labelList& bPoints = mse.boundaryPoints(); @@ -645,11 +692,11 @@ void boundaryLayers::createNewPartitionVerticesParallel const VRWGraph& bpAtProcs = mse.bpAtProcs(); const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - + scalarField penetrationDistances(bPoints.size(), VGREAT); - + std::map<label, LongList<labelledScalar> > exchangeDistances; - + forAll(procPoints, pointI) { const label bpI = procPoints[pointI]; @@ -658,7 +705,7 @@ void boundaryLayers::createNewPartitionVerticesParallel const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + if( exchangeDistances.find(neiProc) == exchangeDistances.end() ) { exchangeDistances.insert @@ -667,58 +714,66 @@ void boundaryLayers::createNewPartitionVerticesParallel ); } } - + if( pVertices[bpI] & EDGENODE ) continue; - + scalar dist(VGREAT); const point& p = points[bPoints[bpI]]; forAllRow(pointPoints, bpI, ppI) { const scalar d = 0.5 * mag(points[bPoints[pointPoints(bpI, ppI)]] - p); - + if( d < dist ) dist = d; } - + penetrationDistances[bpI] = dist; - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + exchangeDistances[neiProc].append ( labelledScalar(globalPointLabel[bpI], dist) ); } } - + //- exchange distances with other processors LongList<labelledScalar> receivedData; help::exchangeMap(exchangeDistances, receivedData); forAll(receivedData, i) { const label bpI = globalToLocal[receivedData[i].scalarLabel()]; - + if( penetrationDistances[bpI] > receivedData[i].value() ) penetrationDistances[bpI] = receivedData[i].value(); } - + //- Finally, create the points const vectorField& pNormals = mse.pointNormals(); forAll(procPoints, pointI) { const label bpI = procPoints[pointI]; - + if( pVertices[bpI] & EDGENODE ) continue; - + const point& p = points[bPoints[bpI]]; - points[nPoints_] = p - pNormals[bpI] * penetrationDistances[bpI]; + const point np = p - pNormals[bpI] * penetrationDistances[bpI]; + if( !help::isnan(np) && !help::isinf(np) ) + { + points[nPoints_] = np; + } + else + { + points[nPoints_] = p; + } newLabelForVertex_[bPoints[bpI]] = nPoints_; ++nPoints_; } @@ -726,14 +781,14 @@ void boundaryLayers::createNewPartitionVerticesParallel void boundaryLayers::createNewEdgeVerticesParallel ( - const labelListPMG& procPoints, + const labelLongList& procPoints, const List<direction>& pVertices, const boolList& treatPatches ) { if( !Pstream::parRun() ) return; - + if( returnReduce(procPoints.size(), sumOp<label>()) == 0 ) return; @@ -744,9 +799,9 @@ void boundaryLayers::createNewEdgeVerticesParallel const VRWGraph& bpAtProcs = mse.bpAtProcs(); const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - - DynList<label> neiProcs(10); - labelListPMG edgePoints; + + DynList<label> neiProcs; + labelLongList edgePoints; Map<label> bpToEdgePoint; forAll(procPoints, pointI) { @@ -756,51 +811,53 @@ void boundaryLayers::createNewEdgeVerticesParallel const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + neiProcs.appendIfNotIn(neiProc); } - + if( pVertices[bpI] & EDGENODE ) { bpToEdgePoint.insert(bpI, edgePoints.size()); edgePoints.append(bpI); } } - + if( returnReduce(edgePoints.size(), sumOp<label>()) == 0 ) return; - - const VRWGraph& pPatches = mse.pointPatches(); + + const meshSurfacePartitioner& mPart = surfacePartitioner(); + const VRWGraph& pPatches = mPart.pointPatches(); + const VRWGraph& pFaces = mse.pointFaces(); const faceList::subList& bFaces = mse.boundaryFaces(); const labelList& boundaryFacePatches = mse.boundaryFacePatches(); - + scalarField dist(edgePoints.size(), VGREAT); vectorField normal(edgePoints.size(), vector::zero); vectorField v(edgePoints.size(), vector::zero); - - label pKey(-1); - if( patchKey_.size() ) - { - forAll(treatPatches, patchI) - if( treatPatches[patchI] ) - { - pKey = patchKey_[patchI]; - break; - } - } - + + label pKey(-1); + if( patchKey_.size() ) + { + forAll(treatPatches, patchI) + if( treatPatches[patchI] ) + { + pKey = patchKey_[patchI]; + break; + } + } + forAll(edgePoints, epI) { const label bpI = edgePoints[epI]; const point& p = points[bPoints[bpI]]; - + //- find patches for the given point - DynList<label> otherPatches(2); + DynList<label> otherPatches; forAllRow(pPatches, bpI, patchI) if( !treatPatches[pPatches(bpI, patchI)] ) otherPatches.appendIfNotIn(pPatches(bpI, patchI)); - + //- find local values of normals and v if( otherPatches.size() == 1 ) { @@ -809,7 +866,7 @@ void boundaryLayers::createNewEdgeVerticesParallel const face& f = bFaces[pFaces(bpI, pfI)]; const label patchLabel = boundaryFacePatches[pFaces(bpI, pfI)]; - + if( treatPatches[patchLabel] ) { normal[epI] += f.normal(points); @@ -826,7 +883,7 @@ void boundaryLayers::createNewEdgeVerticesParallel forAllRow(pointPoints, bpI, ppI) { const label bpJ = pointPoints(bpI, ppI); - + bool found(true); forAll(otherPatches, opI) if( !pPatches.contains(bpJ, otherPatches[opI]) ) @@ -834,17 +891,17 @@ void boundaryLayers::createNewEdgeVerticesParallel found = false; break; } - + if( found ) { otherVertex = bpJ; break; } } - + if( otherVertex == -1 ) continue; - + //- normal vector is co-linear with that edge normal[epI] = p - points[bPoints[otherVertex]]; dist[epI] = mag(normal[epI]); @@ -854,7 +911,7 @@ void boundaryLayers::createNewEdgeVerticesParallel FatalErrorIn ( "void boundaryLayers::createNewEdgeVerticesParallel(" - "const labelListPMG& procPoints," + "const labelLongList& procPoints," "const List<direction>& pVertices," "const boolList& treatPatches," "labelList& newLabelForVertex" @@ -863,7 +920,7 @@ void boundaryLayers::createNewEdgeVerticesParallel << abort(FatalError); } } - + //- prepare normals and v for sending to other procs std::map<label, LongList<labelledPoint> > exchangeNormals; forAll(neiProcs, procI) @@ -871,17 +928,17 @@ void boundaryLayers::createNewEdgeVerticesParallel ( std::make_pair(neiProcs[procI], LongList<labelledPoint>()) ); - + forAll(edgePoints, epI) { const label bpI = edgePoints[epI]; - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + //- store values in the list for sending LongList<labelledPoint>& dataToSend = exchangeNormals[neiProc]; dataToSend.append @@ -891,7 +948,7 @@ void boundaryLayers::createNewEdgeVerticesParallel dataToSend.append(labelledPoint(globalPointLabel[bpI], v[epI])); } } - + //- exchange data with other processors LongList<labelledPoint> receivedData; help::exchangeMap(exchangeNormals, receivedData); @@ -902,48 +959,46 @@ void boundaryLayers::createNewEdgeVerticesParallel { const labelledPoint& otherNormal = receivedData[counter++]; const labelledPoint& otherV = receivedData[counter++]; - + const label bpI = globalToLocal[otherNormal.pointLabel()]; normal[bpToEdgePoint[bpI]] += otherNormal.coordinates(); v[bpToEdgePoint[bpI]] += otherV.coordinates(); } - + //- calculate normals forAll(normal, epI) { const label bpI = edgePoints[epI]; - + //- find patches for the given point - DynList<label> otherPatches(2); + DynList<label> otherPatches; forAllRow(pPatches, bpI, patchI) if( !treatPatches[pPatches(bpI, patchI)] ) otherPatches.appendIfNotIn(pPatches(bpI, patchI)); - + if( otherPatches.size() == 1 ) { - const scalar magV = mag(v[epI]); - if( magV > VSMALL ) - v[epI] /= magV; + const scalar magV = mag(v[epI]) + VSMALL; + v[epI] /= magV; normal[epI] -= (normal[epI] & v[epI]) * v[epI]; } - - const scalar magN = mag(normal[epI]); - if( magN > VSMALL ) - normal[epI] /= magN; + + const scalar magN = mag(normal[epI]) + VSMALL; + normal[epI] /= magN; } - + //- calculate distances forAll(edgePoints, epI) { const label bpI = edgePoints[epI]; const point& p = points[bPoints[bpI]]; - + //- find patches for the given point - DynList<label> otherPatches(2); + DynList<label> otherPatches; forAllRow(pPatches, bpI, patchI) if( !treatPatches[pPatches(bpI, patchI)] ) otherPatches.appendIfNotIn(pPatches(bpI, patchI)); - + if( otherPatches.size() == 1 ) { forAllRow(pointPoints, bpI, ppI) @@ -953,12 +1008,12 @@ void boundaryLayers::createNewEdgeVerticesParallel const vector vec = points[bPoints[pointPoints(bpI, ppI)]] - p; const scalar prod = 0.5 * mag(vec & normal[epI]); - + if( prod < dist[epI] ) dist[epI] = prod; } } - + //- limit distances forAllRow(pFaces, bpI, pfI) { @@ -967,15 +1022,15 @@ void boundaryLayers::createNewEdgeVerticesParallel { const face& f = bFaces[faceLabel]; const label pos = f.which(bPoints[bpI]); - + if( pos != -1 ) { const point& ep1 = points[f.prevLabel(pos)]; const point& ep2 = points[f.nextLabel(pos)]; - + const scalar dst = help::distanceOfPointFromTheEdge(ep1, ep2, p); - + if( dst < dist[epI] ) dist[epI] = 0.9 * dst; } @@ -985,7 +1040,7 @@ void boundaryLayers::createNewEdgeVerticesParallel ( "void boundaryLayers::createNewEdgeVerticesParallel" "(" - "const labelListPMG& procPoints," + "const labelLongList& procPoints," "const List<direction>& pVertices," "const boolList& treatPatches," "labelList& newLabelForVertex" @@ -996,7 +1051,7 @@ void boundaryLayers::createNewEdgeVerticesParallel } } } - + //- exchange distances with other processors std::map<label, LongList<labelledScalar> > exchangeDistances; forAll(neiProcs, procI) @@ -1004,7 +1059,7 @@ void boundaryLayers::createNewEdgeVerticesParallel ( std::make_pair(neiProcs[procI], LongList<labelledScalar>()) ); - + forAll(edgePoints, epI) { const label bpI = edgePoints[epI]; @@ -1013,12 +1068,12 @@ void boundaryLayers::createNewEdgeVerticesParallel const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + LongList<labelledScalar>& ls = exchangeDistances[neiProc]; ls.append(labelledScalar(globalPointLabel[bpI], dist[epI])); } } - + //- exchange distances with other processors LongList<labelledScalar> receivedDistances; help::exchangeMap(exchangeDistances, receivedDistances); @@ -1031,33 +1086,41 @@ void boundaryLayers::createNewEdgeVerticesParallel if( dist[epI] > receivedDistances[i].value() ) dist[epI] = receivedDistances[i].value(); } - + //- Finally, create new points forAll(edgePoints, epI) { const label bpI = edgePoints[epI]; - + const point& p = points[bPoints[bpI]]; - points[nPoints_] = p - normal[epI] * dist[epI]; - - if( pKey == -1 ) - { - //- extrusion for one patch in a single go - newLabelForVertex_[bPoints[bpI]] = nPoints_; - } - else - { - const label pointI = bPoints[bpI]; - - if( otherVrts_.find(pointI) == otherVrts_.end() ) - { - std::map<std::pair<label, label>, label> m; - otherVrts_.insert(std::make_pair(pointI, m)); - } - - std::pair<label, label> pr(pKey, pKey); - otherVrts_[pointI].insert(std::make_pair(pr, nPoints_)); - } + const point np = p - normal[epI] * dist[epI]; + if( !help::isnan(np) && !help::isinf(np) ) + { + points[nPoints_] = np; + } + else + { + points[nPoints_] = p; + } + + if( pKey == -1 ) + { + //- extrusion for one patch in a single go + newLabelForVertex_[bPoints[bpI]] = nPoints_; + } + else + { + const label pointI = bPoints[bpI]; + + if( otherVrts_.find(pointI) == otherVrts_.end() ) + { + std::map<std::pair<label, label>, label> m; + otherVrts_.insert(std::make_pair(pointI, m)); + } + + std::pair<label, label> pr(pKey, pKey); + otherVrts_[pointI].insert(std::make_pair(pr, nPoints_)); + } ++nPoints_; } } diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayersFacesAndCells.C b/meshLibrary/utilities/boundaryLayers/boundaryLayersFacesAndCells.C index 312abe0bb4418bf00429f2a1fed3f4ba3625afcb..e298a37e7557cb59729553887b51abbe0632d035 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayersFacesAndCells.C +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayersFacesAndCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,8 +35,6 @@ Description //#define DEBUGLayer -#include "writeMeshFPMA.H" - // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam @@ -47,76 +44,77 @@ namespace Foam void boundaryLayers::createNewFacesAndCells(const boolList& treatPatches) { - Info << "Starting creating layer cells" << endl; - + Info << "Starting creating layer cells" << endl; + const meshSurfaceEngine& mse = surfaceEngine(); - const faceList::subList& bFaces = mse.boundaryFaces(); - const VRWGraph& faceEdges = mse.faceEdges(); - const VRWGraph& edgeFaces = mse.edgeFaces(); - const labelList& boundaryFacePatches = mse.boundaryFacePatches(); - const labelList& faceOwners = mse.faceOwners(); - + const faceList::subList& bFaces = mse.boundaryFaces(); + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const labelList& boundaryFacePatches = mse.boundaryFacePatches(); + const labelList& faceOwners = mse.faceOwners(); + //- this is used for parallel runs const Map<label>* otherProcPatchPtr(NULL); - + if( Pstream::parRun() ) { createNewFacesParallel(treatPatches); - + otherProcPatchPtr = &mse.otherEdgeFacePatch(); } - - //- create lists for new boundary faces - VRWGraph newBoundaryFaces; - labelListPMG newBoundaryOwners; - labelListPMG newBoundaryPatches; - + + //- create lists for new boundary faces + VRWGraph newBoundaryFaces; + labelLongList newBoundaryOwners; + labelLongList newBoundaryPatches; + //- create storage for new cells - VRWGraphList cellsToAdd; - - //- create layer cells and store boundary faces - const label nOldCells = mesh_.cells().size(); - forAll(bFaces, bfI) - if( treatPatches[boundaryFacePatches[bfI]] ) - { - const face& f = bFaces[bfI]; - - faceList cellFaces(f.size() + 2); - - direction fI(0); - //- store boundary face - cellFaces[fI++] = f.reverseFace(); - - //- create parallel face - face newF(f.size()); - forAll(f, pI) - newF[pI] = newLabelForVertex_[f[pI]]; - cellFaces[fI++] = newF; - - newBoundaryFaces.appendList(newF); - newBoundaryOwners.append(cellsToAdd.size() + nOldCells); - newBoundaryPatches.append(boundaryFacePatches[bfI]); - - //- create quad faces - newF.setSize(4); - forAll(f, pI) - { - newF[0] = f[pI]; - newF[1] = f.nextLabel(pI); - newF[2] = newLabelForVertex_[f.nextLabel(pI)]; - newF[3] = newLabelForVertex_[f[pI]]; - - cellFaces[fI++] = newF; - - //- check if the face is at the boundary + VRWGraphList cellsToAdd; + + //- create layer cells and store boundary faces + const label nOldCells = mesh_.cells().size(); + forAll(bFaces, bfI) + if( treatPatches[boundaryFacePatches[bfI]] ) + { + const face& f = bFaces[bfI]; + + faceList cellFaces(f.size() + 2); + + label fI(0); + + //- store boundary face + cellFaces[fI++] = f.reverseFace(); + + //- create parallel face + face newF(f.size()); + forAll(f, pI) + newF[pI] = newLabelForVertex_[f[pI]]; + cellFaces[fI++] = newF; + + newBoundaryFaces.appendList(newF); + newBoundaryOwners.append(cellsToAdd.size() + nOldCells); + newBoundaryPatches.append(boundaryFacePatches[bfI]); + + //- create quad faces + newF.setSize(4); + forAll(f, pI) + { + newF[0] = f[pI]; + newF[1] = f.nextLabel(pI); + newF[2] = newLabelForVertex_[f.nextLabel(pI)]; + newF[3] = newLabelForVertex_[f[pI]]; + + cellFaces[fI++] = newF; + + //- check if the face is at the boundary //- of the treated partitions - const label edgeI = faceEdges(bfI, pI); + const label edgeI = faceEdges(bfI, pI); if( edgeFaces.sizeOfRow(edgeI) == 2 ) { label neiFace = edgeFaces(edgeI, 0); if( neiFace == bfI ) neiFace = edgeFaces(edgeI, 1); - + if( !treatPatches[boundaryFacePatches[neiFace]] ) { newBoundaryFaces.appendList(newF); @@ -134,49 +132,49 @@ void boundaryLayers::createNewFacesAndCells(const boolList& treatPatches) newBoundaryPatches.append(otherProcPatch[edgeI]); } } - } - + } + cellsToAdd.appendGraph(cellFaces); - } - else - { - # ifdef DEBUGLayer - Info << "Storing original boundary face " - << bfI << " into patch " << boundaryFacePatches[bfI] << endl; - # endif - - newBoundaryFaces.appendList(bFaces[bfI]); - newBoundaryOwners.append(faceOwners[bfI]); - newBoundaryPatches.append(boundaryFacePatches[bfI]); - } - + } + else + { + # ifdef DEBUGLayer + Info << "Storing original boundary face " + << bfI << " into patch " << boundaryFacePatches[bfI] << endl; + # endif + + newBoundaryFaces.appendList(bFaces[bfI]); + newBoundaryOwners.append(faceOwners[bfI]); + newBoundaryPatches.append(boundaryFacePatches[bfI]); + } + //- create mesh modifier - polyMeshGenModifier meshModifier(mesh_); - + polyMeshGenModifier meshModifier(mesh_); + meshModifier.addCells(cellsToAdd); cellsToAdd.clear(); - meshModifier.reorderBoundaryFaces(); - meshModifier.replaceBoundary - ( - patchNames_, - newBoundaryFaces, - newBoundaryOwners, - newBoundaryPatches - ); - + meshModifier.reorderBoundaryFaces(); + meshModifier.replaceBoundary + ( + patchNames_, + newBoundaryFaces, + newBoundaryOwners, + newBoundaryPatches + ); + //- delete meshSurfaceEngine this->clearOut(); - # ifdef DEBUGLayer - mesh_.addressingData().checkMesh(true); - # endif - - Info << "Finished creating layer cells" << endl; + # ifdef DEBUGLayer + mesh_.addressingData().checkMesh(true); + # endif + + Info << "Finished creating layer cells" << endl; } void boundaryLayers::createNewFacesParallel ( - const boolList& treatPatches + const boolList& treatPatches ) { const meshSurfaceEngine& mse = surfaceEngine(); @@ -186,7 +184,7 @@ void boundaryLayers::createNewFacesParallel const labelList& boundaryFacePatches = mse.boundaryFacePatches(); const labelList& globalEdgeLabel = mse.globalBoundaryEdgeLabel(); const Map<label>& globalToLocal = mse.globalToLocalBndEdgeAddressing(); - + const Map<label>& otherProcPatch = mse.otherEdgeFacePatch(); const Map<label>& otherFaceProc = mse.otherEdgeFaceAtProc(); @@ -199,10 +197,10 @@ void boundaryLayers::createNewFacesParallel Map<label> otherProcToProcPatch; forAll(mesh_.procBoundaries(), patchI) { - const writeProcessorPatch& wp = mesh_.procBoundaries()[patchI]; + const processorBoundaryPatch& wp = mesh_.procBoundaries()[patchI]; otherProcToProcPatch.insert(wp.neiProcNo(), patchI); } - + label nTreatedEdges(0); boolList treatEdge(edgeFaces.size(), false); for @@ -213,10 +211,10 @@ void boundaryLayers::createNewFacesParallel ) { const label beI = iter(); - + if( edgeFaces.sizeOfRow(beI) != 1 ) continue; - + if( treatPatches[boundaryFacePatches[edgeFaces(beI, 0)]] && treatPatches[otherProcPatch[beI]] @@ -226,7 +224,7 @@ void boundaryLayers::createNewFacesParallel treatEdge[beI] = true; } } - + //- create a list of treated edges and sort the list labelList treatedEdgeLabels(nTreatedEdges); nTreatedEdges = 0; @@ -238,36 +236,36 @@ void boundaryLayers::createNewFacesParallel treatedEdgeLabels.setSize(nTreatedEdges); sort(treatedEdgeLabels); - + //- create additional processor patches if needed forAll(treatedEdgeLabels, eI) { const label beI = globalToLocal[treatedEdgeLabels[eI]]; - + if( !otherProcToProcPatch.found(otherFaceProc[beI]) ) { - otherProcToProcPatch.insert - ( - otherFaceProc[beI], - polyMeshGenModifier(mesh_).addProcessorPatch - ( - otherFaceProc[beI] - ) - ); + otherProcToProcPatch.insert + ( + otherFaceProc[beI], + polyMeshGenModifier(mesh_).addProcessorPatch + ( + otherFaceProc[beI] + ) + ); } } - + //- create new processor faces VRWGraph newProcFaces; - labelListPMG faceProcPatch; + labelLongList faceProcPatch; FixedList<label, 4> newF; forAll(treatedEdgeLabels, geI) { const label beI = globalToLocal[treatedEdgeLabels[geI]]; - - if( edgeFaces.sizeOfRow(beI) == 0 ) - continue; - + + if( edgeFaces.sizeOfRow(beI) == 0 ) + continue; + const label bfI = edgeFaces(beI, 0); const label pos = faceEdges.containsAtPosition(bfI, beI); const edge e = bFaces[bfI].faceEdge(pos); @@ -276,49 +274,49 @@ void boundaryLayers::createNewFacesParallel { newF[0] = e.start(); newF[1] = e.end(); - if( patchKey_.size() != 0 ) - { - newF[2] = - findNewNodeLabel(e.end(), patchKey_[otherProcPatch[beI]]); - newF[3] = - findNewNodeLabel(e.start(), patchKey_[otherProcPatch[beI]]); - } - else - { - newF[2] = newLabelForVertex_[e.end()]; - newF[3] = newLabelForVertex_[e.start()]; - } + if( patchKey_.size() != 0 ) + { + newF[2] = + findNewNodeLabel(e.end(), patchKey_[otherProcPatch[beI]]); + newF[3] = + findNewNodeLabel(e.start(), patchKey_[otherProcPatch[beI]]); + } + else + { + newF[2] = newLabelForVertex_[e.end()]; + newF[3] = newLabelForVertex_[e.start()]; + } } else { newF[0] = e.end(); - if( patchKey_.size() != 0 ) - { - newF[1] = - findNewNodeLabel + if( patchKey_.size() != 0 ) + { + newF[1] = + findNewNodeLabel ( e.end(), patchKey_[boundaryFacePatches[bfI]] ); - newF[2] = - findNewNodeLabel - ( - e.start(), - patchKey_[boundaryFacePatches[bfI]] - ); - } - else - { - newF[1] = newLabelForVertex_[e.end()]; - newF[2] = newLabelForVertex_[e.start()]; - } + newF[2] = + findNewNodeLabel + ( + e.start(), + patchKey_[boundaryFacePatches[bfI]] + ); + } + else + { + newF[1] = newLabelForVertex_[e.end()]; + newF[2] = newLabelForVertex_[e.start()]; + } newF[3] = e.start(); } - + newProcFaces.appendList(newF); faceProcPatch.append(otherProcToProcPatch[otherFaceProc[beI]]); } - + //- add faces into the mesh polyMeshGenModifier(mesh_).addProcessorFaces(newProcFaces, faceProcPatch); } diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayersI.H b/meshLibrary/utilities/boundaryLayers/boundaryLayersI.H index 539421565d5739ecba4f6a768eacb82992f98776..ee7b8fcc54d0fdf3f9e45f66fe9a728a3dc58fbb 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayersI.H +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayersI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,267 +36,260 @@ namespace Foam label boundaryLayers::findNewNodeLabel ( - const label pointI, - const label pKey + const label pointI, + const label pKey ) const { - if( otherVrts_.find(pointI) != otherVrts_.end() ) - { - const std::map - < - label, std::map<std::pair<label, label>, label> - >::const_iterator it = otherVrts_.find(pointI); - const std::map<std::pair<label, label>, label>& m = it->second; + if( otherVrts_.find(pointI) != otherVrts_.end() ) + { + const std::map + < + label, std::map<std::pair<label, label>, label> + >::const_iterator it = otherVrts_.find(pointI); + const std::map<std::pair<label, label>, label>& m = it->second; - std::map<std::pair<label, label>, label>::const_iterator mit; - if( m.size() == 2 ) - { - for(mit=m.begin();mit!=m.end();++mit) - { - if( mit->first.first != pKey ) - return mit->second; - } - } - else - { - for(mit=m.begin();mit!=m.end();++mit) - { - if( mit->first.first == pKey ) - continue; - if( mit->first.second == pKey ) - continue; - if( mit->first.first == mit->first.second ) - continue; - - return mit->second; - } - } - } + std::map<std::pair<label, label>, label>::const_iterator mit; + if( m.size() == 2 ) + { + for(mit=m.begin();mit!=m.end();++mit) + { + if( mit->first.first != pKey ) + return mit->second; + } + } + else + { + for(mit=m.begin();mit!=m.end();++mit) + { + if( mit->first.first == pKey ) + continue; + if( mit->first.second == pKey ) + continue; + if( mit->first.first == mit->first.second ) + continue; + + return mit->second; + } + } + } - return newLabelForVertex_[pointI]; + return newLabelForVertex_[pointI]; } inline void boundaryLayers::createNewCellFromEdge ( - const edge& e, - const label pKeyI, - const label pKeyJ, - DynList<DynList<label, 4>, 6>& cellFaces + const edge& e, + const label pKeyI, + const label pKeyJ, + FixedList<FixedList<label, 4>, 6>& cellFaces ) const { - const std::map<std::pair<label, label>, label>& ms = - otherVrts_.find(e.start())->second; - const std::map<std::pair<label, label>, label>& me = - otherVrts_.find(e.end())->second; - - # ifdef DEBUGLayer - Info << "Creating cell for edge " << edgeI << " with nodes " << e << endl; - Info << "pKeyI " << pKeyI << endl; - Info << "pKeyJ " << pKeyJ << endl; - std::map<std::pair<label, label>, label>::const_iterator iter; - for(iter=ms.begin();iter!=ms.end();++iter) - Info << "1. Pair (" << iter->first.first << ", " - << iter->first.second << ") has value " << iter->second << endl; - for(iter=me.begin();iter!=me.end();++iter) - Info << "2. Pair (" << iter->first.first << ", " - << iter->first.second << ") has value " << iter->second << endl; - # endif - - label p0s(-1), p1s(-1), ns(-1), p0e(-1), p1e(-1), ne(-1); - - if( ms.size() == 2 ) - { - p0s = ms.find(std::pair<label, label>(pKeyI, pKeyI))->second; - p1s = ms.find(std::pair<label, label>(pKeyJ, pKeyJ))->second; - ns = newLabelForVertex_[e.start()]; - } - else - { - std::map<std::pair<label, label>, label>::const_iterator it; - for(it=ms.begin();it!=ms.end();++it) - { - if( - (it->first.first != pKeyJ) && (it->first.second != pKeyJ) - && (it->first.first != it->first.second) - ) - { - p0s = it->second; - } - else if( - (it->first.first != pKeyI) && (it->first.second != pKeyI) - && (it->first.first != it->first.second) - ) - { - p1s = it->second; - } - else if( - (it->first.first == it->first.second) && - (it->first.first != pKeyI) && (it->first.first != pKeyJ) - ) - { - ns = it->second; - } - } - } - if( me.size() == 2 ) - { - p0e = me.find(std::pair<label, label>(pKeyI, pKeyI))->second; - p1e = me.find(std::pair<label, label>(pKeyJ, pKeyJ))->second; - ne = newLabelForVertex_[e.end()]; - } - else - { - std::map<std::pair<label, label>, label>::const_iterator it; - for(it=me.begin();it!=me.end();++it) - { - if( - (it->first.first != pKeyJ) && (it->first.second != pKeyJ) - && (it->first.first != it->first.second) - ) - { - p0e = it->second; - } - else if( - (it->first.first != pKeyI) && (it->first.second != pKeyI) - && (it->first.first != it->first.second) - ) - { - p1e = it->second; - } - else if( - (it->first.first == it->first.second) && - (it->first.first != pKeyI) && (it->first.first != pKeyJ) - ) - { - ne = it->second; - } - } - } - - cellFaces.setSize(6); - DynList<label, 4> f; - f.setSize(4); - //- F0 - f[0] = e.end(); - f[1] = e.start(); - f[2] = p1s; - f[3] = p1e; - cellFaces[0] = f; - //- F1 - f[0] = p0e; - f[1] = ne; - f[2] = ns; - f[3] = p0s; - cellFaces[1] = f; - //- F2 - f[0] = e.start(); - f[1] = e.end(); - f[2] = p0e; - f[3] = p0s; - cellFaces[2] = f; - //- F3 - f[0] = p1s; - f[1] = ns; - f[2] = ne; - f[3] = p1e; - cellFaces[3] = f; - //- F4 - f[0] = e.end(); - f[1] = p1e; - f[2] = ne; - f[3] = p0e; - cellFaces[4] = f; - //- F5 - f[0] = e.start(); - f[1] = p0s; - f[2] = ns; - f[3] = p1s; - cellFaces[5] = f; + const std::map<std::pair<label, label>, label>& ms = + otherVrts_.find(e.start())->second; + const std::map<std::pair<label, label>, label>& me = + otherVrts_.find(e.end())->second; + + # ifdef DEBUGLayer + Info << "Creating cell for edge " << edgeI << " with nodes " << e << endl; + Info << "pKeyI " << pKeyI << endl; + Info << "pKeyJ " << pKeyJ << endl; + std::map<std::pair<label, label>, label>::const_iterator iter; + for(iter=ms.begin();iter!=ms.end();++iter) + Info << "1. Pair (" << iter->first.first << ", " + << iter->first.second << ") has value " << iter->second << endl; + for(iter=me.begin();iter!=me.end();++iter) + Info << "2. Pair (" << iter->first.first << ", " + << iter->first.second << ") has value " << iter->second << endl; + # endif + + label p0s(-1), p1s(-1), ns(-1), p0e(-1), p1e(-1), ne(-1); + + if( ms.size() == 2 ) + { + p0s = ms.find(std::pair<label, label>(pKeyI, pKeyI))->second; + p1s = ms.find(std::pair<label, label>(pKeyJ, pKeyJ))->second; + ns = newLabelForVertex_[e.start()]; + } + else + { + std::map<std::pair<label, label>, label>::const_iterator it; + for(it=ms.begin();it!=ms.end();++it) + { + if( + (it->first.first != pKeyJ) && (it->first.second != pKeyJ) + && (it->first.first != it->first.second) + ) + { + p0s = it->second; + } + else if( + (it->first.first != pKeyI) && (it->first.second != pKeyI) + && (it->first.first != it->first.second) + ) + { + p1s = it->second; + } + else if( + (it->first.first == it->first.second) && + (it->first.first != pKeyI) && (it->first.first != pKeyJ) + ) + { + ns = it->second; + } + } + } + if( me.size() == 2 ) + { + p0e = me.find(std::pair<label, label>(pKeyI, pKeyI))->second; + p1e = me.find(std::pair<label, label>(pKeyJ, pKeyJ))->second; + ne = newLabelForVertex_[e.end()]; + } + else + { + std::map<std::pair<label, label>, label>::const_iterator it; + for(it=me.begin();it!=me.end();++it) + { + if( + (it->first.first != pKeyJ) && (it->first.second != pKeyJ) + && (it->first.first != it->first.second) + ) + { + p0e = it->second; + } + else if( + (it->first.first != pKeyI) && (it->first.second != pKeyI) + && (it->first.first != it->first.second) + ) + { + p1e = it->second; + } + else if( + (it->first.first == it->first.second) && + (it->first.first != pKeyI) && (it->first.first != pKeyJ) + ) + { + ne = it->second; + } + } + } + + //- F0 + cellFaces[0][0] = e.end(); + cellFaces[0][1] = e.start(); + cellFaces[0][2] = p1s; + cellFaces[0][3] = p1e; + + //- F1 + cellFaces[1][0] = p0e; + cellFaces[1][1] = ne; + cellFaces[1][2] = ns; + cellFaces[1][3] = p0s; + + //- F2 + cellFaces[2][0] = e.start(); + cellFaces[2][1] = e.end(); + cellFaces[2][2] = p0e; + cellFaces[2][3] = p0s; + + //- F3 + cellFaces[3][0] = p1s; + cellFaces[3][1] = ns; + cellFaces[3][2] = ne; + cellFaces[3][3] = p1e; + + //- F4 + cellFaces[4][0] = e.end(); + cellFaces[4][1] = p1e; + cellFaces[4][2] = ne; + cellFaces[4][3] = p0e; + + //- F5 + cellFaces[5][0] = e.start(); + cellFaces[5][1] = p0s; + cellFaces[5][2] = ns; + cellFaces[5][3] = p1s; } inline void boundaryLayers::createNewCellFromNode ( - const label pointI, - const DynList<label, 3>& pKeys, - DynList<DynList<label, 4>, 6>& cellFaces + const label pointI, + const DynList<label, 3>& pKeys, + FixedList<FixedList<label, 4>, 6>& cellFaces ) const { - const std::map<std::pair<label, label>, label>& m = - otherVrts_.find(pointI)->second; - - //- create labels before creating cells - const label n = newLabelForVertex_[pointI]; - const label p00 = - m.find(std::pair<label, label>(pKeys[0], pKeys[0]))->second; - const label p11 = - m.find(std::pair<label, label>(pKeys[1], pKeys[1]))->second; - const label p22 = - m.find(std::pair<label, label>(pKeys[2], pKeys[2]))->second; + const std::map<std::pair<label, label>, label>& m = + otherVrts_.find(pointI)->second; + + //- create labels before creating cells + const label n = newLabelForVertex_[pointI]; + const label p00 = + m.find(std::pair<label, label>(pKeys[0], pKeys[0]))->second; + const label p11 = + m.find(std::pair<label, label>(pKeys[1], pKeys[1]))->second; + const label p22 = + m.find(std::pair<label, label>(pKeys[2], pKeys[2]))->second; - std::pair<label, label> pr; - pr.first = pKeys[0]; - pr.second = pKeys[1]; - if( m.find(pr) == m.end() ) - { - pr.first = pKeys[1]; - pr.second = pKeys[0]; - } - const label p01 = m.find(pr)->second; - - pr.first = pKeys[0]; - pr.second = pKeys[2]; - if( m.find(pr) == m.end() ) - { - pr.first = pKeys[2]; - pr.second = pKeys[0]; - } - const label p02 = m.find(pr)->second; - - pr.first = pKeys[1]; - pr.second = pKeys[2]; - if( m.find(pr) == m.end() ) - { - pr.first = pKeys[2]; - pr.second = pKeys[1]; - } - const label p12 = m.find(pr)->second; - - //- create the cell and append it - cellFaces.setSize(6); - forAll(cellFaces, fI) - cellFaces[fI].setSize(4); + std::pair<label, label> pr; + pr.first = pKeys[0]; + pr.second = pKeys[1]; + if( m.find(pr) == m.end() ) + { + pr.first = pKeys[1]; + pr.second = pKeys[0]; + } + const label p01 = m.find(pr)->second; + + pr.first = pKeys[0]; + pr.second = pKeys[2]; + if( m.find(pr) == m.end() ) + { + pr.first = pKeys[2]; + pr.second = pKeys[0]; + } + const label p02 = m.find(pr)->second; + + pr.first = pKeys[1]; + pr.second = pKeys[2]; + if( m.find(pr) == m.end() ) + { + pr.first = pKeys[2]; + pr.second = pKeys[1]; + } + const label p12 = m.find(pr)->second; + + //- create the cell and append it - //- F0 - cellFaces[0][0] = pointI; - cellFaces[0][1] = p02; - cellFaces[0][2] = p00; - cellFaces[0][3] = p01; - //- F1 - cellFaces[1][0] = p12; - cellFaces[1][1] = p11; - cellFaces[1][2] = n; - cellFaces[1][3] = p22; + //- F0 + cellFaces[0][0] = pointI; + cellFaces[0][1] = p02; + cellFaces[0][2] = p00; + cellFaces[0][3] = p01; + //- F1 + cellFaces[1][0] = p12; + cellFaces[1][1] = p11; + cellFaces[1][2] = n; + cellFaces[1][3] = p22; - //- F2 - cellFaces[2][0] = pointI; - cellFaces[2][1] = p01; - cellFaces[2][2] = p11; - cellFaces[2][3] = p12; - //- F3 - cellFaces[3][0] = p02; - cellFaces[3][1] = p22; - cellFaces[3][2] = n; - cellFaces[3][3] = p00; - //- F4 - cellFaces[4][0] = pointI; - cellFaces[4][1] = p12; - cellFaces[4][2] = p22; - cellFaces[4][3] = p02; - //- F5 - cellFaces[5][0] = p01; - cellFaces[5][1] = p00; - cellFaces[5][2] = n; - cellFaces[5][3] = p11; + //- F2 + cellFaces[2][0] = pointI; + cellFaces[2][1] = p01; + cellFaces[2][2] = p11; + cellFaces[2][3] = p12; + //- F3 + cellFaces[3][0] = p02; + cellFaces[3][1] = p22; + cellFaces[3][2] = n; + cellFaces[3][3] = p00; + //- F4 + cellFaces[4][0] = pointI; + cellFaces[4][1] = p12; + cellFaces[4][2] = p22; + cellFaces[4][3] = p02; + //- F5 + cellFaces[5][0] = p01; + cellFaces[5][1] = p00; + cellFaces[5][2] = n; + cellFaces[5][3] = p11; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/boundaryLayers/boundaryLayersWrapperLayer.C b/meshLibrary/utilities/boundaryLayers/boundaryLayersWrapperLayer.C index 61c381e14d1c8cf8b4c607ad8cba586301fd8784..5e83bc48a2b67788079a51114ded21f276909090 100644 --- a/meshLibrary/utilities/boundaryLayers/boundaryLayersWrapperLayer.C +++ b/meshLibrary/utilities/boundaryLayers/boundaryLayersWrapperLayer.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -34,36 +33,36 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void boundaryLayers::addWrapperLayer() { - createOTopologyLayers(); - - if( treatedPatch_[0] ) return; + createOTopologyLayers(); + + if( treatedPatch_[0] ) return; - const meshSurfaceEngine& mse = surfaceEngine(); - - const labelList& bPoints = mse.boundaryPoints(); - - boolList treatPatches(mesh_.boundaries().size(), true); - - labelListPMG newLabelForVertex(nPoints_, -1); + const meshSurfaceEngine& mse = surfaceEngine(); + + const labelList& bPoints = mse.boundaryPoints(); + + boolList treatPatches(mesh_.boundaries().size(), true); + + labelLongList newLabelForVertex(nPoints_, -1); - pointFieldPMG& points = mesh_.points(); - points.setSize(points.size() + bPoints.size()); - forAll(bPoints, bpI) - { - points[nPoints_] = points[bPoints[bpI]]; - newLabelForVertex[bPoints[bpI]] = nPoints_++; - } - - createNewFacesAndCells(treatPatches); - - forAll(treatPatches, patchI) - if( treatPatches[patchI] ) - treatedPatch_[patchI] = true; + pointFieldPMG& points = mesh_.points(); + points.setSize(points.size() + bPoints.size()); + forAll(bPoints, bpI) + { + points[nPoints_] = points[bPoints[bpI]]; + newLabelForVertex[bPoints[bpI]] = nPoints_++; + } + + createNewFacesAndCells(treatPatches); + + forAll(treatPatches, patchI) + if( treatPatches[patchI] ) + treatedPatch_[patchI] = true; //- delete surface engine clearOut(); diff --git a/meshLibrary/utilities/boundaryLayers/extrudeLayer.C b/meshLibrary/utilities/boundaryLayers/extrudeLayer.C index 509f2c2682cc471a5d60fa9ade26dff7dd1199a5..ebbd5600c373e88cb3affa27407125e29cf0b129 100644 --- a/meshLibrary/utilities/boundaryLayers/extrudeLayer.C +++ b/meshLibrary/utilities/boundaryLayers/extrudeLayer.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,13 +29,14 @@ Description #include "helperFunctions.H" #include "polyMeshGenAddressing.H" #include "meshSurfaceEngine.H" +#include "meshSurfacePartitioner.H" #include "labelledPointScalar.H" +# ifdef USE_OMP #include <omp.h> +# endif #ifdef DEBUGExtrudeLayer -#include "writeMeshFPMA.H" -#include "writeMeshFLMA.H" #include "polyMeshGenChecks.H" #endif @@ -109,7 +109,9 @@ void extrudeLayer::createDuplicateFrontFaces(const LongList<labelPair>& front) extrudedFaces_.setSize(counter); pairOrientation_.setSize(counter); + # ifdef USE_OMP # pragma omp parallel for if( faceInFront.size() > 100 ) schedule(guided) + # endif forAll(faceInFront, faceI) { if( faceInFront[faceI] < 0 ) @@ -173,7 +175,9 @@ void extrudeLayer::createDuplicateFrontFaces(const LongList<labelPair>& front) } //- renumber the cells + # ifdef USE_OMP # pragma omp parallel for if( faceInFront.size() > 100 ) schedule(guided) + # endif forAll(faceInFront, faceI) { if( faceInFront[faceI] < 0 ) @@ -215,7 +219,9 @@ void extrudeLayer::createNewVertices() //- find the points in the marked front List<direction> frontPoints(points.size(), NONE); + # ifdef USE_OMP # pragma omp parallel for if( points.size() > 1000 ) schedule(guided) + # endif forAll(extrudedFaces_, efI) { const face& f = faces[extrudedFaces_[efI].first()]; @@ -233,9 +239,9 @@ void extrudeLayer::createNewVertices() const DynList<label>& pProcs = addr.pointNeiProcs(); //- allocate the map - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAll(pProcs, i) - exchangeData.insert(std::make_pair(pProcs[i], labelListPMG())); + exchangeData.insert(std::make_pair(pProcs[i], labelLongList())); //- collect the information about markes points at processor boundaries forAllConstIter(Map<label>, globalToLocal, it) @@ -258,8 +264,10 @@ void extrudeLayer::createNewVertices() LongList<label> receivedData; help::exchangeMap(exchangeData, receivedData); + # ifdef USE_OMP # pragma omp parallel for if( receivedData.size() > 1000 ) \ schedule(guided) + # endif forAll(receivedData, i) { frontPoints[globalToLocal[receivedData[i]]] = @@ -287,14 +295,14 @@ void extrudeLayer::createNewVertices() } //- create new vertices at processor boundaries - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); const polyMeshGenAddressing& addr = mesh_.addressingData(); const VRWGraph& pAtProcs = addr.pointAtProcs(); - const labelListPMG& globalPointLabel = addr.globalPointLabel(); + const labelLongList& globalPointLabel = addr.globalPointLabel(); const Map<label>& globalToLocal = addr.globalToLocalPointAddressing(); const DynList<label>& pProcs = addr.pointNeiProcs(); - const labelListPMG& globalCellLabel = addr.globalCellLabel(); + const labelLongList& globalCellLabel = addr.globalCellLabel(); //- create the information which faces are attached to points //- at parallel boundaries in dual form where each edge represents @@ -415,9 +423,9 @@ void extrudeLayer::createNewVertices() returnReduce(1, sumOp<label>()); Pout << "Exchanging data with other processors" << endl; - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAll(pProcs, i) - exchangeData.insert(std::make_pair(pProcs[i], labelListPMG())); + exchangeData.insert(std::make_pair(pProcs[i], labelLongList())); //- fill in the exchangeData map forAllConstIter(dualEdgesMap, procPointsDual, dIter) @@ -431,7 +439,7 @@ void extrudeLayer::createNewVertices() if( neiProc == Pstream::myProcNo() ) continue; - labelListPMG& dts = exchangeData[neiProc]; + labelLongList& dts = exchangeData[neiProc]; dts.append(globalPointLabel[pointI]); @@ -447,7 +455,7 @@ void extrudeLayer::createNewVertices() } //- exchange data with other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); //- update local data @@ -714,7 +722,6 @@ void extrudeLayer::createNewVertices() mesh_.addPointToSubset(frontID, pI); } - writeMeshFLMA(mesh_, "withNewVertices"); returnReduce(1, sumOp<label>()); //::exit(1); # endif @@ -836,10 +843,14 @@ void extrudeLayer::movePoints() } } + # ifdef USE_OMP # pragma omp parallel if( displacements.size() > 100 ) + # endif { //- find displacement vectors + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(displacements, pI) { if( pointAtProcBnd[pI] ) @@ -889,15 +900,19 @@ void extrudeLayer::movePoints() displacements[pI] = normal * thickness; } + # ifdef USE_OMP # pragma omp barrier + # endif + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(displacements, pI) points[nOrigPoints_+pI] += displacements[pI]; } # ifdef DEBUGExtrudeLayer - writeMeshFPMA(mesh_, "movedPoints"); + mesh_.write(); returnReduce(1, sumOp<label>()); //::exit(1); # endif @@ -909,7 +924,7 @@ void extrudeLayer::createNewFacesParallel() return; VRWGraph newProcFaces; - labelListPMG faceProcPatch; + labelLongList faceProcPatch; //- add faces into the mesh polyMeshGenModifier(mesh_).addProcessorFaces(newProcFaces, faceProcPatch); @@ -1210,15 +1225,17 @@ void extrudeLayer::updateBoundary() patchNames[patchI] = mesh_.boundaries()[patchI].patchName(); VRWGraph newBoundaryFaces; - labelListPMG newBoundaryOwners; - labelListPMG newBoundaryPatches; + labelLongList newBoundaryOwners; + labelLongList newBoundaryPatches; meshSurfaceEngine mse(mesh_); const faceList::subList& bFaces = mse.boundaryFaces(); const labelList& bfOwner = mse.faceOwners(); const labelList& facePatch = mse.boundaryFacePatches(); const labelList& bp = mse.bp(); - const VRWGraph& pointPatches = mse.pointPatches(); + + meshSurfacePartitioner mPart(mse); + const VRWGraph& pointPatches = mPart.pointPatches(); //- store existing boundary faces. They remain in the mesh forAll(bFaces, bfI) diff --git a/meshLibrary/utilities/boundaryLayers/extrudeLayer.H b/meshLibrary/utilities/boundaryLayers/extrudeLayer.H index e048610b649ab741611930e41b6e3d3420751792..70548df6b99ec440d8eab5a25dcb1fffe9575691 100644 --- a/meshLibrary/utilities/boundaryLayers/extrudeLayer.H +++ b/meshLibrary/utilities/boundaryLayers/extrudeLayer.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005- Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class extrudeLayer @@ -77,9 +76,9 @@ class extrudeLayer LongList<bool> pairOrientation_; //- original point label - labelListPMG origPointLabel_; - - // Private member functions + labelLongList origPointLabel_; + + // Private member functions //- duplicate faces which will be extruded void createDuplicateFrontFaces(const LongList<labelPair>&); @@ -184,11 +183,11 @@ class extrudeLayer //- Disallow bitwise assignment void operator=(const extrudeLayer&); - + public: - + // Constructors - + //- Construct from mesh, extrusion faces, thickness and number of layers extrudeLayer ( @@ -196,11 +195,11 @@ class extrudeLayer const LongList<labelPair>& extrusionFront, const scalar thickness = -1.0 ); - - // Destructor + + // Destructor ~extrudeLayer(); - - // Public member functions + + // Public member functions }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/boundaryLayers/extrudeLayerI.H b/meshLibrary/utilities/boundaryLayers/extrudeLayerI.H index a89b71d856c7c115275e514a1628464c7b378103..1ccb1a0825c4cddfd28e42dc5e2c89ec6eed5946 100644 --- a/meshLibrary/utilities/boundaryLayers/extrudeLayerI.H +++ b/meshLibrary/utilities/boundaryLayers/extrudeLayerI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/boundaryLayers/refineBoundaryLayers.C b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayers.C new file mode 100644 index 0000000000000000000000000000000000000000..05632a5ede58a581e639da12694ed91f10eafd57 --- /dev/null +++ b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayers.C @@ -0,0 +1,357 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "refineBoundaryLayers.H" +#include "meshSurfaceEngine.H" +#include "demandDrivenData.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +const meshSurfaceEngine& refineBoundaryLayers::surfaceEngine() const +{ + if( !msePtr_ ) + msePtr_ = new meshSurfaceEngine(mesh_); + + return *msePtr_; +} + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +refineBoundaryLayers::refineBoundaryLayers(polyMeshGen& mesh) +: + mesh_(mesh), + msePtr_(NULL), + globalNumLayers_(1), + globalThicknessRatio_(1.0), + globalMaxThicknessFirstLayer_(VGREAT), + numLayersForPatch_(), + thicknessRatioForPatch_(), + maxThicknessForPatch_(), + discontinuousLayersForPatch_(), + done_(false), + is2DMesh_(false), + nLayersAtBndFace_(), + splitEdges_(), + splitEdgesAtPoint_(), + newVerticesForSplitEdge_(), + facesFromFace_(), + newFaces_() +{} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +refineBoundaryLayers::~refineBoundaryLayers() +{ + deleteDemandDrivenData(msePtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void refineBoundaryLayers::avoidRefinement() +{ + globalNumLayers_ = 1; + numLayersForPatch_.clear(); +} + +void refineBoundaryLayers::activate2DMode() +{ + is2DMesh_ = true; +} + +void refineBoundaryLayers::setGlobalNumberOfLayers(const label nLayers) +{ + if( nLayers < 2 ) + { + WarningIn + ( + "void refineBoundaryLayers::setGlobalNumberOfLayers(const label)" + ) << "The specified global number of boundary layers is less than 2" + << endl; + + return; + } + + globalNumLayers_ = nLayers; +} + +void refineBoundaryLayers::setGlobalThicknessRatio(const scalar thicknessRatio) +{ + if( thicknessRatio < 1.0 ) + { + WarningIn + ( + "void refineBoundaryLayers::setGlobalThicknessRatio(const scalar)" + ) << "The specified global thickness ratio is less than 1.0" << endl; + + return; + } + + globalThicknessRatio_ = thicknessRatio; +} + +void refineBoundaryLayers::setGlobalMaxThicknessOfFirstLayer +( + const scalar maxThickness +) +{ + if( maxThickness <= 0.0 ) + { + WarningIn + ( + "void refineBoundaryLayers::setGlobalMaxThicknessOfFirstLayer" + "(const scalar)" + ) << "The specified global maximum thickness of the first" + << " boundary layer is negative!!" << endl; + + return; + } + + globalMaxThicknessFirstLayer_ = maxThickness; +} + +void refineBoundaryLayers::setNumberOfLayersForPatch +( + const word& patchName, + const label nLayers +) +{ + if( nLayers < 2 ) + { + WarningIn + ( + "void refineBoundaryLayers::setNumberOfLayersForPatch" + "(const word&, const label)" + ) << "The specified number of boundary layers for patch " << patchName + << " is less than 2" << endl; + + return; + } + + numLayersForPatch_[patchName] = nLayers; +} + +void refineBoundaryLayers::setThicknessRatioForPatch +( + const word& patchName, + const scalar thicknessRatio +) +{ + if( thicknessRatio < 1.0 ) + { + WarningIn + ( + "void refineBoundaryLayers::setThicknessRatioForPatch" + "(const word&, const scalar)" + ) << "The specified thickness ratio for patch " << patchName + << " is less than 1.0" << endl; + + return; + } + + thicknessRatioForPatch_[patchName] = thicknessRatio; +} + +void refineBoundaryLayers::setMaxThicknessOfFirstLayerForPatch +( + const word& patchName, + const scalar maxThickness +) +{ + if( maxThickness <= 0.0 ) + { + WarningIn + ( + "void refineBoundaryLayers::setGlobalMaxThicknessOfFirstLayer" + "(const word&, const scalar)" + ) << "The specified maximum thickness of the first boundary layer " + << "for patch " << patchName << " is negative!!" << endl; + + return; + } + + maxThicknessForPatch_[patchName] = maxThickness; +} + +void refineBoundaryLayers::setInteruptForPatch(const word& patchName) +{ + discontinuousLayersForPatch_.insert(patchName); +} + +void refineBoundaryLayers::refineLayers() +{ + bool refinePatch(false); + for + ( + std::map<word, label>::const_iterator it=numLayersForPatch_.begin(); + it!=numLayersForPatch_.end(); + ++it + ) + if( it->second > 1 ) + refinePatch = true; + + if( (globalNumLayers_ < 2) && !refinePatch ) + return; + + Info << "Starting refining boundary layers" << endl; + + if( done_ ) + { + WarningIn + ( + "void refineBoundaryLayers::refineLayers()" + ) << "Boundary layers are already refined! Stopping refinement" << endl; + + return; + } + + analyseLayers(); + + if( !findSplitEdges() ) + { + WarningIn + ( + "void refineBoundaryLayers::refineLayers()" + ) << "Boundary layers do not exist in the mesh! Cannot refine" << endl; + + return; + } + + generateNewVertices(); + + generateNewFaces(); + + generateNewCells(); + + done_ = true; + + Info << "Finished refining boundary layers" << endl; +} + +void refineBoundaryLayers::readSettings +( + const dictionary& meshDict, + refineBoundaryLayers& refLayers +) +{ + if( meshDict.isDict("boundaryLayers") ) + { + const dictionary& bndLayers = meshDict.subDict("boundaryLayers"); + + //- read global properties + if( bndLayers.found("nLayers") ) + { + const label nLayers = readLabel(bndLayers.lookup("nLayers")); + refLayers.setGlobalNumberOfLayers(nLayers); + } + if( bndLayers.found("thicknessRatio") ) + { + const scalar ratio = readScalar(bndLayers.lookup("thicknessRatio")); + refLayers.setGlobalThicknessRatio(ratio); + } + if( bndLayers.found("maxFirstLayerThickness") ) + { + const scalar maxFirstThickness = + readScalar(bndLayers.lookup("maxFirstLayerThickness")); + refLayers.setGlobalMaxThicknessOfFirstLayer(maxFirstThickness); + } + + //- patch-based properties + if( bndLayers.isDict("patchBoundaryLayers") ) + { + const dictionary& patchBndLayers = + bndLayers.subDict("patchBoundaryLayers"); + const wordList patchNames = patchBndLayers.toc(); + + forAll(patchNames, patchI) + { + const word pName = patchNames[patchI]; + + if( patchBndLayers.isDict(pName) ) + { + const dictionary& patchDict = + patchBndLayers.subDict(pName); + + if( patchDict.found("nLayers") ) + { + const label nLayers = + readLabel(patchDict.lookup("nLayers")); + + refLayers.setNumberOfLayersForPatch(pName, nLayers); + } + if( patchDict.found("thicknessRatio") ) + { + const scalar ratio = + readScalar(patchDict.lookup("thicknessRatio")); + refLayers.setThicknessRatioForPatch(pName, ratio); + } + if( patchDict.found("maxFirstLayerThickness") ) + { + const scalar maxFirstThickness = + readScalar + ( + patchDict.lookup("maxFirstLayerThickness") + ); + refLayers.setMaxThicknessOfFirstLayerForPatch + ( + pName, + maxFirstThickness + ); + } + if( patchDict.found("allowDiscontinuity") ) + { + const bool allowDiscontinuity = + readBool(patchDict.lookup("allowDiscontinuity")); + + if( allowDiscontinuity ) + refLayers.setInteruptForPatch(pName); + } + } + else + { + Warning << "Cannot refine layer for patch " + << patchNames[patchI] << endl; + } + } + } + } + else + { + //- the layer will not be refined + refLayers.avoidRefinement(); + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/boundaryLayers/refineBoundaryLayers.H b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayers.H new file mode 100644 index 0000000000000000000000000000000000000000..1e8535ea25fa40c0fe741458145e4f789d2230b1 --- /dev/null +++ b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayers.H @@ -0,0 +1,406 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + refineBoundaryLayers + +Description + Refine existing boundary layers + +SourceFiles + refineBoundaryLayers.C + refineBoundaryLayersFunctions.C + +\*---------------------------------------------------------------------------*/ + +#ifndef refineBoundaryLayers_H +#define refineBoundaryLayers_H + +#include "polyMeshGenModifier.H" +#include "meshSurfaceEngine.H" +#include "DynList.H" +#include "labelLongList.H" +#include "labelPair.H" + +#include <map> +#include <set> + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class meshSurfaceEngine; + +/*---------------------------------------------------------------------------*\ + Class refineBoundaryLayers Declaration +\*---------------------------------------------------------------------------*/ + +class refineBoundaryLayers +{ + //- Reference to the mesh + polyMeshGen& mesh_; + + //- pointer to mesh surface engine + mutable meshSurfaceEngine* msePtr_; + + //- global number of boundary layers + label globalNumLayers_; + + //- global thickness ratio + scalar globalThicknessRatio_; + + //- global maximum thickness of the first layer + scalar globalMaxThicknessFirstLayer_; + + //- number of boundary layers for user-selected patches + std::map<word, label> numLayersForPatch_; + + //- local thickness ratio for selected patches + std::map<word, scalar> thicknessRatioForPatch_; + + //- local maximum layer thickness for selected patches + std::map<word, scalar> maxThicknessForPatch_; + + //- allow discontinuous layers for patch + std::set<word> discontinuousLayersForPatch_; + + //- check whether the refinement is already executed + bool done_; + + //- a flag whether a 2D mesh generation is active or not + bool is2DMesh_; + + //- information about existing boundary layers at patches + //- only available layers + labelList layerAtPatch_; + + //- which patches are part of a single layer + List<DynList<word> > patchesInLayer_; + + //- a containing the number of layers which shall be generated above + //- a boundary face + labelList nLayersAtBndFace_; + + //- a list of edges which shall be refined + LongList<edge> splitEdges_; + + //- split edges at point + VRWGraph splitEdgesAtPoint_; + + //- new vertices for on edges which shall be refined + VRWGraph newVerticesForSplitEdge_; + + //- a graph containing information which new faces were generated + //- from an existing face + VRWGraph facesFromFace_; + + //- a graph containing faces after layer refinement + VRWGraph newFaces_; + + // Private member functions + //- Return reference to meshSurfaceEngine + const meshSurfaceEngine& surfaceEngine() const; + + //- analyse layers to check their topology + void analyseLayers(); + + //- calculate addressing for a boundary cell + void calculateAddressing + ( + const label bfI, + label& baseFace, + DynList<edge, 48>& edges, + DynList<DynList<label, 2>, 48>& edgeFaces, + DynList<DynList<label, 10>, 24>& faceEdges + ) const; + + //- find bnd layer hairs for a boundary face + bool findHairsForFace(const label, DynList<edge>&) const; + + //- find edges which shall be split due to refinement + bool findSplitEdges(); + + //- generate new points on edges, faces and in cells + void generateNewVertices(); + + //- refine a given face and return the new faces + //- generates new points at cross-split faces + void refineFace + ( + const face& f, + const FixedList<label, 2>& nLayersInDirection, + DynList<DynList<label, 4>, 128>& newFaces + ); + + //- generate a matrix of points generated by splitting a face + //- and return them in the local i, j system of the face + void sortFacePoints + ( + const label faceI, + DynList<DynList<label> >& facePoints, + const label transpose = false + ) const; + + //- generate a matrix of faces generated by splitting a face + //- and return them in the local i, j, system of the face + void sortFaceFaces + ( + const label faceI, + DynList<DynList<label> >& faceFaces, + const label transpose = false + ) const; + + //- map split edges onto a cell + void generateNewFaces(); + + //- generate new cells for a prism with one boundary face + void generateNewCellsPrism + ( + const label cellI, + DynList<DynList<DynList<label, 8>, 10> >& cellsFromCell + ); + + //- a helper function which stores faces generated from + //- an existing face into new cells + void storeFacesIntoCells + ( + const label faceI, + const bool reverseOrientation, + const label normalDirection, + const bool maxCoordinate, + const label nLayersI, + const label nLayersJ, + const label nLayersK, + DynList<DynList<DynList<label, 4>, 6>, 256>& cellsFromCell + ) const; + + //- generate new cells and add them to the mesh + void generateNewCells(); + + // Nested classes + class refineEdgeHexCell + { + // Private data + //- label of cell + const label cellI_; + + //- number of cells in local direction i + label nLayersI_; + + //- number of cells in locatiol direction j + label nLayersJ_; + + //- container for new cells + DynList<DynList<DynList<label, 4>, 6>, 256> cellsFromCell_; + + //- reference to the boundary layer class + refineBoundaryLayers& bndLayers_; + + //- faces sorted into directions of a hex shape + FixedList<label, 6> faceInDirection_; + + //- information about orientation of faces + //- false means the orientation as expected + //- true means wrong orientation + FixedList<bool, 6> faceOrientation_; + + //- points on cross-split faces + FixedList<DynList<DynList<label> >, 2> cellPoints_; + + // Private member functions + //- populate faceInDirection_nad wrongFaceOrientation_ + void determineFacesInDirections(); + + //- populate new cells with new faces generated from already + //- existing faces + void populateExistingFaces(); + + //- generate new internal faces and tore them to new cells + void generateMissingFaces(); + + public: + + // Constructor + //- construct from cell label and the refineBoundaryLayers + refineEdgeHexCell(const label cellI, refineBoundaryLayers& ref); + + // Public member functions + inline const DynList<DynList<DynList<label, 4>, 6>, 256>& + newCells() const + { + return cellsFromCell_; + } + }; + + class refineCornerHexCell + { + // Private data + //- label of cell + const label cellI_; + + //- number of cells in local direction i + label nLayersI_; + + //- number of cells in local direction j + label nLayersJ_; + + //- number of cells in local direction k + label nLayersK_; + + //- split edge in directions + FixedList<label, 3> splitEdgeInDirection_; + + //- container for new cells + DynList<DynList<DynList<label, 4>, 6>, 256> cellsFromCell_; + + //- reference to the boundary layer class + refineBoundaryLayers& bndLayers_; + + //- faces sorted into directions of a hex shape + FixedList<label, 6> faceInDirection_; + + //- information about orientation of faces + //- false means the orientation as expected + //- true means wrong orientation + FixedList<bool, 6> faceOrientation_; + + //- points on cross-split faces + FixedList<DynList<DynList<label> >, 6> facePoints_; + + //- points inside the cell + DynList<DynList<DynList<label> > > cellPoints_; + + // Private member functions + //- populate faceInDirection_nad wrongFaceOrientation_ + void determineFacesInDirections(); + + //- populate new cells with new faces generated from already + //- existing faces + void populateExistingFaces(); + + //- generate missing points inside the cell + void generateNewPoints(); + + //- generate new internal faces and tore them to new cells + void generateMissingFaces(); + + public: + + // Constructor + //- construct from cell label and the refineBoundaryLayers + refineCornerHexCell + ( + const label cellI, + refineBoundaryLayers& ref + ); + + // Public member functions + inline const DynList<DynList<DynList<label, 4>, 6>, 256>& + newCells() const + { + return cellsFromCell_; + } + }; + + // Private member functions + + //- Disallow bitwise copy construct + refineBoundaryLayers(const refineBoundaryLayers&); + + //- Disallow bitwise assignment + void operator=(const refineBoundaryLayers&); + +public: + + // Constructors + + //- Construct from mesh reference + refineBoundaryLayers(polyMeshGen& mesh); + + // Destructor + ~refineBoundaryLayers(); + + // Public member functions + //- set no refinement flag + void avoidRefinement(); + + //- activate 2D layer refinement + void activate2DMode(); + + //- set the global number of boundary layers + void setGlobalNumberOfLayers(const label nLayers); + + //- set the global thickness ratio (default is 1) + void setGlobalThicknessRatio(const scalar thicknessRatio); + + //- set the maximum thickness of the first boundary layer + void setGlobalMaxThicknessOfFirstLayer(const scalar maxThickness); + + //- set the number of layers for a patch + //- the settings override the global settings + void setNumberOfLayersForPatch + ( + const word& patchName, + const label nLayers + ); + + //- set the thickness ratio for a patch + //- it overrides the global settings + void setThicknessRatioForPatch + ( + const word& patchName, + const scalar thicknessRatio + ); + + //- set the maximum thickness of the first layer for a patch + void setMaxThicknessOfFirstLayerForPatch + ( + const word& patchName, + const scalar maxThickness + ); + + //- set whether the settings for a given patch are valid for the + //- patch only, or whether they extend over th whole sheet + //- the selected patch belongs to + //- the default behaviour is to apply the patch settings to the whole + //- sheet + void setInteruptForPatch(const word& patchName); + + //- performs refinement based on the given settings + void refineLayers(); + + //- read the settings from dictionary + static void readSettings(const dictionary&, refineBoundaryLayers&); +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersCells.C b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersCells.C new file mode 100644 index 0000000000000000000000000000000000000000..7755e4085d49e141e6fcf8f06bf8dec1b53ea820 --- /dev/null +++ b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersCells.C @@ -0,0 +1,1905 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "refineBoundaryLayers.H" +#include "meshSurfaceEngine.H" +#include "helperFunctions.H" +#include "demandDrivenData.H" + +//#define DEBUGLayer + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void refineBoundaryLayers::generateNewCellsPrism +( + const label cellI, + DynList<DynList<DynList<label, 8>, 10> >& cellsFromCell +) +{ + cellsFromCell.clear(); + + const cell& c = mesh_.cells()[cellI]; + const labelList& owner = mesh_.owner(); + + # ifdef DEBUGLayer + Pout << "New cells from cell " << cellI << endl; + # endif + + const label startBoundary = mesh_.boundaries()[0].patchStart(); + + //- find the number of lyers for this cell + label nLayers(1), baseFace(-1); + forAll(c, fI) + { + const label bfI = c[fI] - startBoundary; + + if( (bfI < 0) || (bfI >= nLayersAtBndFace_.size()) ) + continue; + + if( nLayersAtBndFace_[bfI] < 2 ) + continue; + + # ifdef DEBUGLayer + Pout << "Boundary face " << bfI << endl; + # endif + + nLayers = nLayersAtBndFace_[bfI]; + baseFace = fI; + } + + # ifdef DEBUGLayer + Pout << "Number of layers " << nLayers << endl; + Pout << "Base face " << baseFace << " has points " + << mesh_.faces()[c[baseFace]] << endl; + forAll(c, fI) + { + Pout << "Faces from face " << fI << " are " + << facesFromFace_[c[fI]] << endl; + + forAllRow(facesFromFace_, c[fI], i) + Pout << "Face " << facesFromFace_(c[fI], i) + << " is " << newFaces_[facesFromFace_(c[fI], i)] << endl; + } + # endif + + //- set the number of layers + cellsFromCell.setSize(nLayers); + + //- distribute existing faces into new cells + label otherBaseFace(-1); + forAll(c, fI) + { + if( fI == baseFace ) + { + const label faceI = facesFromFace_(c[fI], 0); + DynList<label, 8> f; + f = newFaces_[faceI]; + cellsFromCell[nLayers-1].append(f); + } + else if( facesFromFace_.sizeOfRow(c[fI]) == 1 ) + { + const label faceI = facesFromFace_(c[fI], 0); + otherBaseFace = fI; + DynList<label, 8> f; + f = newFaces_[faceI]; + cellsFromCell[0].append(f); + } + else + { + forAllRow(facesFromFace_, c[fI], cfI) + { + const label nfI = facesFromFace_(c[fI], cfI); + + DynList<label, 8> cf; + cf = newFaces_[nfI]; + + if( owner[c[fI]] != cellI ) + cf = help::reverseFace(cf); + + cellsFromCell[Foam::max(nLayers-1-cfI, 0)].append(cf); + } + } + } + + //- generate missing faces + const faceListPMG& faces = mesh_.faces(); + const face& bf = faces[c[baseFace]]; + const face& obf = faces[c[otherBaseFace]]; + for(label layerI=1;layerI<nLayers;++layerI) + { + //- create new face from points at the same height + DynList<label, 8> cf; + forAll(bf, pI) + { + const label pointI = bf[pI]; + + # ifdef DEBUGLayer + Pout << "Split edges at point " << pointI << " are " + << splitEdgesAtPoint_[pointI] << endl; + # endif + + label seI(-1); + if( splitEdgesAtPoint_.sizeOfRow(pointI) == 1 ) + { + seI = splitEdgesAtPoint_(pointI, 0); + } + else + { + forAllRow(splitEdgesAtPoint_, pointI, sepI) + { + const label seJ = splitEdgesAtPoint_(pointI, sepI); + const edge& se = splitEdges_[seJ]; + + if( obf.which(se.end()) >= 0 || obf.which(se.start()) >= 0 ) + { + seI = seJ; + break; + } + } + } + + cf.append(newVerticesForSplitEdge_(seI, layerI)); + } + + //- add faces to cells + cellsFromCell[nLayers-layerI].append(cf); + cellsFromCell[nLayers-1-layerI].append(cf); + } + + # ifdef DEBUGLayer + Pout << "New cells from cell " << cellI << " are " << cellsFromCell << endl; + //::exit(1); + + Pout << "1. Newly generated cells " << cellsFromCell << endl; + + //- check if all generated cells are topologically closed + forAll(cellsFromCell, cI) + { + const DynList<DynList<label, 8>, 10>& cellFaces = cellsFromCell[cI]; + + DynList<edge, 12> edges; + DynList<label, 12> nAppearances; + + forAll(cellFaces, fI) + { + const DynList<label, 8>& f = cellFaces[fI]; + + forAll(f, eI) + { + const edge e(f[eI], f.fcElement(eI)); + + const label pos = edges.containsAtPosition(e); + + if( pos < 0 ) + { + edges.append(e); + nAppearances.append(1); + } + else + { + ++nAppearances[pos]; + } + } + } + + forAll(nAppearances, eI) + if( nAppearances[eI] != 2 ) + { + Pout << "Prism cell " << cI << " edge " << edges[eI] + << " is present " << nAppearances[eI] << " times!" << endl; + abort(FatalError); + } + } + # endif +} + +void refineBoundaryLayers::storeFacesIntoCells +( + const label faceI, + const bool reverseOrientation, + const label normalDirection, + const bool maxCoordinate, + const label nLayersI, + const label nLayersJ, + const label nLayersK, + DynList<DynList<DynList<label, 4>, 6>, 256>& cellsFromCell +) const +{ + DynList<DynList<label> > faceFaces; + sortFaceFaces(faceI, faceFaces, reverseOrientation); + + const label maxI = nLayersI - 1; + const label maxJ = nLayersJ - 1; + const label maxK = nLayersK - 1; + + # ifdef DEBUGLayer + Pout << "Storing new faces from face " << faceI + << " reverseOrientation = " << reverseOrientation + << " normal direction " << normalDirection + << " maxCoordinate " << maxCoordinate << endl; + Pout << "faceFaces " << faceFaces << endl; + # endif + + label i(-1), j(-1), k(-1); + + forAll(faceFaces, nI) + { + forAll(faceFaces[nI], nJ) + { + const label nfI = faceFaces[nI][nJ]; + + # ifdef DEBUGLayer + Pout << "nI = " << nI << " nJ = " << nJ << endl; + # endif + + if( normalDirection == 0 ) + { + //- k is const + i = Foam::min(nI, maxI); + j = Foam::min(nJ, maxJ); + k = maxCoordinate?maxK:0; + } + else if( normalDirection == 1 ) + { + //- j is const + i = Foam::min(nJ, maxI); + j = maxCoordinate?maxJ:0; + k = Foam::min(nI, maxK); + } + else if( normalDirection == 2 ) + { + //- i is const + i = maxCoordinate?maxI:0; + j = Foam::min(nI, maxJ); + k = Foam::min(nJ, maxK); + } + + //- store the face into a new cell + const label cI + ( + j * nLayersI + + k * nLayersI * nLayersJ + + i + ); + + # ifdef DEBUGLayer + Pout << "Storing face " << newFaces_[nfI] + << " i = " << i << " j = " << j << " k = " << k + << "\n cell label " << cI << endl; + # endif + + cellsFromCell[cI].append(newFaces_[nfI]); + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void refineBoundaryLayers::refineEdgeHexCell::determineFacesInDirections() +{ + const labelList& nLayersAtBndFace = bndLayers_.nLayersAtBndFace_; + const polyMeshGen& mesh = bndLayers_.mesh_; + const faceListPMG& faces = mesh.faces(); + const cell& c = mesh.cells()[cellI_]; + + # ifdef DEBUGLayer + Pout << "Generating new cells from edge cell " << cellI_ << endl; + # endif + + const PtrList<boundaryPatch>& bnd = mesh.boundaries(); + const label startBoundary = bnd[0].patchStart(); + + //- find the number of layers for this cell + FixedList<label, 2> layersInDirection(-1), dirFace; + label currDir(0); + + FixedList<bool, 6> determinedFace(false); + + forAll(c, fI) + { + const label bfI = c[fI] - startBoundary; + + if( (bfI < 0) || (bfI >= nLayersAtBndFace.size()) ) + continue; + + # ifdef DEBUGLayer + Pout << "Boundary face " << bfI << endl; + # endif + + if( nLayersAtBndFace[bfI] < 2 ) + continue; + + layersInDirection[currDir] = nLayersAtBndFace[bfI]; + dirFace[currDir] = fI; + ++currDir; + } + + //- set the number of newly create cells + nLayersI_ = layersInDirection[0]; + nLayersJ_ = layersInDirection[1]; + cellsFromCell_.setSize(nLayersI_ * nLayersJ_); + + //- find the shared edge between the boundary faces + const edge commonEdge = + help::sharedEdge(faces[c[dirFace[0]]], faces[c[dirFace[1]]]); + + //- faces at i = const in the local coordinate system + faceInDirection_[4] = dirFace[0]; + determinedFace[dirFace[0]] = true; + forAll(c, fI) + { + if( determinedFace[fI] ) + continue; + + if( !help::shareAnEdge(faces[c[dirFace[0]]], faces[c[fI]]) ) + { + faceInDirection_[5] = fI; + determinedFace[fI] = true; + break; + } + } + + //- faces k = const in the local coordinate system + faceInDirection_[2] = dirFace[1]; + determinedFace[dirFace[1]] = true; + forAll(c, fI) + { + if( determinedFace[fI] ) + continue; + + if( !help::shareAnEdge(faces[c[dirFace[1]]], faces[c[fI]]) ) + { + faceInDirection_[3] = fI; + determinedFace[fI] = true; + break; + } + } + + # ifdef DEBUGLayer + Pout << "Common edge " << commonEdge << endl; + Pout << "Donor face " << dirFace[0] << endl; + Pout << "Donor face points " << faces[c[dirFace[0]]] << endl; + # endif + + //- find the face attached to the starting point of the edge and + //- the face attached to the end point of the edge + forAll(c, fI) + { + if( determinedFace[fI] ) + continue; + + if( + (faces[c[fI]].which(commonEdge.start()) >= 0) && + (help::positionOfEdgeInFace(commonEdge, faces[c[fI]]) < 0) + ) + faceInDirection_[0] = fI; + + if( + (faces[c[fI]].which(commonEdge.end()) >= 0) && + (help::positionOfEdgeInFace(commonEdge, faces[c[fI]]) < 0) + ) + faceInDirection_[1] = fI; + } + + //- check the orientation of faces + const labelList& owner = mesh.owner(); + + //- checking face at direction k = 0 + faceOrientation_[0] = owner[c[faceInDirection_[0]]] == cellI_?true:false; + + //- checking face in direction k = 1 + faceOrientation_[1] = owner[c[faceInDirection_[1]]] == cellI_?false:true; + + //- set orientation flag for face in direction j = 0 + faceOrientation_[2] = true; + + //- checking face in direction j = nLayersJ_ + faceOrientation_[3] = owner[c[faceInDirection_[3]]] == cellI_?false:true; + + //- set orientation flag for face in direction i = 0 + faceOrientation_[4] = true; + + //- checking face in direction i = nLayersI_ + faceOrientation_[5] = owner[c[faceInDirection_[5]]] == cellI_?false:true; + + # ifdef DEBUGLayer + Pout << "Face at start " << faces[c[faceInDirection_[0]]] << endl; + Pout << "Face at end " << faces[c[faceInDirection_[1]]] << endl; + forAll(faceInDirection_, i) + Pout << "Face in direction " << i << " is " + << faces[c[faceInDirection_[i]]] + << " orientation " << faceOrientation_[i] << endl; + # endif +} + +void refineBoundaryLayers::refineEdgeHexCell::populateExistingFaces() +{ + const cell& c = bndLayers_.mesh_.cells()[cellI_]; + const VRWGraph& facesFromFace = bndLayers_.facesFromFace_; + const VRWGraph& newFaces = bndLayers_.newFaces_; + + cellsFromCell_.setSize(nLayersI_ * nLayersJ_); + forAll(cellsFromCell_, cI) + cellsFromCell_[cI].clear(); + + //- store new faces at k = 0 + bndLayers_.storeFacesIntoCells + ( + c[faceInDirection_[0]], faceOrientation_[0], + 0, 0, + nLayersI_, nLayersJ_, 1, + cellsFromCell_ + ); + + //- store new faces at k = 1 + bndLayers_.storeFacesIntoCells + ( + c[faceInDirection_[1]], faceOrientation_[1], + 0, 1, + nLayersI_, nLayersJ_, 1, + cellsFromCell_ + ); + + //- store new faces at j = 0 + forAllRow(facesFromFace, c[faceInDirection_[2]], i) + { + const label faceI = facesFromFace(c[faceInDirection_[2]], i); + cellsFromCell_[i].append(newFaces[faceI]); + } + + //- store faces at j = nLayersJ + const label maxJ = nLayersJ_ - 1; + forAllRow(facesFromFace, c[faceInDirection_[3]], i) + { + const label faceI = facesFromFace(c[faceInDirection_[3]], i); + cellsFromCell_[i + maxJ * nLayersI_].append(newFaces[faceI]); + } + + //- store new faces at i = 0 + forAllRow(facesFromFace, c[faceInDirection_[4]], j) + { + const label faceI = facesFromFace(c[faceInDirection_[4]], j); + cellsFromCell_[j * nLayersI_].append(newFaces[faceI]); + } + + //- store new faces at i = nLayersI + const label maxI = nLayersI_ - 1; + forAllRow(facesFromFace, c[faceInDirection_[5]], j) + { + const label faceI = facesFromFace(c[faceInDirection_[5]], j); + cellsFromCell_[j * nLayersI_ + maxI].append(newFaces[faceI]); + } + + # ifdef DEBUGLayer + Pout << "New cells after populating existing faces " + << cellsFromCell_ << endl; + # endif +} + +void refineBoundaryLayers::refineEdgeHexCell::generateMissingFaces() +{ + const cell& c = bndLayers_.mesh_.cells()[cellI_]; + + //- fill up the matrix of points for this cell + //- the matrix is used for generation of new cells + FixedList<DynList<DynList<label> >, 2> cellPoints; + + //- fill in the data for a cross-split faces + bndLayers_.sortFacePoints + ( + c[faceInDirection_[0]], + cellPoints[0], + faceOrientation_[0] + ); + bndLayers_.sortFacePoints + ( + c[faceInDirection_[1]], + cellPoints[1], + faceOrientation_[1] + ); + + //- generate new internal faces for this cell + //- generate faces with normal in the i direction + const label maxI = nLayersI_ - 1; + const label maxJ = nLayersJ_ - 1; + + for(label i=1;i<nLayersI_;++i) + { + for(label j=0;j<nLayersJ_;++j) + { + const label own = j * nLayersI_ + i - 1; + const label nei = own + 1; + + if( j < maxJ ) + { + //- generate a quad face + FixedList<label, 4> mf; + + //- populate the points form cellPoints + mf[0] = cellPoints[0][i][j]; + mf[1] = cellPoints[0][i][j+1]; + mf[2] = cellPoints[1][i][j+1]; + mf[3] = cellPoints[1][i][j]; + + # ifdef DEBUGLayer + Pout << "1. Adding missing face " << mf + << " to cells " << own << " and " << nei << endl; + # endif + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + else + { + DynList<label> mf; + for(label index=j;index<cellPoints[0][i].size();++index) + mf.append(cellPoints[0][i][index]); + for(label index=cellPoints[1][i].size()-1;index>=j;--index) + mf.append(cellPoints[1][i][index]); + + # ifdef DEBUGLayer + Pout << "2. Adding missing face " << mf + << " to cells " << own << " and " << nei << endl; + # endif + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + }; + } + } + + //- generate faces with the normal in j direction + for(label i=0;i<nLayersI_;++i) + { + for(label j=1;j<nLayersJ_;++j) + { + const label nei = j * nLayersI_ + i; + const label own = (j - 1) * nLayersI_ + i; + + if( i < maxI ) + { + //- generate a quad face + FixedList<label, 4> mf; + + //- populate the points form cellPoints + mf[0] = cellPoints[0][i][j]; + mf[1] = cellPoints[1][i][j]; + mf[2] = cellPoints[1][i+1][j]; + mf[3] = cellPoints[0][i+1][j]; + + # ifdef DEBUGLayer + Pout << "3. Adding missing face " << mf + << " to cells " << own << " and " << nei << endl; + # endif + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + else + { + DynList<label> mf; + for(label index=i;index<cellPoints[1].size();++index) + mf.append(cellPoints[1][index][j]); + for(label index=cellPoints[0].size()-1;index>=i;--index) + mf.append(cellPoints[0][index][j]); + + # ifdef DEBUGLayer + Pout << "4. Adding missing face " << mf + << " to cells " << own << " and " << nei << endl; + # endif + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + }; + } + } + + # ifdef DEBUGLayer + Pout << "Cell " << cellI_ << " new cells are " << cellsFromCell_ << endl; + //::exit(1); + # endif +} + +refineBoundaryLayers::refineEdgeHexCell::refineEdgeHexCell +( + const label cellI, + refineBoundaryLayers& ref +) +: + cellI_(cellI), + nLayersI_(), + nLayersJ_(), + cellsFromCell_(), + bndLayers_(ref), + faceInDirection_(), + faceOrientation_(), + cellPoints_() +{ + determineFacesInDirections(); + + populateExistingFaces(); + + generateMissingFaces(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void refineBoundaryLayers::refineCornerHexCell::determineFacesInDirections() +{ + const polyMeshGen& mesh = bndLayers_.mesh_; + const cell& c = mesh.cells()[cellI_]; + const faceListPMG& faces = mesh.faces(); + const labelList& nLayersAtBndFace = bndLayers_.nLayersAtBndFace_; + + # ifdef DEBUGLayer + Pout << "Generating new cells from corner hex cell " << cellI_ << endl; + Pout << "Cell faces " << c << endl; + # endif + + const label startBoundary = mesh.boundaries()[0].patchStart(); + + //- find the number of layers for this cell + FixedList<label, 3> layersInDirection(-1), dirFace; + FixedList<bool, 6> usedDirection(false); + label currDir(0); + + forAll(c, fI) + { + const label bfI = c[fI] - startBoundary; + + if( (bfI < 0) || (bfI >= nLayersAtBndFace.size()) ) + continue; + + # ifdef DEBUGLayer + Pout << "Boundary face " << bfI << endl; + # endif + + if( nLayersAtBndFace[bfI] < 2 ) + continue; + + usedDirection[fI] = true; + layersInDirection[currDir] = nLayersAtBndFace[bfI]; + dirFace[currDir] = fI; + ++currDir; + } + + //- find a common point for all three boundary faces + FixedList<DynList<label, 4>, 3> bndFaces; + forAll(dirFace, i) + { + bndFaces[i] = faces[c[dirFace[i]]]; + } + + const label commonPoint = help::sharedVertex(bndFaces); + + # ifdef DEBUGLayer + Pout << "Used directions " << usedDirection << endl; + Pout << "Layers in direction " << layersInDirection << endl; + Pout << "dirFace " << dirFace << endl; + Pout << "Common point " << commonPoint << endl; + + forAll(dirFace, i) + Pout << "bnd face " << i << " is " << faces[c[dirFace[i]]] << endl; + # endif + + //- find the position of the common point in each boundary face + const edgeLongList& splitEdges = bndLayers_.splitEdges_; + const VRWGraph& splitEdgesAtPoint = bndLayers_.splitEdgesAtPoint_; + + const face& baseFace = faces[c[dirFace[0]]]; + const label posInBndFace = baseFace.which(commonPoint); + + //- find split edges starting at the commonPoints + forAllRow(splitEdgesAtPoint, commonPoint, i) + { + const edge& se = splitEdges[splitEdgesAtPoint(commonPoint, i)]; + + if( se == baseFace.faceEdge(posInBndFace) ) + { + //- this edge is in j direction + splitEdgeInDirection_[1] = splitEdgesAtPoint(commonPoint, i); + } + else if( se == baseFace.faceEdge(baseFace.rcIndex(posInBndFace)) ) + { + //- this edge is in i diretion + splitEdgeInDirection_[0] = splitEdgesAtPoint(commonPoint, i); + } + else if( splitEdgesAtPoint.sizeOfRow(commonPoint) == 3 ) + { + //- this point is in k direction + splitEdgeInDirection_[2] = splitEdgesAtPoint(commonPoint, i); + } + else + { + //- this situation is not allowed + FatalErrorIn + ( + "void refineBoundaryLayers::refineCornerHexCell::" + "determineFacesInDirections()" + ) << "Cannot refine layer for cell " << cellI_ << abort(FatalError); + } + } + + # ifdef DEBUGLayer + const VRWGraph& newVerticesForSplitEdge = + bndLayers_.newVerticesForSplitEdge_; + forAll(splitEdgeInDirection_, i) + Pout << "Split edge in direction " << i << " has nodes " + << splitEdges[splitEdgeInDirection_[i]] + << " number of points on split edge " + << newVerticesForSplitEdge.sizeOfRow(splitEdgeInDirection_[i]) + << endl; + # endif + + //- find the direction od other boundary faces + //- in the local coordinate system + FixedList<label, 3> permutation; + permutation[0] = 0; + + label helper = help::positionOfEdgeInFace + ( + baseFace.faceEdge(baseFace.rcIndex(posInBndFace)), + faces[c[dirFace[1]]] + ); + + if( helper >= 0 ) + { + permutation[1] = 1; + permutation[2] = 2; + } + else + { + permutation[1] = 2; + permutation[2] = 1; + } + + //- find the number of layers and a split in each direction + nLayersI_ = layersInDirection[permutation[2]]; + nLayersJ_ = layersInDirection[permutation[1]]; + nLayersK_ = layersInDirection[permutation[0]]; + + //- determine the directions of cell faces + //- store boundary faces first. Their normals point in the wrong direction + //- face at k = 0 + faceInDirection_[0] = dirFace[permutation[0]]; + faceOrientation_[0] = true; + //- face at j = 0 + faceInDirection_[2] = dirFace[permutation[1]]; + faceOrientation_[2] = true; + //- face at i = 0 + faceInDirection_[4] = dirFace[permutation[2]]; + faceOrientation_[4] = true; + + //- find directions of other faces and thrie orientation + const labelList& owner = mesh.owner(); + forAll(c, fI) + { + if( usedDirection[fI] ) + continue; + + const bool orientation = owner[c[fI]]==cellI_?false:true; + + if( !help::shareAnEdge(faces[c[fI]], faces[c[faceInDirection_[0]]]) ) + { + //- face at k = nLayersK_ + faceInDirection_[1] = fI; + faceOrientation_[1] = orientation; + } + else if + ( + !help::shareAnEdge(faces[c[fI]], faces[c[faceInDirection_[2]]]) + ) + { + //- face at j = nLayersJ_ + faceInDirection_[3] = fI; + faceOrientation_[3] = orientation; + } + else if + ( + !help::shareAnEdge(faces[c[fI]], faces[c[faceInDirection_[4]]]) + ) + { + //- face at i = nLayersI_ + faceInDirection_[5] = fI; + faceOrientation_[5] = orientation; + } + } + + # ifdef DEBUGLayer + forAll(faceInDirection_, i) + Pout << "Face in direction " << i + << " is " << faces[c[faceInDirection_[i]]] + << " orientation " << faceOrientation_[i] << endl; + Pout << "nLayersI = " << nLayersI_ + << " nLayersJ = " << nLayersJ_ + << " nLayersK = " << nLayersK_ << endl; + # endif +} + +void refineBoundaryLayers::refineCornerHexCell::populateExistingFaces() +{ + const cell& c = bndLayers_.mesh_.cells()[cellI_]; + + //- set the number of cells + cellsFromCell_.setSize(nLayersI_ * nLayersJ_ * nLayersK_); + forAll(cellsFromCell_, i) + cellsFromCell_[i].clear(); + + //- add new faces from existing faces into new cells + forAll(faceInDirection_, dirI) + { + bndLayers_.storeFacesIntoCells + ( + c[faceInDirection_[dirI]], faceOrientation_[dirI], + dirI / 2, dirI % 2, + nLayersI_, nLayersJ_, nLayersK_, + cellsFromCell_ + ); + } + + # ifdef DEBUGLayer + Pout << "cellsFromCell_ before new faces " << cellsFromCell_ << endl; + //::exit(1); + # endif +} + +void refineBoundaryLayers::refineCornerHexCell::generateNewPoints() +{ + const cell& c = bndLayers_.mesh_.cells()[cellI_]; + + //- allocate space for points generated inside the cell + cellPoints_.setSize(nLayersI_+1); + forAll(cellPoints_, i) + { + cellPoints_[i].setSize(nLayersJ_+1); + + forAll(cellPoints_[i], j) + { + cellPoints_[i][j].setSize(nLayersK_+1); + cellPoints_[i][j] = -1; + } + } + + //- collect information about points generated on faces of the cell + forAll(faceInDirection_, dirI) + { + bndLayers_.sortFacePoints + ( + c[faceInDirection_[dirI]], + facePoints_[dirI], + faceOrientation_[dirI] + ); + } + + # ifdef DEBUGLayer + Pout << "Face points " << facePoints_ << endl; + # endif + + //- fill in cellPoints at the boundary + forAll(cellPoints_, i) + { + forAll(cellPoints_[i], j) + { + cellPoints_[i][j][0] = facePoints_[0][i][j]; + cellPoints_[i][j][nLayersK_] = facePoints_[1][i][j]; + } + } + + forAll(cellPoints_, i) + { + forAll(cellPoints_[i][0], k) + { + cellPoints_[i][0][k] = facePoints_[2][k][i]; + cellPoints_[i][nLayersJ_][k] = facePoints_[3][k][i]; + } + } + + forAll(cellPoints_[0], j) + { + forAll(cellPoints_[0][j], k) + { + cellPoints_[0][j][k] = facePoints_[4][j][k]; + cellPoints_[nLayersI_][j][k] = facePoints_[5][j][k]; + } + } + + //- useful data for generating missing points + const edgeLongList& splitEdges = bndLayers_.splitEdges_; + const edge& seDirI = splitEdges[splitEdgeInDirection_[0]]; + const edge& seDirJ = splitEdges[splitEdgeInDirection_[1]]; + const edge& seDirK = splitEdges[splitEdgeInDirection_[2]]; + const VRWGraph& ptsAtEdge = bndLayers_.newVerticesForSplitEdge_; + + //- const references to vertices of the cell ordered in a local + //- i, j, k coordinate system + pointFieldPMG& points = bndLayers_.mesh_.points(); + const point v000 = points[seDirI.start()]; + const point v100 = points[seDirI.end()]; + const point v110 = points[facePoints_[0].lastElement().lastElement()]; + const point v010 = points[seDirJ.end()]; + const point v001 = points[seDirK.end()]; + const point v101 = points[facePoints_[1].lastElement()[0]]; + const point v111 = points[facePoints_[1].lastElement().lastElement()]; + const point v011 = points[facePoints_[1][0].lastElement()]; + + for(label i=1;i<nLayersI_;++i) + { + const scalar u + ( + Foam::mag + ( + points[ptsAtEdge(splitEdgeInDirection_[0], i)] - + points[seDirI.start()] + ) / + seDirI.mag(points) + ); + + for(label j=1;j<nLayersJ_;++j) + { + const scalar v + ( + Foam::mag + ( + points[ptsAtEdge(splitEdgeInDirection_[1], j)] - + points[seDirJ.start()] + ) / + seDirJ.mag(points) + ); + + for(label k=1;k<nLayersK_;++k) + { + const scalar w + ( + Foam::mag + ( + points[ptsAtEdge(splitEdgeInDirection_[2], k)] - + points[seDirK.start()] + ) / + seDirK.mag(points) + ); + + # ifdef DEBUGLayer + Pout << "Generating point in corner cell local coordinates " + << "u = " << u << " v = " << v << " w = " << w << endl; + # endif + + //- calculate coordinates of the new vertex + const point newP = + (1.0 - u) * (1.0 - v) * (1.0 - w) * v000 + + u * (1.0 - v) * (1.0 - w) * v100 + + u * v * (1.0 - w) * v110 + + (1.0 - u) * v * (1.0 - w) * v010 + + (1.0 - u) * (1.0 - v) * w * v001 + + u * (1.0 - v) * w * v101 + + u * v * w * v111 + + (1.0 - u) * v * w * v011; + + # ifdef DEBUGLayer + Pout << "New point " << points.size() << " in corner hex " + << "has coordinates " << newP << endl; + # endif + + //- add the point to the mesh + cellPoints_[i][j][k] = points.size(); + points.append(newP); + } + } + } + + # ifdef DEBUGLayer + Pout << "New cell points " << cellPoints_ << endl; + //::exit(1); + # endif +} + +void refineBoundaryLayers::refineCornerHexCell::generateMissingFaces() +{ + //- generate face in direction i + for(label i=1;i<nLayersI_;++i) + { + //- generate quad faces + for(label j=0;j<nLayersJ_;++j) + { + for(label k=0;k<nLayersK_;++k) + { + //- skip generating last face because it might not be a quad + if( (j == (nLayersJ_-1)) && (k == (nLayersK_-1)) ) + continue; + + const label own + ( + k * nLayersI_ * nLayersJ_ + + j * nLayersI_ + + i - 1 + ); + const label nei = own + 1; + + FixedList<label, 4> mf; + + mf[0] = cellPoints_[i][j][k]; + mf[1] = cellPoints_[i][j+1][k]; + mf[2] = cellPoints_[i][j+1][k+1]; + mf[3] = cellPoints_[i][j][k+1]; + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + } + + //- generate faces which might not be a quads + DynList<label> mf; + + mf.append(cellPoints_[i][nLayersJ_-1][nLayersK_-1]); + + //- this face might not be a quad + //- add points fom the last face in direction j + const DynList<DynList<label> >& f3 = facePoints_[3]; + for(label index=nLayersK_-1;index<f3.size()-1;++index) + mf.append(f3[index][i]); + + //- add points from the last face in direction k + const DynList<DynList<label> >& f1 = facePoints_[1]; + for(label index=f1[i].size()-1;index>=nLayersJ_-1;--index) + mf.append(f1[i][index]); + + const label own + ( + (nLayersK_-1) * nLayersI_ * nLayersJ_ + + (nLayersJ_-1) * nLayersI_ + + i - 1 + ); + + const label nei = own + 1; + + # ifdef DEBUGLayer + Pout << "Additional face in direction i = " << i + << " j = " << (nLayersJ_-1) + << " has owner " << own + << " neighbour " << nei << " with nodes " << mf << endl; + # endif + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + + //- generate faces in direction j + for(label j=1;j<nLayersJ_;++j) + { + //- generate quad faces + for(label i=0;i<nLayersI_;++i) + { + for(label k=0;k<nLayersK_;++k) + { + //- skip generating late face because it might not be a quad + if( (i == (nLayersI_-1)) && (k == (nLayersK_-1)) ) + continue; + + const label own + ( + k * nLayersI_ * nLayersJ_ + + (j-1) * nLayersI_ + + i + ); + + const label nei + ( + k * nLayersI_ * nLayersJ_ + + j * nLayersI_ + + i + ); + + FixedList<label, 4> mf; + + mf[0] = cellPoints_[i][j][k]; + mf[1] = cellPoints_[i][j][k+1]; + mf[2] = cellPoints_[i+1][j][k+1]; + mf[3] = cellPoints_[i+1][j][k]; + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + } + + //- generate a face which might not be a quad + DynList<label> mf; + + mf.append(cellPoints_[nLayersI_-1][j][nLayersK_-1]); + + //- add points from the last face in direction k + const DynList<DynList<label> >& fp1 = facePoints_[1]; + for(label index=nLayersI_-1;index<fp1.size()-1;++index) + mf.append(fp1[index][j]); + + //- add points from the last face in direction i + const DynList<DynList<label> >& fp5 = facePoints_[5]; + for(label index=fp5[j].size()-1;index>=nLayersK_-1;--index) + mf.append(fp5[j][index]); + + const label own + ( + (nLayersK_-1) * nLayersI_ * nLayersJ_ + + (j-1) * nLayersI_ + + (nLayersI_ - 1) + ); + + const label nei + ( + (nLayersK_-1) * nLayersI_ * nLayersJ_ + + j * nLayersI_ + + (nLayersI_ - 1) + ); + + # ifdef DEBUGLayer + Pout << "Additional face at i = " << (nLayersI_-1) + << " j = " << j << " k = " << (nLayersK_-1) + << " has owner " << own + << " neighbour " << nei << " with nodes " << mf << endl; + # endif + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + + //- generate faces in direction k + for(label k=1;k<nLayersK_;++k) + { + //- generate quad faces + for(label i=0;i<nLayersI_;++i) + { + for(label j=0;j<nLayersJ_;++j) + { + //- skip the last face because it might not be a quad + if( (i == (nLayersI_-1)) && (j == (nLayersJ_-1)) ) + continue; + + const label own + ( + (k-1) * nLayersI_ * nLayersJ_ + + j * nLayersI_ + + i + ); + + const label nei + ( + k * nLayersI_ * nLayersJ_ + + j * nLayersI_ + + i + ); + + FixedList<label, 4> mf; + + mf[0] = cellPoints_[i][j][k]; + mf[1] = cellPoints_[i+1][j][k]; + mf[2] = cellPoints_[i+1][j+1][k]; + mf[3] = cellPoints_[i][j+1][k]; + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + } + + //- generate a face which might not be a quad + DynList<label> mf; + + mf.append(cellPoints_[nLayersI_-1][nLayersJ_-1][k]); + + //- this face might not be a quad + //- add points from the last face in direction i + const DynList<DynList<label> >& fp5 = facePoints_[5]; + for(label index=nLayersJ_-1;index<fp5.size()-1;++index) + mf.append(fp5[index][k]); + + //- add points from the last face in direction j + const DynList<DynList<label> >& fp3 = facePoints_[3]; + for(label index=fp3[k].size()-1;index>=nLayersI_-1;--index) + mf.append(fp3[k][index]); + + const label own + ( + (k-1) * nLayersI_ * nLayersJ_ + + (nLayersJ_-1) * nLayersI_ + + (nLayersI_ - 1) + ); + + const label nei + ( + k * nLayersI_ * nLayersJ_ + + (nLayersJ_-1) * nLayersI_ + + (nLayersI_ - 1) + ); + + # ifdef DEBUGLayer + Pout << "Additional face at position i = " << (nLayersI_-1) + << " j = " << (nLayersJ_-1) << " k = " << k + << " has owner " << own + << " neighbour " << nei << " with nodes " << mf << endl; + # endif + + cellsFromCell_[own].append(mf); + cellsFromCell_[nei].append(help::reverseFace(mf)); + } + + # ifdef DEBUGLayer + Pout << "Generated cells " << cellsFromCell_ << endl; + + forAll(cellsFromCell_, cI) + { + const DynList<DynList<label, 4>, 6>& cellFaces = cellsFromCell_[cI]; + + DynList<edge, 12> edges; + DynList<label, 12> nAppearances; + + forAll(cellFaces, fI) + { + const DynList<label, 4>& f = cellFaces[fI]; + + forAll(f, eI) + { + const edge e(f[eI], f.fcElement(eI)); + + const label pos = edges.containsAtPosition(e); + + if( pos < 0 ) + { + edges.append(e); + nAppearances.append(1); + } + else + { + ++nAppearances[pos]; + } + } + } + + forAll(nAppearances, eI) + if( nAppearances[eI] != 2 ) + { + Pout << "Edge hex cell " << cI << " edge " << edges[eI] + << " is present " << nAppearances[eI] << " times!" << endl; + abort(FatalError); + } + } + + //::exit(1); + # endif +} + +refineBoundaryLayers::refineCornerHexCell::refineCornerHexCell +( + const label cellI, + refineBoundaryLayers& ref +) +: + cellI_(cellI), + nLayersI_(), + nLayersJ_(), + nLayersK_(), + splitEdgeInDirection_(), + cellsFromCell_(), + bndLayers_(ref), + faceInDirection_(), + faceOrientation_(), + facePoints_(), + cellPoints_() +{ + determineFacesInDirections(); + + populateExistingFaces(); + + generateNewPoints(); + + generateMissingFaces(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void refineBoundaryLayers::generateNewCells() +{ + labelList nCellsFromCell(mesh_.cells().size(), 1); + labelList refType(mesh_.cells().size(), 0); + + const meshSurfaceEngine& mse = surfaceEngine(); + const labelList& faceOwners = mse.faceOwners(); + + //- calculate the number new cells generated from a cell + forAll(faceOwners, bfI) + { + const label cellI = faceOwners[bfI]; + + nCellsFromCell[cellI] *= nLayersAtBndFace_[bfI]; + + if( nLayersAtBndFace_[bfI] > 1 ) + ++refType[cellI]; + } + + label nNewCells(0); + forAll(nCellsFromCell, cellI) + nNewCells += (nCellsFromCell[cellI] - 1); + + # ifdef DEBUGLayer + forAll(nCellsFromCell, cellI) + { + Pout << "\nCell " << cellI << endl; + Pout << "nCellsFromCell " << nCellsFromCell[cellI] << endl; + Pout << "Ref type " << refType[cellI] << endl; + } + # endif + + const label totalNumNewCells = returnReduce(nNewCells, sumOp<label>()); + Info << "Number of newly generated cells " << totalNumNewCells << endl; + + //- create mesh modifier + polyMeshGenModifier meshModifier(mesh_); + faceListPMG& faces = meshModifier.facesAccess(); + + const label numFacesBefore = newFaces_.size(); + + //- set the number of cells to the new value + cellListPMG& cells = meshModifier.cellsAccess(); + label nCells = cells.size(); + cells.setSize(nCells+nNewCells); + + //- start creating new cells + //- store the information which new cells were generated from + //- an existing cell + VRWGraph newCellsFromCell(refType.size()); + + VRWGraph pointNewFaces; + pointNewFaces.reverseAddressing(newFaces_); + + forAll(nCellsFromCell, cellI) + { + if( refType[cellI] == 0 ) + { + //- this cell is not refined + //- update face labels + newCellsFromCell.append(cellI, cellI); + + cell& c = cells[cellI]; + + //- copy the new faces of this cell + DynList<label, 64> newC; + forAll(c, fI) + { + forAllRow(facesFromFace_, c[fI], cfI) + newC.append(facesFromFace_(c[fI], cfI)); + } + + //- update the cell + c.setSize(newC.size()); + forAll(c, fI) + c[fI] = newC[fI]; + } + else if( refType[cellI] == 1 ) + { + //- generate new cells from this prism refined in one direction + DynList<DynList<DynList<label, 8>, 10> > cellsFromCell; + generateNewCellsPrism(cellI, cellsFromCell); + + forAll(cellsFromCell, cI) + { + const DynList<DynList<label, 8>, 10>& nc = cellsFromCell[cI]; + + const label newCellI = cI==0?cellI:nCells++; + + newCellsFromCell.append(cellI, newCellI); + + cell& c = cells[newCellI]; + c.setSize(nc.size()); + + //- find face labels for this cell + forAll(nc, fI) + { + const DynList<label, 8>& nf = nc[fI]; + + label faceLabel(-1); + forAllRow(pointNewFaces, nf[0], pfI) + { + const label nfI = pointNewFaces(nf[0], pfI); + + if( help::areFacesEqual(nf, newFaces_[nfI]) ) + { + c[fI] = nfI; + faceLabel = nfI; + break; + } + } + + if( faceLabel < 0 ) + { + forAll(nf, pI) + pointNewFaces.append(nf[pI], newFaces_.size()); + c[fI] = newFaces_.size(); + newFaces_.appendList(nf); + } + } + } + } + else if( refType[cellI] == 2 ) + { + //- generate new cell from a hex cell where two layers intersect + //- generate mostly hex cells; + refineEdgeHexCell refEdgeHex(cellI, *this); + const DynList<DynList<DynList<label, 4>, 6>, 256>& cellsFromCell = + refEdgeHex.newCells(); + + forAll(cellsFromCell, cI) + { + const DynList<DynList<label, 4>, 6>& nc = cellsFromCell[cI]; + + # ifdef DEBUGLayer + Pout << "Adding cell " << (cI==0?cellI:nCells) + << " originating from cell " << cellI << endl; + # endif + + const label newCellI = cI==0?cellI:nCells++; + + newCellsFromCell.append(cellI, newCellI); + + cell& c = cells[newCellI]; + c.setSize(nc.size()); + + //- find face labels for this cell + forAll(nc, fI) + { + const DynList<label, 4>& nf = nc[fI]; + + label faceLabel(-1); + forAllRow(pointNewFaces, nf[0], pfI) + { + const label nfI = pointNewFaces(nf[0], pfI); + + if( help::areFacesEqual(nf, newFaces_[nfI]) ) + { + c[fI] = nfI; + faceLabel = nfI; + break; + } + } + + if( faceLabel < 0 ) + { + forAll(nf, pI) + pointNewFaces.append(nf[pI], newFaces_.size()); + c[fI] = newFaces_.size(); + newFaces_.appendList(nf); + } + } + } + } + else if( refType[cellI] == 3 ) + { + //- generate new cells from a hex at a corner where three + //- layers intersect + //- generate mostly hex cells + refineCornerHexCell refCell(cellI, *this); + const DynList<DynList<DynList<label, 4>, 6>, 256>& cellsFromCell = + refCell.newCells(); + + //- new points have been generated + pointNewFaces.setSize(mesh_.points().size()); + + //- recognise face cells in the graph of new faces + forAll(cellsFromCell, cI) + { + const DynList<DynList<label, 4>, 6>& nc = cellsFromCell[cI]; + + const label newCellI = cI==0?cellI:nCells++; + + newCellsFromCell.append(cellI, newCellI); + + cell& c = cells[newCellI]; + c.setSize(nc.size()); + + //- find face labels for this cell + forAll(nc, fI) + { + const DynList<label, 4>& nf = nc[fI]; + + label faceLabel(-1); + forAllRow(pointNewFaces, nf[0], pfI) + { + const label nfI = pointNewFaces(nf[0], pfI); + + if( help::areFacesEqual(nf, newFaces_[nfI]) ) + { + c[fI] = nfI; + faceLabel = nfI; + break; + } + } + + if( faceLabel < 0 ) + { + forAll(nf, pI) + pointNewFaces.append(nf[pI], newFaces_.size()); + c[fI] = newFaces_.size(); + newFaces_.appendList(nf); + } + } + } + } + else + { + FatalErrorIn + ( + "void refineBoundaryLayers::generateNewCells()" + ) << "Cannot refine boundary layer for cell " + << cellI << abort(FatalError); + } + } + + //- check the orientation of new faces, because owner and neighbour cells + //- may require a face to be flipped + const label nOrigInternalFaces = mesh_.nInternalFaces(); + + # ifdef USE_OMP + # pragma omp parallel + # endif + { + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + for(label fI=0;fI<nOrigInternalFaces;++fI) + { + const label own = owner[fI]; + const label nei = neighbour[fI]; + + if( facesFromFace_.sizeOfRow(fI) == 1 ) + continue; + + forAllRow(facesFromFace_, fI, cfI) + { + const label nfI = facesFromFace_(fI, cfI); + + //- find the new owner and neighbour cells of the new face + label newOwner(-1), newNeighbour(-1); + forAllRow(newCellsFromCell, own, cI) + { + const cell& cOwn = cells[newCellsFromCell(own, cI)]; + + const label pos = help::positionInList(nfI, cOwn); + + if( pos >= 0 ) + { + newOwner = newCellsFromCell(own, cI); + break; + } + } + + forAllRow(newCellsFromCell, nei, cI) + { + const cell& cNei = cells[newCellsFromCell(nei, cI)]; + + const label pos = help::positionInList(nfI, cNei); + + if( pos >= 0 ) + { + newNeighbour = newCellsFromCell(nei, cI); + break; + } + } + + if( newOwner > newNeighbour ) + { + DynList<label> rf; + rf.setSize(newFaces_.sizeOfRow(nfI)); + + forAll(rf, i) + rf[i] = newFaces_(nfI, i); + + rf = help::reverseFace(rf); + + newFaces_.setRow(nfI, rf); + } + } + } + } + + //- update cell sets + mesh_.updateCellSubsets(newCellsFromCell); + newCellsFromCell.setSize(0); + + //- point-faces addressing is not needed any more + pointNewFaces.setSize(0); + + //- copy newFaces to the mesh + # ifdef DEBUGLayer + Pout << "Copying internal faces " << endl; + Pout << "Original number of internal faces " << nOrigInternalFaces << endl; + # endif + + //- store internal faces originating from existing faces + labelLongList newFaceLabel(newFaces_.size()); + faces.setSize(newFaces_.size()); + + label currFace = 0; + for(label faceI=0;faceI<nOrigInternalFaces;++faceI) + { + forAllRow(facesFromFace_, faceI, ffI) + { + face& f = faces[currFace]; + newFaceLabel[currFace] = currFace; + ++currFace; + + const label newFaceI = facesFromFace_(faceI, ffI); + + f.setSize(newFaces_.sizeOfRow(newFaceI)); + + forAll(f, pI) + f[pI] = newFaces_(newFaceI, pI); + } + } + + //- store newly-generated internal faces + # ifdef DEBUGLayer + Pout << "Copying newly generated internal faces" << endl; + Pout << "nNewInternalFaces " << currFace << endl; + Pout << "numFacesBefore " << numFacesBefore << endl; + Pout << "Total number of faces " << newFaces_.size() << endl; + # endif + + for(label faceI=numFacesBefore;faceI<newFaces_.size();++faceI) + { + newFaceLabel[faceI] = currFace; + face& f = faces[currFace]; + ++currFace; + + f.setSize(newFaces_.sizeOfRow(faceI)); + + forAll(f, pI) + f[pI] = newFaces_(faceI, pI); + } + + //- store new boundary faces + # ifdef DEBUGLayer + Pout << "Copying boundary faces " << endl; + Pout << "currFace " << currFace << endl; + Pout << "Faces size " << faces.size() << endl; + Pout << "Initial number of faces " << facesFromFace_.size() << endl; + # endif + + PtrList<boundaryPatch>& boundaries = meshModifier.boundariesAccess(); + forAll(boundaries, patchI) + { + const label start = boundaries[patchI].patchStart(); + const label size = boundaries[patchI].patchSize(); + + const label newStart = currFace; + label nNewFacesInPatch(0); + for(label fI=0;fI<size;++fI) + { + const label faceI = start + fI; + + forAllRow(facesFromFace_, faceI, nfI) + { + face& f = faces[currFace]; + + //- update the new label + const label origFaceI = facesFromFace_(faceI, nfI); + newFaceLabel[origFaceI] = currFace; + facesFromFace_(faceI, nfI) = currFace; + ++currFace; + + //- copy the face into the mesh + f.setSize(newFaces_.sizeOfRow(origFaceI)); + forAll(f, pI) + f[pI] = newFaces_(origFaceI, pI); + + ++nNewFacesInPatch; + } + } + + //- update patch + boundaries[patchI].patchStart() = newStart; + boundaries[patchI].patchSize() = nNewFacesInPatch; + } + + if( Pstream::parRun() ) + { + # ifdef DEBUGLayer + Pout << "Copying processor faces" << endl; + # endif + + //- copy faces at inter-processor boundaries + PtrList<processorBoundaryPatch>& procBoundaries = + meshModifier.procBoundariesAccess(); + + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + const label newStart = currFace; + label nNewFacesInPatch(0); + for(label fI=0;fI<size;++fI) + { + const label faceI = start + fI; + forAllRow(facesFromFace_, faceI, nfI) + { + face& f = faces[currFace]; + + //- update the new label + const label origFaceI = facesFromFace_(faceI, nfI); + newFaceLabel[origFaceI] = currFace; + facesFromFace_(faceI, nfI) = currFace; + ++currFace; + + //- copy the face into the mesh + f.setSize(newFaces_.sizeOfRow(origFaceI)); + forAll(f, pI) + f[pI] = newFaces_(origFaceI, pI); + + ++nNewFacesInPatch; + } + } + + //- update patch + procBoundaries[patchI].patchStart() = newStart; + procBoundaries[patchI].patchSize() = nNewFacesInPatch; + } + } + + # ifdef DEBUGLayer + Pout << "Faces after refinement " << faces << endl; + Pout << "newFaceLabel " << newFaceLabel << endl; + # endif + + //- update face subsets + mesh_.updateFaceSubsets(facesFromFace_); + facesFromFace_.setSize(0); + newFaces_.setSize(0); + + //- update cells to match the faces + # ifdef DEBUGLayer + Pout << "Updating cells to match new faces" << endl; + # endif + + forAll(cells, cellI) + { + cell& c = cells[cellI]; + + forAll(c, fI) + c[fI] = newFaceLabel[c[fI]]; + } + + # ifdef DEBUGLayer + Pout << "Cleaning mesh " << endl; + # endif + + //- delete all adressing which is no longer up-to-date + meshModifier.clearAll(); + deleteDemandDrivenData(msePtr_); + + # ifdef DEBUGLayer + for(label procI=0;procI<Pstream::nProcs();++procI) + { + if( procI == Pstream::myProcNo() ) + { + forAll(cells, cellI) + { + const cell& c = cells[cellI]; + + DynList<edge> edges; + DynList<label> nAppearances; + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + forAll(f, eI) + { + const edge e = f.faceEdge(eI); + + const label pos = edges.containsAtPosition(e); + + if( pos < 0 ) + { + edges.append(e); + nAppearances.append(1); + } + else + { + ++nAppearances[pos]; + } + } + } + + bool badCell(false); + forAll(nAppearances, i) + if( nAppearances[i] != 2 ) + { + badCell = true; + break; + + } + + if( badCell ) + { + Pout << "Cell " << cellI + << " is not topologically closed" << endl; + + forAll(c, fI) + Pout << "Face " << c[fI] << " with points " + << faces[c[fI]] << endl; + Pout << "Cell edges " << edges << endl; + Pout << "nAppearances " << nAppearances << endl; + ::exit(1); + } + } + } + + returnReduce(1, sumOp<label>()); + } + + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + const label nInternalFaces = mesh_.nInternalFaces(); + + for(label procI=0;procI<Pstream::nProcs();++procI) + { + if( procI == Pstream::myProcNo() ) + { + forAll(faces, faceI) + { + if( faceI < nInternalFaces && neighbour[faceI] < 0 ) + { + Pout << "Num interface faces " << nInternalFaces + << " current face " << faceI + << " face points " << faces[faceI] << endl; + ::exit(1); + } + Pout << "Face " << faceI << " owner " << owner[faceI] + << " neighbour " << neighbour[faceI] + << " face points " << faces[faceI] << endl; + } + + forAll(cells, cellI) + Pout << "Cell " << cellI << " has faces " + << cells[cellI] << endl; + } + + returnReduce(procI, maxOp<label>()); + } + # endif + + Info << "Finished generating new cells " << endl; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // + diff --git a/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersFaces.C b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersFaces.C new file mode 100644 index 0000000000000000000000000000000000000000..aa1858296fff0a4158d18009dd486b7d57d62931 --- /dev/null +++ b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersFaces.C @@ -0,0 +1,1235 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "refineBoundaryLayers.H" +#include "meshSurfaceEngine.H" +#include "demandDrivenData.H" +#include "FixedList.H" +#include "helperFunctions.H" + +//#define DEBUGLayer + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void refineBoundaryLayers::refineFace +( + const face& f, + const FixedList<label, 2>& nLayersInDirection, + DynList<DynList<label, 4>, 128>& newFaces +) +{ + //- this face must be a quad + if( f.size() != 4 ) + { + WarningIn + ( + "void refineBoundaryLayers::refineFace(const face&," + " const FixedList<label, 2>&, DynList<DynList<label, 4> >&)" + ) << "Face " << f << " is not a quad" << endl; + return; + } + + //- direction 0 represents edges 0 and 2 + //- direction 1 represents edges 1 and 3 + if( (nLayersInDirection[0] <= 1) && (nLayersInDirection[1] <= 1) ) + { + //- this face may comprise of some split edges + DynList<label, 64> newF; + forAll(f, eI) + { + const edge e = f.faceEdge(eI); + + //- add the current point label + newF.append(f[eI]); + + //- check if a split edge matches this face edge + forAllRow(splitEdgesAtPoint_, f[eI], peI) + { + const label seI = splitEdgesAtPoint_(f[eI], peI); + const edge& se = splitEdges_[seI]; + + if( e == se ) + { + //- check the orientation and add new vertices created + //- on this edge + const label s = newVerticesForSplitEdge_.sizeOfRow(seI) - 1; + if( e.start() == se.start() ) + { + for(label pI=1;pI<s;++pI) + newF.append(newVerticesForSplitEdge_(seI, pI)); + } + else + { + for(label pI=s-1;pI>0;--pI) + newF.append(newVerticesForSplitEdge_(seI, pI)); + } + } + } + } + + newFaces.setSize(1); + newFaces[0] = newF; + return; + } + + //- check which face edge is a direction 0 and which one is a direction 1 + label dir0(-1), dir1(-1); + labelPair dir0Edges(-1, -1), dir1Edges(-1, -1); + forAll(f, eI) + { + const edge e = f.faceEdge(eI); + + label ses(-1), see(-1); + bool start(false), end(false); + forAllRow(splitEdgesAtPoint_, e.start(), i) + { + const edge& se = splitEdges_[splitEdgesAtPoint_(e.start(), i)]; + + if( (se.start() == e.start()) && (se.end() == f.prevLabel(eI)) ) + { + ses = splitEdgesAtPoint_(e.start(), i); + start = true; + break; + } + } + + forAllRow(splitEdgesAtPoint_, e.end(), i) + { + const edge& se = splitEdges_[splitEdgesAtPoint_(e.end(), i)]; + + if( (se.start() == e.end()) && (se.end() == f[(eI+2)%4]) ) + { + see = splitEdgesAtPoint_(e.end(), i); + end = true; + break; + } + } + + if( start && end ) + { + if( dir0 == -1 ) + { + dir0 = eI; + dir0Edges = labelPair(ses, see); + } + else if( dir1 == -1 ) + { + dir1 = eI; + dir1Edges = labelPair(ses, see); + } + else + { + FatalErrorIn + ( + "void refineBoundaryLayers::refineFace(const face&," + " const FixedList<label, 2>&, DynList<DynList<label, 4> >&)" + ) << "More than two split directions for a face" + << abort(FatalError); + } + } + } + + # ifdef DEBUGLayer + Pout << "Refining face " << f << endl; + Pout << "Splits in direction " << nLayersInDirection << endl; + Pout << "Here " << endl; + Pout << "Dir0 " << dir0 << endl; + Pout << "dir0Edges " << dir0Edges << endl; + Pout << "Dir1 " << dir1 << endl; + Pout << "dir1Edges " << dir1Edges << endl; + # endif + + if( (dir0 < 0) && (dir1 < 0) ) + { + Pout << "Refining face " << f << endl; + forAll(f, pI) + { + if( splitEdgesAtPoint_.size() >= f[pI] ) + Pout << "Split edges at point " << f[pI] + << " are " << splitEdgesAtPoint_[f[pI]] << endl; + } + Pout << "Splits in direction " << nLayersInDirection << endl; + Pout << "Here " << endl; + Pout << "Dir0 " << dir0 << endl; + Pout << "dir0Edges " << dir0Edges << endl; + Pout << "Dir1 " << dir1 << endl; + Pout << "dir1Edges " << dir1Edges << endl; + + FatalErrorIn + ( + "void refineBoundaryLayers::refineFace(const face&," + " const FixedList<label, 2>&, DynList<DynList<label, 4> >&)" + ) << "Cannot find split edges for a face" << abort(FatalError); + } + + //- in case of only one refinement direction, it must direction 0 + if( (dir1 != -1) && (dir0 == -1) ) + { + dir0 = dir1; + dir0Edges = dir1Edges; + dir1 = -1; + } + else if( (dir0 != -1) && (dir1 != -1) && (dir1 != f.fcIndex(dir0)) ) + { + //- alternate value to preserve correct face orientation + const label add = dir0; + dir0 = dir1; + dir1 = add; + + const labelPair lpAdd = dir0Edges; + dir0Edges = dir1Edges; + dir1Edges = lpAdd; + } + + //- permutate the number of refinements in each direction + const label nLayersDir0 = dir0>=0?nLayersInDirection[dir0%2]:1; + const label nLayersDir1 = dir1>=0?nLayersInDirection[dir1%2]:1; + + # ifdef DEBUGLayer + Pout << "Face has points " << f << endl; + Pout << "dirEdges0 " << dir0Edges << endl; + Pout << "dir1Edges " << dir1Edges << endl; + if( dir0 >= 0 ) + { + Pout << "Points on edge " << dir0Edges.first() << " with nodes " + << splitEdges_[dir0Edges.first()] + << " are " << newVerticesForSplitEdge_[dir0Edges.first()] << endl; + Pout << "Points on edge " << dir0Edges.second() << " with nodes " + << splitEdges_[dir0Edges.second()] + << " are " << newVerticesForSplitEdge_[dir0Edges.second()] << endl; + } + if( dir1 >= 0 ) + { + Pout << "Points on edge " << dir1Edges.first() << " with nodes " + << splitEdges_[dir1Edges.first()] + << " are " << newVerticesForSplitEdge_[dir1Edges.first()] << endl; + Pout << "Points on edge " << dir1Edges.second() << " with nodes " + << splitEdges_[dir1Edges.second()] + << " are " << newVerticesForSplitEdge_[dir1Edges.second()] << endl; + } + Pout << "nLayersDir0 " << nLayersDir0 << endl; + Pout << "nLayersDir1 " << nLayersDir1 << endl; + # endif + + //- map the face onto a matrix for easier orientation + DynList<DynList<label> > facePoints; + facePoints.setSize(nLayersDir0+1); + forAll(facePoints, i) + { + facePoints[i].setSize(nLayersDir1+1); + facePoints[i] = -1; + } + + //- add points in the matrix + for(label i=0;i<nLayersDir0;++i) + { + facePoints[i][0] = newVerticesForSplitEdge_(dir0Edges.second(), i); + facePoints[i][nLayersDir1] = + newVerticesForSplitEdge_(dir0Edges.first(), i); + } + facePoints[nLayersDir0][0] = splitEdges_[dir0Edges.second()].end(); + facePoints[nLayersDir0][nLayersDir1] = splitEdges_[dir0Edges.first()].end(); + + for(label i=1;i<nLayersDir1;++i) + { + facePoints[0][i] = newVerticesForSplitEdge_(dir1Edges.first(), i); + facePoints[nLayersDir0][i] = + newVerticesForSplitEdge_(dir1Edges.second(), i); + } + + //- create missing vertices if there are any + pointFieldPMG& points = mesh_.points(); + const point v00 = points[facePoints[0][0]]; + const point v10 = points[facePoints[nLayersDir0][0]]; + const point v01 = points[facePoints[0][nLayersDir1]]; + const point v11 = points[facePoints[nLayersDir0][nLayersDir1]]; + + # ifdef DEBUGLayer + forAll(points, pointI) + Pout << "Point " << pointI << " coordinates " << points[pointI] << endl; + Pout << "v00 = " << v00 << endl; + Pout << "v10 = " << v10 << endl; + Pout << "v11 = " << v11 << endl; + Pout << "v01 = " << v01 << endl; + # endif + + forAll(facePoints, i) + { + forAll(facePoints[i], j) + { + if( facePoints[i][j] < 0 ) + { + # ifdef DEBUGLayer + Pout << "Determining u " << facePoints[0][0] + << " coordinates " << points[facePoints[0][0]] << endl; + Pout << "Other point " << facePoints[i][0] + << " coordinates " << points[facePoints[i][0]] << endl; + Pout << "Points at aplit edge " + << newVerticesForSplitEdge_[dir0Edges.second()] << endl;} + # endif + + const scalar u + ( + Foam::mag(points[facePoints[i][0]] - v00) / + splitEdges_[dir0Edges.second()].mag(points) + ); + + # ifdef DEBUGLayer + Pout << "Determining v " << facePoints[0][0] + << " coordinates " << points[facePoints[0][0]] << endl; + Pout << "Other point " << facePoints[0][j] + << " coordinates " << points[facePoints[0][j]] << endl; + Pout << "Points at aplit edge " + << newVerticesForSplitEdge_[dir1Edges.first()] << endl;} + # endif + + const scalar v + ( + Foam::mag(points[facePoints[0][j]] - v00) / + splitEdges_[dir1Edges.first()].mag(points) + ); + + # ifdef DEBUGLayer + Pout << "Generating point of face " << endl; + Pout << "u = " << u << endl; + Pout << "v = " << v << endl;} + # endif + + //- calculate the coordinates of the missing point via + //- transfinite interpolation + const point newP + ( + (1.0 - u) * (1.0 - v) * v00 + + u * (1.0 - v) * v10 + + u * v * v11 + + (1.0 - u) * v * v01 + ); + + # ifdef DEBUGLayer + Pout << "Point coordinate " << newP << endl; + # endif + + //- add the vertex to the mesh + facePoints[i][j] = points.size(); + points.append(newP); + } + } + } + + # ifdef DEBUGLayer + Pout << "Face points after creating vertices " << facePoints << endl; + # endif + + //- Finally, create the faces + for(label j=0;j<nLayersDir1;++j) + { + for(label i=0;i<nLayersDir0;++i) + { + //- create quad face + DynList<label, 4> f; + + f.append(facePoints[i][j]); + + if( (i == (nLayersDir0 - 1)) && (j == 0) ) + { + # ifdef DEBUGLayer + Pout << "1. Adding additional points on edge " << endl; + # endif + + //- add additional points on edge + const label eLabel = dir0Edges.second(); + const label size = + newVerticesForSplitEdge_.sizeOfRow(eLabel) - 1; + + for(label index=i+1;index<size;++index) + f.append(newVerticesForSplitEdge_(eLabel, index)); + } + + f.append(facePoints[i+1][j]); + + if( + (dir1 != -1) && + (i == (nLayersDir0 - 1)) && + (j == (nLayersDir1 - 1)) + ) + { + # ifdef DEBUGLayer + Pout << "2. Adding additional points on edge " << endl; + # endif + + //- add additional points on edge + const label eLabel = dir1Edges.second(); + const label size = + newVerticesForSplitEdge_.sizeOfRow(eLabel) - 1; + + for(label index=j+1;index<size;++index) + f.append(newVerticesForSplitEdge_(eLabel, index)); + } + + f.append(facePoints[i+1][j+1]); + + if( (i == (nLayersDir0 - 1)) && (j == (nLayersDir1 - 1)) ) + { + # ifdef DEBUGLayer + Pout << "3. Adding additional points on edge " << endl; + # endif + + const label eLabel = dir0Edges.first(); + const label size = + newVerticesForSplitEdge_.sizeOfRow(eLabel) - 2; + for(label index=size;index>i;--index) + f.append(newVerticesForSplitEdge_(eLabel, index)); + } + + f.append(facePoints[i][j+1]); + + if( (dir1 != -1) && (i == 0) && (j == (nLayersDir1 - 1)) ) + { + # ifdef DEBUGLayer + Pout << "4. Adding additional points on edge " << endl; + # endif + + const label eLabel = dir1Edges.first(); + const label size = + newVerticesForSplitEdge_.sizeOfRow(eLabel) - 2; + for(label index=size;index>j;--index) + f.append(newVerticesForSplitEdge_(eLabel, index)); + } + + newFaces.append(f); + } + } + + # ifdef DEBUGLayer + Pout << "Input face " << f << endl; + Pout << "Decomposed faces are " << newFaces << endl; + //if( (nLayersInDirection[0] > 1) && (nLayersInDirection[1] > 1) ) + //::exit(1); + # endif +} + +void refineBoundaryLayers::sortFacePoints +( + const label faceI, + DynList<DynList<label> >& facePoints, + const label transpose +) const +{ + const faceListPMG& faces = mesh_.faces(); + const face& f = faces[faceI]; + + # ifdef DEBUGLayer + Pout << "Creating matrix of points on a split face " << faceI << endl; + Pout << "Face comprises of points " << f << endl; + Pout << "New faces from face " << facesFromFace_.sizeOfRow(faceI) << endl; + # endif + + label procStart = mesh_.faces().size(); + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); + if( Pstream::parRun() ) + procStart = procBoundaries[0].patchStart(); + + if( + (faceI < procStart) || + procBoundaries[mesh_.faceIsInProcPatch(faceI)].owner() + ) + { + //- orientation of new faces is the same as the face itself + //- start the procedure by finding the number of splits in + //- both i and j direction + label numSplitsI(1); + + const label pos = f.which(newFaces_(facesFromFace_(faceI, 0), 0)); + + forAllRow(facesFromFace_, faceI, i) + { + const label nfI = facesFromFace_(faceI, i); + + if( (numSplitsI == 1) && newFaces_.contains(nfI, f.nextLabel(pos)) ) + { + numSplitsI = i + 1; + break; + } + } + + const label numSplitsJ = (facesFromFace_.sizeOfRow(faceI) / numSplitsI); + + # ifdef DEBUGLayer + Pout << "Pos " << pos << endl; + Pout << "Num splits in direction 0 " << numSplitsI << endl; + Pout << "Num splits in direction 1 " << numSplitsJ << endl; + # endif + + facePoints.setSize(numSplitsI+1); + forAll(facePoints, i) + facePoints[i].setSize(numSplitsJ+1); + + //- start filling in the matrix + forAllRow(facesFromFace_, faceI, fI) + { + const label nfI = facesFromFace_(faceI, fI); + + const label i = fI % numSplitsI; + const label j = fI / numSplitsI; + + # ifdef DEBUGLayer + Pout << "New face " << fI << " is " << newFaces_[nfI] << endl; + Pout << " i = " << i << endl; + Pout << " j = " << j << endl; + # endif + + if( newFaces_.sizeOfRow(nfI) == 4 ) + { + facePoints[i][j] = newFaces_(nfI, 0); + facePoints[i+1][j] = newFaces_(nfI, 1); + facePoints[i+1][j+1] = newFaces_(nfI, 2); + facePoints[i][j+1] = newFaces_(nfI, 3); + } + else + { + if( j == 0 ) + { + forAllRow(newFaces_, nfI, pI) + if( f.which(newFaces_(nfI, pI)) >= 0 ) + { + facePoints[i+1][0] = newFaces_(nfI, pI); + break; + } + } + else if( i == 0 ) + { + forAllRow(newFaces_, nfI, pI) + if( f.which(newFaces_(nfI, pI)) >= 0 ) + { + facePoints[0][j+1] = newFaces_(nfI, pI); + break; + } + } + else + { + forAllRow(newFaces_, nfI, pI) + if( f.which(newFaces_(nfI, pI)) >= 0 ) + { + facePoints[i+1][j+1] = newFaces_(nfI, pI); + break; + } + } + } + } + + # ifdef DEBUGLayer + Pout << "Generated matrix of points on face " << faceI + << " is " << facePoints << endl; + # endif + } + else + { + //- this situation exists on inter-processor boundaries + //- on neighbour processor. i and j coordinates are reversed + label numSplitsJ(1); + + const label pos = f.which(newFaces_(facesFromFace_(faceI, 0), 0)); + + forAllRow(facesFromFace_, faceI, j) + { + const label nfI = facesFromFace_(faceI, j); + + if( (numSplitsJ == 1) && newFaces_.contains(nfI, f.prevLabel(pos)) ) + { + numSplitsJ = j + 1; + break; + } + } + + const label numSplitsI = (facesFromFace_.sizeOfRow(faceI) / numSplitsJ); + + # ifdef DEBUGLayer + Pout << "2. Face comprises of points " << f << endl; + Pout << "2. Num splits in direction 0 " << numSplitsI << endl; + Pout << "2. Num splits in direction 1 " << numSplitsJ << endl; + # endif + + facePoints.setSize(numSplitsI+1); + forAll(facePoints, i) + facePoints[i].setSize(numSplitsJ+1); + + //- start filling in the matrix + forAllRow(facesFromFace_, faceI, fI) + { + const label nfI = facesFromFace_(faceI, fI); + + const label i = fI / numSplitsJ; + const label j = fI % numSplitsJ; + + # ifdef DEBUGLayer + Pout << "2. New face " << fI << " is " << newFaces_[nfI] << endl; + Pout << "2. i = " << i << endl; + Pout << "2. j = " << j << endl; + # endif + + if( newFaces_.sizeOfRow(nfI) == 4 ) + { + facePoints[i][j] = newFaces_(nfI, 0); + facePoints[i+1][j] = newFaces_(nfI, 1); + facePoints[i+1][j+1] = newFaces_(nfI, 2); + facePoints[i][j+1] = newFaces_(nfI, 3); + } + else + { + if( i == 0 ) + { + forAllRow(newFaces_, nfI, pI) + if( f.which(newFaces_(nfI, pI)) >= 0 ) + { + facePoints[0][j+1] = newFaces_(nfI, pI); + break; + } + } + else if( j == 0 ) + { + forAllRow(newFaces_, nfI, pI) + if( f.which(newFaces_(nfI, pI)) >= 0 ) + { + facePoints[i+1][0] = newFaces_(nfI, pI); + break; + } + } + else + { + forAllRow(newFaces_, nfI, pI) + if( f.which(newFaces_(nfI, pI)) >= 0 ) + { + facePoints[i+1][j+1] = newFaces_(nfI, pI); + break; + } + } + } + } + + # ifdef DEBUGLayer + Pout << "Generated matrix of points on processor face " << faceI + << " is " << facePoints << endl; + # endif + } + + if( transpose ) + { + DynList<DynList<label> > transposedFacePoints; + transposedFacePoints.setSize(facePoints[0].size()); + forAll(transposedFacePoints, j) + transposedFacePoints[j].setSize(facePoints.size()); + + forAll(facePoints, i) + forAll(facePoints[i], j) + transposedFacePoints[j][i] = facePoints[i][j]; + + facePoints = transposedFacePoints; + + # ifdef DEBUGLayer + Pout << "Transposed face points " << facePoints << endl; + # endif + } +} + +void refineBoundaryLayers::sortFaceFaces +( + const label faceI, + DynList<DynList<label> >& faceFaces, + const label transpose +) const +{ + const faceListPMG& faces = mesh_.faces(); + const face& f = faces[faceI]; + + # ifdef DEBUGLayer + Pout << "Creating matrix of faces on a split face " << faceI << endl; + Pout << "Face comprises of points " << f << endl; + # endif + + label procStart = mesh_.faces().size(); + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); + if( Pstream::parRun() ) + procStart = procBoundaries[0].patchStart(); + + if( + (faceI < procStart) || + procBoundaries[mesh_.faceIsInProcPatch(faceI)].owner() + ) + { + //- orientation of new faces is the same as the face itself + //- start the procedure by finding the number of splits in + //- both i and j direction + label numSplitsI(1); + + const label pos = f.which(newFaces_(facesFromFace_(faceI, 0), 0)); + + forAllRow(facesFromFace_, faceI, i) + { + const label nfI = facesFromFace_(faceI, i); + + if( (numSplitsI == 1) && newFaces_.contains(nfI, f.nextLabel(pos)) ) + { + numSplitsI = i + 1; + break; + } + } + + label numSplitsJ = (facesFromFace_.sizeOfRow(faceI) / numSplitsI); + + # ifdef DEBUGLayer + Pout << "3. Num splits in direction 0 " << numSplitsI << endl; + Pout << "3. Num splits in direction 1 " << numSplitsJ << endl; + # endif + + faceFaces.setSize(numSplitsI); + forAll(faceFaces, i) + faceFaces[i].setSize(numSplitsJ); + + //- start filling in the matrix + forAllRow(facesFromFace_, faceI, fI) + { + const label nfI = facesFromFace_(faceI, fI); + + const label i = fI % numSplitsI; + const label j = fI / numSplitsI; + + # ifdef DEBUGLayer + Pout << "3. New face " << fI << " is " << newFaces_[nfI] << endl; + Pout << "3. i = " << i << endl; + Pout << "3. j = " << j << endl; + # endif + + faceFaces[i][j] = nfI; + } + + # ifdef DEBUGLayer + Pout << "3. Generated matrix of points on face " << faceI + << " is " << faceFaces << endl; + # endif + } + else + { + //- this situation exists on inter-processor boundaries + //- on neighbour processor. i and j coordinates are reversed + label numSplitsJ(1); + + const label pos = f.which(newFaces_(facesFromFace_(faceI, 0), 0)); + + forAllRow(facesFromFace_, faceI, j) + { + const label nfI = facesFromFace_(faceI, j); + + if( (numSplitsJ == 1) && newFaces_.contains(nfI, f.prevLabel(pos)) ) + { + numSplitsJ = j + 1; + break; + } + } + + const label numSplitsI = (facesFromFace_.sizeOfRow(faceI) / numSplitsJ); + + # ifdef DEBUGLayer + Pout << "4. Num splits in direction 0 " << numSplitsI << endl; + Pout << "4. Num splits in direction 1 " << numSplitsJ << endl; + # endif + + faceFaces.setSize(numSplitsI); + forAll(faceFaces, i) + faceFaces[i].setSize(numSplitsJ); + + //- start filling in the matrix + forAllRow(facesFromFace_, faceI, fI) + { + const label nfI = facesFromFace_(faceI, fI); + + const label i = fI / numSplitsJ; + const label j = fI % numSplitsJ; + + # ifdef DEBUGLayer + Pout << "4. New face " << fI << " is " << newFaces_[nfI] << endl; + Pout << "4. i = " << i << endl; + Pout << "4. j = " << j << endl; + # endif + + faceFaces[i][j] = nfI; + } + + # ifdef DEBUGLayer + Pout << "4. Generated matrix of faces on processor face " << faceI + << " is " << faceFaces << endl; + # endif + } + + if( transpose ) + { + DynList<DynList<label> > transposedFaceFaces; + transposedFaceFaces.setSize(faceFaces[0].size()); + forAll(transposedFaceFaces, j) + transposedFaceFaces[j].setSize(faceFaces.size()); + + forAll(faceFaces, i) + forAll(faceFaces[i], j) + transposedFaceFaces[j][i] = faceFaces[i][j]; + + faceFaces = transposedFaceFaces; + + # ifdef DEBUGLayer + Pout << "Transposed face faces " << faceFaces << endl; + # endif + } +} + +void refineBoundaryLayers::generateNewFaces() +{ + //- generate new boundary and inter-processor faces + const meshSurfaceEngine& mse = surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& facePatches = mse.boundaryFacePatches(); + const edgeList& edges = mse.edges(); + const labelList& bp = mse.bp(); + const VRWGraph& bfEdges = mse.faceEdges(); + const VRWGraph& bpEdges = mse.boundaryPointEdges(); + const VRWGraph& beFaces = mse.edgeFaces(); + + //- mesh data + const label nInternalFaces = mesh_.nInternalFaces(); + const faceListPMG& faces = mesh_.faces(); + + //- container for faces + facesFromFace_.setSize(faces.size()); + newFaces_.clear(); + + //- split internal faces + for(label faceI=0;faceI<nInternalFaces;++faceI) + { + const face& f = faces[faceI]; + + //- only quad faces can be split + if( f.size() != 4 ) + { + facesFromFace_.append(faceI, newFaces_.size()); + newFaces_.appendList(f); + continue; + } + + //- check if there exist an edge of the face at the boundary + FixedList<label, 2> nRefinementInDirection(1); + + forAll(f, eI) + { + const edge fe = f.faceEdge(eI); + + const label bps = bp[fe.start()]; + + if( bps < 0 ) + continue; + + forAllRow(bpEdges, bps, bpsI) + { + const label beI = bpEdges(bps, bpsI); + + if( edges[beI] == fe ) + { + //- this edge is attached to the boundary + //- get the number of layers for neighbouring cells + const label nSplits0 = nLayersAtBndFace_[beFaces(beI, 0)]; + const label nSplits1 = nLayersAtBndFace_[beFaces(beI, 1)]; + + //- set the number of layers for the given direction + const label dir = eI % 2; + nRefinementInDirection[dir] = + Foam::max + ( + nRefinementInDirection[dir], + Foam::max(nSplits0, nSplits1) + ); + } + } + } + + //- refine the face + DynList<DynList<label, 4>, 128> newFacesForFace; + refineFace(f, nRefinementInDirection, newFacesForFace); + + //- store decomposed faces + forAll(newFacesForFace, fI) + { + facesFromFace_.append(faceI, newFaces_.size()); + newFaces_.appendList(newFacesForFace[fI]); + } + + # ifdef DEBUGLayer + Pout << "Internal face " << faceI << " with points " << f + << " is refined " << endl; + forAllRow(facesFromFace_, faceI, i) + Pout << "New face " << i << " is " + << newFaces_[facesFromFace_(faceI, i)] << endl; + DynList<DynList<label> > tralala; + sortFacePoints(faceI, tralala); + # endif + } + + //- refine boundary faces where needed + //- it is required in locations where two or three layers intersect + const label startingBoundaryFace = mesh_.boundaries()[0].patchStart(); + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + const label faceI = startingBoundaryFace + bfI; + + //- only quad faces can be split + if( bf.size() != 4 ) + { + facesFromFace_.append(faceI, newFaces_.size()); + newFaces_.appendList(bf); + continue; + } + + //- check whether this face shall be refined and in which directions + FixedList<label, 2> nRefinementInDirection(1); + + forAll(bf, eI) + { + const label beI = bfEdges(bfI, eI); + + //- get the neighbour face over the edge + label neiFace = beFaces(beI, 0); + + if( beFaces.sizeOfRow(beI) != 2 ) + continue; + + if( neiFace == bfI ) + neiFace = beFaces(beI, 1); + + //- faces cannot be in the same layer + if( + layerAtPatch_[facePatches[neiFace]] == + layerAtPatch_[facePatches[bfI]] + ) + continue; + + //- set the refinement direction for this face + nRefinementInDirection[eI%2] = nLayersAtBndFace_[neiFace]; + } + + //- refine the face + DynList<DynList<label, 4>, 128> newFacesForFace; + refineFace(bf, nRefinementInDirection, newFacesForFace); + + //- store the refined faces + forAll(newFacesForFace, fI) + { + facesFromFace_.append(faceI, newFaces_.size()); + newFaces_.appendList(newFacesForFace[fI]); + } + + # ifdef DEBUGLayer + Pout << "Boundary face " << faceI << " with points " << bf + << " owner cell " << mesh_.owner()[faceI] << " is refined " << endl; + forAllRow(facesFromFace_, faceI, i) + Pout << "New face " << i << " is " + << newFaces_[facesFromFace_(faceI, i)] << endl; + # endif + } + + if( Pstream::parRun() ) + { + //- refine faces at interprocessor boundaries + const PtrList<processorBoundaryPatch>& procBoundaries = + mesh_.procBoundaries(); + + //- exchange information about the number of splits + //- to other processors + std::map<label, DynList<labelPair, 2> > localSplits; + forAll(procBoundaries, patchI) + { + labelLongList sendData; + + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + for(label fI=0;fI<size;++fI) + { + const label faceI = start + fI; + const face& f = faces[faceI]; + + forAll(f, eI) + { + const edge fe = f.faceEdge(eI); + + const label bps = bp[fe.start()]; + + if( bps < 0 ) + continue; + + forAllRow(bpEdges, bps, bpeI) + { + const label beI = bpEdges(bps, bpeI); + + if( edges[beI] == fe ) + { + //- this edge is attached to the boundary + //- get the number of layers for neighbouring cell + const label nSplits0 = + nLayersAtBndFace_[beFaces(beI, 0)]; + + //- add the data to the list for sending + const label dir = (eI % 2); + + # ifdef DEBUGLayer + Pout << "Face " << fI << " owner of proc patch " + << procBoundaries[patchI].myProcNo() + << " nei proc " + << procBoundaries[patchI].neiProcNo() + << " bnd face patch " + << facePatches[beFaces(beI, 0)] + << " direction " << dir + << " nSplits " << nSplits0 << endl; + # endif + + //- add face label, direction + //- and the number of splits + sendData.append(fI); + sendData.append(dir); + sendData.append(nSplits0); + localSplits[faceI].append(labelPair(dir, nSplits0)); + } + } + } + } + + OPstream toOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo(), + sendData.byteSize() + ); + + toOtherProc << sendData; + } + + //- receive data from other procesors + forAll(procBoundaries, patchI) + { + //- get the data sent from the neighbour processor + labelList receivedData; + + IPstream fromOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo() + ); + + fromOtherProc >> receivedData; + + const label start = procBoundaries[patchI].patchStart(); + + label counter(0); + while( counter < receivedData.size() ) + { + const label fI = receivedData[counter++]; + const label dir = ((receivedData[counter++] + 1) % 2); + const label nSplits = receivedData[counter++]; + + DynList<labelPair, 2>& currentSplits = localSplits[start+fI]; + forAll(currentSplits, i) + { + if( currentSplits[i].first() == dir ) + currentSplits[i].second() = + Foam::max(currentSplits[i].second(), nSplits); + } + } + } + + # ifdef DEBUGLayer + returnReduce(1, sumOp<label>()); + Pout << "Starting splitting processor boundaries" << endl; + # endif + + //- perform splitting + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + for(label fI=0;fI<size;++fI) + { + const label faceI = start + fI; + + std::map<label, DynList<labelPair, 2> >::const_iterator it = + localSplits.find(faceI); + + if( it == localSplits.end() ) + { + //- this face is not split + facesFromFace_.append(faceI, newFaces_.size()); + newFaces_.appendList(faces[faceI]); + continue; + } + + //- split the face and add the faces to the list + if( procBoundaries[patchI].owner() ) + { + //- this processor owns this patch + FixedList<label, 2> nLayersInDirection(1); + const DynList<labelPair, 2>& dirSplits = it->second; + forAll(dirSplits, i) + nLayersInDirection[dirSplits[i].first()] = + dirSplits[i].second(); + + # ifdef DEBUGLayer + Pout << "Face " << fI << " at owner processor " + << procBoundaries[patchI].myProcNo() + << " neighbour processor " + << procBoundaries[patchI].neiProcNo() + << " face " << faces[faceI] << " refinement direction " + << nLayersInDirection << endl; + # endif + + DynList<DynList<label, 4>, 128> facesFromFace; + refineFace(faces[faceI], nLayersInDirection, facesFromFace); + + //- add faces + forAll(facesFromFace, i) + { + facesFromFace_.append(faceI, newFaces_.size()); + newFaces_.appendList(facesFromFace[i]); + } + } + else + { + //- reverse the face before splitting + FixedList<label, 2> nLayersInDirection(1); + const DynList<labelPair, 2>& dirSplits = it->second; + forAll(dirSplits, i) + nLayersInDirection[(dirSplits[i].first()+1)%2] = + dirSplits[i].second(); + + const face rFace = faces[faceI].reverseFace(); + + # ifdef DEBUGLayer + Pout << "Face " << fI << " at owner processor " + << procBoundaries[patchI].myProcNo() + << " neighbour processor " + << procBoundaries[patchI].neiProcNo() + << " face " << rFace << " refinement direction " + << nLayersInDirection << endl; + # endif + + DynList<DynList<label, 4>, 128> facesFromFace; + refineFace(rFace, nLayersInDirection, facesFromFace); + + forAll(facesFromFace, i) + { + const DynList<label, 4>& df = facesFromFace[i]; + DynList<label, 4> rFace = help::reverseFace(df); + + facesFromFace_.append(faceI, newFaces_.size()); + newFaces_.appendList(rFace); + } + } + } + } + + # ifdef DEBUGLayer + returnReduce(1, sumOp<label>()); + for(label procI=0;procI<Pstream::nProcs();++procI) + { + if( procI == Pstream::myProcNo() ) + { + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + for(label fI=0;fI<size;++fI) + { + const label faceI = start + fI; + const face& f = faces[faceI]; + Pout << "Face " << fI << " in patch " + << procBoundaries[patchI].patchName() + << " has nodes " << f + << " local splits " << localSplits[faceI] + << " new faces from face " << facesFromFace_[faceI] + << endl; + + Pout << " Face points "; + forAll(f, pI) + Pout << mesh_.points()[f[pI]] << " "; + Pout << endl; + + forAllRow(facesFromFace_, faceI, ffI) + { + const label nfI = facesFromFace_(faceI, ffI); + Pout << "New face " << ffI << " with label " << nfI + << " consists of points "; + forAllRow(newFaces_, nfI, pI) + Pout << mesh_.points()[newFaces_(nfI, pI)] + << " "; + Pout << endl; + } + } + } + } + + returnReduce(1, sumOp<label>()); + } + + returnReduce(1, sumOp<label>()); + //::exit(1); + # endif + } + + # ifdef DEBUGLayer + returnReduce(1, sumOp<label>()); + + for(label procI=0;procI<Pstream::nProcs();++procI) + { + if( procI == Pstream::myProcNo() ) + { + Pout << "facesFromFace_ " << facesFromFace_ << endl; + Pout << "newFaces_ " << newFaces_ << endl; + } + + returnReduce(1, sumOp<label>()); + } + # endif + + Info << "Finished refining boundary-layer faces " << endl; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // + diff --git a/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersFunctions.C b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersFunctions.C new file mode 100644 index 0000000000000000000000000000000000000000..8e56002c7ff9d795677c993341baa71465c8fc73 --- /dev/null +++ b/meshLibrary/utilities/boundaryLayers/refineBoundaryLayersFunctions.C @@ -0,0 +1,1202 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "refineBoundaryLayers.H" +#include "meshSurfaceEngine.H" +#include "helperFunctions.H" +#include "polyMeshGenAddressing.H" +#include "polyMeshGen2DEngine.H" +#include "VRWGraphList.H" + +#include "labelledPair.H" +#include "labelledScalar.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGLayer + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace bndLayerOps +{ + +class meshBndLayerNeighbourOperator +{ + const meshSurfaceEngine& mse_; + const label size_; + +public: + + meshBndLayerNeighbourOperator(const meshSurfaceEngine& mse) + : + mse_(mse), + size_(mse.boundaryFaces().size()) + {} + + label size() const + { + return size_; + } + + void operator()(const label bfI, DynList<label>& neighbourFaces) const + { + neighbourFaces.clear(); + + const cellListPMG& cells = mse_.cells(); + + const labelList& faceOwner = mse_.faceOwners(); + const label cellI = faceOwner[bfI]; + const cell& c = cells[cellI]; + + const VRWGraph& faceEdges = mse_.faceEdges(); + const VRWGraph& edgeFaces = mse_.edgeFaces(); + + forAllRow(faceEdges, bfI, feI) + { + const label edgeI = faceEdges(bfI, feI); + + if( edgeFaces.sizeOfRow(edgeI) == 2 ) + { + label nei = edgeFaces(edgeI, 0); + + if( nei == bfI ) + nei = edgeFaces(edgeI, 1); + + //- faces must not be part of the same cell + if( faceOwner[nei] == cellI ) + continue; + + //- owner cell of the other face must + //- have cellI as its neighbour + const cell& neiC = cells[faceOwner[nei]]; + bool sharedFace(false); + forAll(c, fI) + { + forAll(neiC, fJ) + { + if( c[fI] == neiC[fJ] ) + { + sharedFace = true; + break; + } + } + + if( sharedFace ) + break; + } + + if( sharedFace ) + neighbourFaces.append(nei); + } + } + } + + template<class labelListType> + void collectGroups + ( + std::map<label, DynList<label> >& neiGroups, + const labelListType& elementInGroup, + const DynList<label>& localGroupLabel + ) const + { + const polyMeshGen& mesh = mse_.mesh(); + const faceListPMG& faces = mesh.faces(); + const cellListPMG& cells = mesh.cells(); + + const edgeList& edges = mse_.edges(); + const labelList& faceOwner = mse_.faceOwners(); + const VRWGraph& edgeFaces = mse_.edgeFaces(); + const Map<label>& otherProc = mse_.otherEdgeFaceAtProc(); + const Map<label>& globalToLocal = mse_.globalToLocalBndEdgeAddressing(); + + std::map<label, LongList<labelPair> > exchangeData; + forAll(mse_.beNeiProcs(), procI) + exchangeData[mse_.beNeiProcs()[procI]].clear(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + //- combine data if the cell attached to this face has a face + //- attached to the inter-processor boundary + //- this must hold for boundary layer cells + const cell& c = cells[faceOwner[edgeFaces(beI, 0)]]; + + bool validCell(false); + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + forAll(f, eI) + { + const edge fe = f.faceEdge(eI); + + if( fe == edges[beI] && mesh.faceIsInProcPatch(c[fI]) >= 0 ) + { + validCell = true; + break; + } + } + + if( validCell ) + break; + } + + if( !validCell ) + continue; + + const label groupI = elementInGroup[edgeFaces(beI, 0)]; + + if( groupI < 0 ) + continue; + + const label lgI = localGroupLabel[groupI]; + exchangeData[otherProc[beI]].append(labelPair(it.key(), lgI)); + } + + LongList<labelPair> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelPair& lp = receivedData[i]; + + const label beI = globalToLocal[lp.first()]; + + const cell& c = cells[faceOwner[edgeFaces(beI, 0)]]; + + //- combine data if the cell attached to this face has a face + //- attached to the inter-processor boundary + //- this must hold for boundary layer cells + bool validCell(false); + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + forAll(f, eI) + { + const edge fe = f.faceEdge(eI); + + if( fe == edges[beI] && mesh.faceIsInProcPatch(c[fI]) >= 0 ) + { + validCell = true; + break; + } + } + + if( validCell ) + break; + } + + if( !validCell ) + continue; + + const label groupI = elementInGroup[edgeFaces(beI, 0)]; + + if( groupI < 0 ) + continue; + + DynList<label>& ng = neiGroups[localGroupLabel[groupI]]; + + //- store the connection over the inter-processor boundary + ng.appendIfNotIn(lp.second()); + } + } +}; + +class meshBndLayerSelectorOperator +{ + const meshSurfaceEngine& mse_; + +public: + + meshBndLayerSelectorOperator(const meshSurfaceEngine& mse) + : + mse_(mse) + {} + + bool operator()(const label bfI) const + { + const labelList& faceOwner = mse_.faceOwners(); + const polyMeshGen& mesh = mse_.mesh(); + const faceListPMG& faces = mesh.faces(); + + const cell& c = mesh.cells()[faceOwner[bfI]]; + const PtrList<boundaryPatch>& boundaries = mesh.boundaries(); + const label start = boundaries[0].patchStart(); + + label nBndFaces(0), baseFace(-1), otherBase(-1), nQuads(0); + forAll(c, fI) + { + if( faces[c[fI]].size() == 4 ) + ++nQuads; + + if( (c[fI] - start) == bfI ) + { + baseFace = fI; + ++nBndFaces; + } + } + + if( nQuads == 6 ) + { + //- cell is a hex + return true; + } + + if( (nQuads + 2) != c.size() ) + return false; + + if( nBndFaces != 1 ) + return false; + + label nQuadsAttachedToBaseFace(0); + forAll(c, fI) + { + if( fI == baseFace ) + continue; + + const bool sEdge = + help::shareAnEdge(faces[c[baseFace]], faces[c[fI]]); + + if( (faces[c[fI]].size() == 4) && sEdge ) + { + ++nQuadsAttachedToBaseFace; + } + else if( !sEdge ) + { + if( otherBase != -1 ) + return false; + + otherBase = fI; + } + } + + if( + (nQuads == 6) || + ( + ((nQuadsAttachedToBaseFace + 2) == c.size()) && + otherBase != -1 && + !help::shareAnEdge(faces[c[baseFace]], faces[c[otherBase]]) + ) + ) + return true; + + return false; + } +}; + +} // End namespace bndLayerOps + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void refineBoundaryLayers::analyseLayers() +{ + Info << "Analysing mesh for bnd layer existence" << endl; + + const meshSurfaceEngine& mse = surfaceEngine(); + const labelList& facePatch = mse.boundaryFacePatches(); + mse.faceOwners(); + mse.faceEdges(); + mse.edgeFaces(); + mse.edges(); + mse.boundaryPointEdges(); + + //- find layers in patch + labelLongList bndFaceInLayer; + const label nGroups = + help::groupMarking + ( + bndFaceInLayer, + bndLayerOps::meshBndLayerNeighbourOperator(mse), + bndLayerOps::meshBndLayerSelectorOperator(mse) + ); + + # ifdef DEBUGLayer + Info << "Number of independent layers in the mesh is " << nGroups << endl; + # endif + + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + + //- create patch name to index addressing + std::map<word, label> patchNameToIndex; + forAll(boundaries, patchI) + patchNameToIndex[boundaries[patchI].patchName()] = patchI; + + //- check layer labels over a patch + List<DynList<label> > groupsAtPatch(boundaries.size()); + forAll(facePatch, bfI) + { + if( bndFaceInLayer[bfI] < 0 ) + continue; + + groupsAtPatch[facePatch[bfI]].appendIfNotIn(bndFaceInLayer[bfI]); + } + + //- set the information which patches have an extruded layer + labelList groupIDs(nGroups, -1); + + layerAtPatch_.setSize(boundaries.size()); + layerAtPatch_ = -1; + + label nValidLayers(0); + forAll(groupsAtPatch, patchI) + { + if( groupsAtPatch[patchI].size() == 1 ) + { + const label groupI = groupsAtPatch[patchI][0]; + + if( groupIDs[groupI] == -1 ) + groupIDs[groupI] = nValidLayers++; + + layerAtPatch_[patchI] = groupIDs[groupI]; + } + } + + # ifdef DEBUGLayer + Info << "Layer at patch " << layerAtPatch_ << endl; + # endif + + //- set the information which patches are a single boundary layer face + patchesInLayer_.setSize(nValidLayers); + forAll(layerAtPatch_, patchI) + { + if( layerAtPatch_[patchI] < 0 ) + continue; + + patchesInLayer_[layerAtPatch_[patchI]].append + ( + boundaries[patchI].patchName() + ); + } + + # ifdef DEBUGLayer + Info << "Patches in layer " << patchesInLayer_ << endl; + + //- write layers to a subset + std::map<label, label> layerId; + for(label i=0;i<nValidLayers;++i) + layerId[i] = mesh_.addFaceSubset("layerFaces_"+help::scalarToText(i)); + + forAll(layerAtPatch_, i) + { + if( layerAtPatch_[i] < 0 ) + continue; + + const label start = boundaries[i].patchStart(); + const label end = start + boundaries[i].patchSize(); + + for(label faceI=start;faceI<end;++faceI) + mesh_.addFaceToSubset(layerId[layerAtPatch_[i]], faceI); + } + mesh_.write(); + # endif + + //- set the number of boundary layers for each patch + labelList nLayersAtPatch(layerAtPatch_.size(), -1); + boolList protectedValue(layerAtPatch_.size(), false); + + forAll(patchesInLayer_, layerI) + { + const DynList<word>& layerPatches = patchesInLayer_[layerI]; + + label maxNumLayers(1); + bool hasLocalValue(false); + + //- find the maximum requested number of layers over the layer + forAll(layerPatches, lpI) + { + const word pName = layerPatches[lpI]; + + std::map<word, label>::const_iterator it = + numLayersForPatch_.find(pName); + + if( it != numLayersForPatch_.end() ) + { + //- check if the layer is interrupted at this patch + if( + discontinuousLayersForPatch_.find(pName) != + discontinuousLayersForPatch_.end() + ) + { + //- set the number of layers and lock this location + nLayersAtPatch[patchNameToIndex[pName]] = it->second; + protectedValue[patchNameToIndex[pName]] = true; + hasLocalValue = true; + } + else + { + //- take the maximum number of layers + maxNumLayers = Foam::max(maxNumLayers, it->second); + hasLocalValue = true; + } + } + } + + //- apply the global value if no local values exist + if( !hasLocalValue ) + maxNumLayers = globalNumLayers_; + + //- apply the maximum number of ayer of all unprotected patches + forAll(layerPatches, lpI) + { + const label ptchI = patchNameToIndex[layerPatches[lpI]]; + + if( !protectedValue[ptchI] ) + nLayersAtPatch[ptchI] = maxNumLayers; + } + } + + if( is2DMesh_ ) + { + polyMeshGen2DEngine mesh2DEngine(mesh_); + const boolList& zMinPoint = mesh2DEngine.zMinPoints(); + const boolList& zMaxPoint = mesh2DEngine.zMaxPoints(); + + const faceList::subList& bFaces = mse.boundaryFaces(); + + boolList allZMax(mesh_.boundaries().size(), true); + boolList allZMin(mesh_.boundaries().size(), true); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + { + if( !zMinPoint[bf[pI]] ) + allZMin[facePatch[bfI]] = false; + if( !zMaxPoint[bf[pI]] ) + allZMax[facePatch[bfI]] = false; + } + } + + //- mark empty patches as already used + forAll(allZMin, patchI) + { + if( allZMin[patchI] ^ allZMax[patchI] ) + { + nLayersAtPatch[patchI] = -1; + layerAtPatch_[patchI] = -1; + } + } + } + + # ifdef DEBUGLayer + Pout << "nLayersAtPatch " << nLayersAtPatch << endl; + # endif + + //- set the number of boundary layers which shall be generated above + //- each boundary face + nLayersAtBndFace_.setSize(facePatch.size()); + nLayersAtBndFace_ = globalNumLayers_; + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(nLayersAtBndFace_, bfI) + { + const label patchI = facePatch[bfI]; + + if( nLayersAtPatch[patchI] < 0 ) + { + nLayersAtBndFace_[bfI] = 1; + } + else + { + nLayersAtBndFace_[bfI] = nLayersAtPatch[patchI]; + } + } + + # ifdef DEBUGLayer + forAll(nLayersAtBndFace_, bfI) + Pout << "Boundary face " << bfI << " in patch " + << facePatch[bfI] << " num layers " << nLayersAtBndFace_[bfI] << endl; + //::exit(1); + # endif +} + +void refineBoundaryLayers::calculateAddressing +( + const label bfI, + label& baseFace, + DynList<edge, 48>& edges, + DynList<DynList<label, 2>, 48>& edgeFaces, + DynList<DynList<label, 10>, 24>& faceEdges +) const +{ + const label nInternalFaces = mesh_.boundaries()[0].patchStart(); + + const meshSurfaceEngine& mse = surfaceEngine(); + const labelList& faceOwner = mse.faceOwners(); + + const faceListPMG& faces = mesh_.faces(); + const cell& c = mesh_.cells()[faceOwner[bfI]]; + + faceEdges.setSize(c.size()); + baseFace = -1; + forAll(c, fI) + { + if( c[fI] - nInternalFaces == bfI ) + { + baseFace = fI; + } + + const face& f = faces[c[fI]]; + faceEdges[fI].setSize(f.size()); + + forAll(f, eI) + { + const edge e = f.faceEdge(eI); + + label pos = edges.containsAtPosition(e); + + if( pos < 0 ) + { + pos = edges.size(); + edges.append(e); + edgeFaces.setSize(pos+1); + } + + edgeFaces[pos].append(fI); + faceEdges[fI][eI] = pos; + } + } +} + +bool refineBoundaryLayers::findHairsForFace +( + const label bfI, + DynList<edge>& hairEdges +) const +{ + const label nInternalFaces = mesh_.boundaries()[0].patchStart(); + + const meshSurfaceEngine& mse = surfaceEngine(); + const labelList& faceOwner = mse.faceOwners(); + + const faceListPMG& faces = mesh_.faces(); + const cell& c = mesh_.cells()[faceOwner[bfI]]; + + //- check cell topology + DynList<edge, 48> edges; + DynList<DynList<label, 2>, 48> edgeFaces; + DynList<DynList<label, 10>, 24> faceEdges; + faceEdges.setSize(c.size()); + label baseFace(-1); + forAll(c, fI) + { + if( c[fI] - nInternalFaces == bfI ) + { + baseFace = fI; + } + + const face& f = faces[c[fI]]; + faceEdges[fI].setSize(f.size()); + + forAll(f, eI) + { + const edge e = f.faceEdge(eI); + + label pos = edges.containsAtPosition(e); + + if( pos < 0 ) + { + pos = edges.size(); + edges.append(e); + edgeFaces.setSize(pos+1); + } + + edgeFaces[pos].append(fI); + faceEdges[fI][eI] = pos; + } + } + + if( (baseFace < 0) || ((c.size() - faces[c[baseFace]].size()) != 2) ) + return false; + + //- check if all faces attached to the base face are quads + bool isPrism(true); + + const face& bf = faces[c[baseFace]]; + forAll(bf, pI) + { + const label nextEdge = faceEdges[baseFace][pI]; + const label prevEdge = faceEdges[baseFace][(pI+bf.size()-1)%bf.size()]; + + if( edgeFaces[nextEdge].size() != 2 || edgeFaces[prevEdge].size() != 2 ) + { + isPrism = false; + break; + } + + //- find the face attached to the edge after the current point + label otherNextFace = edgeFaces[nextEdge][0]; + if( otherNextFace == baseFace ) + otherNextFace = edgeFaces[nextEdge][1]; + + //- find the face attached to the edge before the current point + label otherPrevFace = edgeFaces[prevEdge][0]; + if( otherPrevFace == baseFace ) + otherPrevFace = edgeFaces[prevEdge][1]; + + label commonEdge; + for(commonEdge=0;commonEdge<edges.size();++commonEdge) + if( + edgeFaces[commonEdge].contains(otherNextFace) && + edgeFaces[commonEdge].contains(otherPrevFace) + ) + break; + + if( commonEdge == edges.size() ) + { + isPrism = false; + break; + } + + //- there exists a common edge which shall be used as a hair + if( edges[commonEdge].start() == bf[pI] ) + { + hairEdges.append(edges[commonEdge]); + } + else + { + hairEdges.append(edges[commonEdge].reverseEdge()); + } + } + + return isPrism; +} + +bool refineBoundaryLayers::findSplitEdges() +{ + bool validLayer(true); + + const meshSurfaceEngine& mse = surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& facePatch = mse.boundaryFacePatches(); + mse.faceOwners(); + const VRWGraph& pFaces = mse.pointFaces(); + const labelList& bp = mse.bp(); + + # ifdef USE_OMP + # pragma omp parallel if( bFaces.size() > 1000 ) + # endif + { + edgeLongList localEdges; + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 100) + # endif + forAll(bFaces, bfI) + { + if( layerAtPatch_[facePatch[bfI]] < 0 ) + continue; + + //- find hair edges for this face + DynList<edge> hairEdges; + if( !findHairsForFace(bfI, hairEdges) ) + { + validLayer = false; + continue; + } + + const face& bf = bFaces[bfI]; + forAll(bf, pI) + { + //- check if every the hair shall be store or not + //- only a hair edge from a face with the smallest label + //- out of all faces at a points is stored + const label bpI = bp[bf[pI]]; + + bool store(true); + forAllRow(pFaces, bpI, pfI) + { + const face& obf = bFaces[pFaces(bpI, pfI)]; + + if( + (obf.which(hairEdges[pI].end()) < 0) && + (pFaces(bpI, pfI) < bfI) + ) + { + store = false; + break; + } + } + + if( store ) + { + //- hair edge shall be stored + localEdges.append(hairEdges[pI]); + } + } + } + + # ifdef USE_OMP + //- find the starting element for this thread + label startEl; + # pragma omp critical + { + startEl = splitEdges_.size(); + + splitEdges_.setSize(startEl+localEdges.size()); + } + + //- copy the local data to splitEdges_ + forAll(localEdges, i) + splitEdges_[startEl++] = localEdges[i]; + # else + //- just transfer the data to splitEdges_ + splitEdges_.transfer(localEdges); + # endif + } + + //- create point to split edges addressing + splitEdgesAtPoint_.reverseAddressing(splitEdges_); + + reduce(validLayer, minOp<bool>()); + + # ifdef DEBUGLayer + for(label procI=0;procI<Pstream::nProcs();++procI) + { + if( procI == Pstream::myProcNo() ) + { + Pout << "Generated split edges " << splitEdges_ << endl; + } + + returnReduce(1, sumOp<label>()); + } + # endif + + return validLayer; +} + +void refineBoundaryLayers::generateNewVertices() +{ + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + pointFieldPMG& points = mesh_.points(); + + const meshSurfaceEngine& mse = surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const VRWGraph& pointFaces = mse.pointFaces(); + const labelList& facePatch = mse.boundaryFacePatches(); + const labelList& bp = mse.bp(); + + //- allocate the data from storing parameters applying to a split edge + LongList<scalar> firstLayerThickness(splitEdges_.size()); + LongList<scalar> thicknessRatio(splitEdges_.size()); + labelLongList nNodesAtEdge(splitEdges_.size()); + + //- count the number of vertices for each split edge + # ifdef USE_OMP + const label nThreads = 3 * omp_get_num_procs(); + # else + const label nThreads = 1; + # endif + + # ifdef USE_OMP + # pragma omp parallel num_threads(nThreads) + # endif + { +// # ifdef USE_OMP +// const label threadI = omp_get_thread_num(); +// # else +// const label threadI(0); +// # endif + + //- start counting vertices at each thread + # ifdef USE_OMP + # pragma omp for schedule(static, 1) + # endif + forAll(splitEdges_, seI) + { + const edge& e = splitEdges_[seI]; + + //- get the requested number of boundary layers + label nLayers(1); + scalar ratio(globalThicknessRatio_); + scalar thickness(globalMaxThicknessFirstLayer_); + bool overridenThickness(false); + + const label bpI = bp[e.start()]; + + forAllRow(pointFaces, bpI, pfI) + { + const label bfI = pointFaces(bpI, pfI); + const label pos = help::positionOfEdgeInFace(e, bFaces[bfI]); + if( pos >= 0 ) + continue; + + const word& patchName = + boundaries[facePatch[bfI]].patchName(); + + //- overrride the global value with the maximum number of layers + //- at this edge + nLayers = Foam::max(nLayers, nLayersAtBndFace_[bfI]); + + //- override with the maximum ratio + const std::map<word, scalar>::const_iterator rIt = + thicknessRatioForPatch_.find(patchName); + if( rIt != thicknessRatioForPatch_.end() ) + { + ratio = rIt->second; + } + + //- override with the minimum thickness set for this edge + const std::map<word, scalar>::const_iterator tIt = + maxThicknessForPatch_.find(patchName); + if( tIt != maxThicknessForPatch_.end() ) + { + if( overridenThickness ) + { + thickness = Foam::min(thickness, tIt->second); + } + else + { + thickness = tIt->second; + overridenThickness = true; + } + } + } + + //- store the information + firstLayerThickness[seI] = thickness; + thicknessRatio[seI] = ratio; + nNodesAtEdge[seI] = nLayers + 1; + } + } + + if( Pstream::parRun() ) + { + //- transfer the information over all processor for edges + //- at inter-processor boundaries + const labelLongList& globalEdgeLabel = + mesh_.addressingData().globalEdgeLabel(); + const VRWGraph& edgeAtProcs = mesh_.addressingData().edgeAtProcs(); + const Map<label>& globalToLocal = + mesh_.addressingData().globalToLocalEdgeAddressing(); + const DynList<label>& neiProcs = mesh_.addressingData().edgeNeiProcs(); + const edgeList& edges = mesh_.addressingData().edges(); + const VRWGraph& pointEdges = mesh_.addressingData().pointEdges(); + + //- exchange point number of layers + std::map<label, LongList<labelPair> > exchangeNumLayers; + std::map<label, LongList<labelledScalar> > exchangeThickness; + std::map<label, LongList<labelledScalar> > exchangeRatio; + forAll(neiProcs, i) + { + exchangeNumLayers.insert + ( + std::make_pair(neiProcs[i], LongList<labelPair>()) + ); + exchangeThickness.insert + ( + std::make_pair(neiProcs[i], LongList<labelledScalar>()) + ); + exchangeRatio.insert + ( + std::make_pair(neiProcs[i], LongList<labelledScalar>()) + ); + } + + //- exchange the number of layers + forAll(splitEdges_, seI) + { + const edge& se = splitEdges_[seI]; + + const label s = se.start(); + label edgeI(-1); + forAllRow(pointEdges, s, peI) + { + const label eI = pointEdges(s, peI); + + if( edges[eI] == se ) + { + edgeI = eI; + break; + } + } + + const label geI = globalEdgeLabel[edgeI]; + + if( globalToLocal.found(geI) ) + { + forAllRow(edgeAtProcs, edgeI, i) + { + const label neiProc = edgeAtProcs(edgeI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeNumLayers[neiProc].append + ( + labelPair(geI, nNodesAtEdge[seI]) + ); + exchangeThickness[neiProc].append + ( + labelledScalar(geI, firstLayerThickness[seI]) + ); + exchangeRatio[neiProc].append + ( + labelledScalar(geI, thicknessRatio[seI]) + ); + } + } + } + + //- exchange number of layers + LongList<labelPair> receivedNumLayers; + help::exchangeMap(exchangeNumLayers, receivedNumLayers); + + forAll(receivedNumLayers, i) + { + const labelPair& lp = receivedNumLayers[i]; + const label eI = globalToLocal[lp.first()]; + const edge& e = edges[eI]; + label seI(-1); + forAllRow(splitEdgesAtPoint_, e.start(), i) + { + const label seJ = splitEdgesAtPoint_(e.start(), i); + if( splitEdges_[seJ] == e ) + { + seI = seJ; + break; + } + } + nNodesAtEdge[seI] = std::max(nNodesAtEdge[seI], lp.second()); + } + + //- exchange thickness ratio + LongList<labelledScalar> receivedScalar; + help::exchangeMap(exchangeRatio, receivedScalar); + + forAll(receivedScalar, i) + { + const labelledScalar& ls = receivedScalar[i]; + const label eI = globalToLocal[ls.scalarLabel()]; + const edge& e = edges[eI]; + label seI(-1); + forAllRow(splitEdgesAtPoint_, e.start(), i) + { + const label seJ = splitEdgesAtPoint_(e.start(), i); + if( splitEdges_[seJ] == e ) + { + seI = seJ; + break; + } + } + thicknessRatio[seI] = std::max(thicknessRatio[seI], ls.value()); + } + + //- exchange maximum thickness of the first layer + receivedScalar.clear(); + help::exchangeMap(exchangeThickness, receivedScalar); + + forAll(receivedScalar, i) + { + const labelledScalar& ls = receivedScalar[i]; + const label eI = globalToLocal[ls.scalarLabel()]; + const edge& e = edges[eI]; + label seI(-1); + forAllRow(splitEdgesAtPoint_, e.start(), i) + { + const label seJ = splitEdgesAtPoint_(e.start(), i); + if( splitEdges_[seJ] == e ) + { + seI = seJ; + break; + } + } + firstLayerThickness[seI] = + std::min(firstLayerThickness[seI], ls.value()); + } + } + + //- calculate the number of additional vertices which will be generated + //- on edges of the mesh + DynList<label> numPointsAtThread; + numPointsAtThread.setSize(nThreads); + numPointsAtThread = 0; + + # ifdef USE_OMP + # pragma omp parallel for num_threads(nThreads) schedule(static, 1) + # endif + forAll(nNodesAtEdge, seI) + { + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif + + numPointsAtThread[threadI] += nNodesAtEdge[seI] - 2; + } + + //- allocate the space in a graph storing ids of points on a split edge + newVerticesForSplitEdge_.setSizeAndRowSize(nNodesAtEdge); + + //- calculate the number of points which will be generated + //- on split edges + label numPoints = points.size(); + forAll(numPointsAtThread, threadI) + { + const label nPts = numPointsAtThread[threadI]; + numPointsAtThread[threadI] = numPoints; + numPoints += nPts; + } + + points.setSize(numPoints); + + # ifdef DEBUGLayer + Info << "Generating split vertices" << endl; + # endif + + //- generate vertices on split edges + # ifdef USE_OMP + # pragma omp parallel num_threads(nThreads) + # endif + { + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif + + label& nPoints = numPointsAtThread[threadI]; + + # ifdef USE_OMP + # pragma omp for schedule(static, 1) + # endif + forAll(splitEdges_, seI) + { + const edge& e = splitEdges_[seI]; + + const vector v = e.vec(points); + const scalar magv = mag(v); + + const label nLayers = newVerticesForSplitEdge_.sizeOfRow(seI) - 1; + + scalar firstThickness = magv / nLayers; + if( thicknessRatio[seI] > (1. + SMALL) ) + { + firstThickness = + magv / + ( + (1 - Foam::pow(thicknessRatio[seI], nLayers)) / + (1.0 - thicknessRatio[seI]) + ); + + # ifdef DEBUGLayer + Pout << "Thread " << threadI << endl; + Pout << "Generating vertices at split edge " + << " start point " << points[e.start()] + << " end point " << points[e.end()] << endl; + Pout << "Edge length " << magv << endl; + Pout << "Thickness of the first layer " + << firstThickness << endl; + # endif + } + + firstThickness = + Foam::min + ( + Foam::max(firstLayerThickness[seI], SMALL), + firstThickness + ); + + //- generate vertices for this edge + newVerticesForSplitEdge_(seI, 0) = e.start(); + + scalar param = firstThickness; + const vector vec = v / (magv + VSMALL); + + for(label pI=1;pI<nLayers;++pI) + { + //- generate the new vertex + const point newP = points[e.start()] + param * vec; + + # ifdef DEBUGLayer + Pout << "Split edge " << seI << " edge points " << e + << " start point " << points[e.start()] + << " end point " << points[e.end()] + << " param " << param + << " new point " << nPoints + << " has coordinates " << newP << endl; + # endif + + param += firstThickness * Foam::pow(thicknessRatio[seI], pI); + + newVerticesForSplitEdge_(seI, pI) = nPoints; + points[nPoints++] = newP; + } + + newVerticesForSplitEdge_(seI, nLayers) = e.end(); + } + } + + # ifdef DEBUGLayer + for(label procI=0;procI<Pstream::nProcs();++procI) + { + if( procI == Pstream::myProcNo() ) + { + forAll(splitEdges_, seI) + { + Pout << "\nSplit edge " << seI << " nodes " << splitEdges_[seI] + << " coordinates " << points[splitEdges_[seI][0]] + << " " << points[splitEdges_[seI][1]] + << " has new points " + << newVerticesForSplitEdge_[seI] << endl; + + forAllRow(newVerticesForSplitEdge_, seI, i) + Pout << "Point " << i << " on edge ha coordinates " + << points[newVerticesForSplitEdge_(seI, i)] << endl; + } + } + + returnReduce(1, sumOp<label>()); + } + + Info << "Finished generating vertices at split edges" << endl; + //::exit(1); + # endif +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/checkMeshDict/checkMeshDict.C b/meshLibrary/utilities/checkMeshDict/checkMeshDict.C index d9948590c08cfc830139448fe387d15373c97f29..471a262bb31d5e2729bb113f833bf0b74846d30a 100644 --- a/meshLibrary/utilities/checkMeshDict/checkMeshDict.C +++ b/meshLibrary/utilities/checkMeshDict/checkMeshDict.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,104 +28,835 @@ Description #include "checkMeshDict.H" #include "patchRefinementList.H" #include "PtrList.H" +#include "LongList.H" #include "objectRefinement.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void checkMeshDict::checkPatchCellSize() +void checkMeshDict::checkPatchCellSize() const { if( meshDict_.found("patchCellSize") ) { - patchRefinementList prl(meshDict_.lookup("patchCellSize")); + if( meshDict_.isDict("patchCellSize") ) + { + const dictionary& dict = meshDict_.subDict("patchCellSize"); + + const wordList patchNames = dict.toc(); + patchNames.size(); + } + else + { + patchRefinementList prl(meshDict_.lookup("patchCellSize")); + prl.size(); + } + } +} + +void checkMeshDict::checkSubsetCellSize() const +{ + if( meshDict_.found("subsetCellSize") ) + { + if( meshDict_.isDict("subsetCellSize") ) + { + const dictionary& dict = meshDict_.subDict("subsetCellSize"); + + const wordList subsetNames = dict.toc(); + subsetNames.size(); + } + else + { + patchRefinementList prl(meshDict_.lookup("patchCellSize")); + } + } +} + +void checkMeshDict::checkLocalRefinementLevel() const +{ + if( meshDict_.found("localRefinement") ) + { + if( meshDict_.isDict("localRefinement") ) + { + const dictionary& refDict = meshDict_.subDict("localRefinement"); + const wordList entries = refDict.toc(); + + forAll(entries, dictI) + { + const dictionary& dict = refDict.subDict(entries[dictI]); + + if( dict.found("cellSize") ) + { + const scalar cs = readScalar(dict.lookup("cellSize")); + + if( cs > 0.0 ) + continue; + + WarningIn + ( + "void checkMeshDict::checkLocalRefinementLevel() const" + ) << "Cell size for " << entries[dictI] + << " is negative" << endl; + } + else if( dict.found("additionalRefinementLevels") ) + { + const label nLevels = + readLabel(dict.lookup("additionalRefinementLevels")); + + if( nLevels > 0 ) + continue; + + WarningIn + ( + "void checkMeshDict::checkLocalRefinementLevel() const" + ) << "Refinement level for " << entries[dictI] + << " is negative" << endl; + } + else + { + FatalErrorIn + ( + "void checkMeshDict::checkLocalRefinementLevel() const" + ) << "Cannot read keyword" + << " additionalRefinementLevels or cellSize" + << "for " << entries[dictI] << exit(FatalError); + } + } + } + else + { + FatalErrorIn + ( + "void checkMeshDict::checkLocalRefinementLevel() const" + ) << "Cannot read localRefinement" << exit(FatalError); + } } } - -void checkMeshDict::checkKeepCellsIntersectingPatches() + +void checkMeshDict::checkKeepCellsIntersectingPatches() const { if( meshDict_.found("keepCellsIntersectingPatches") ) { - wordList kcip(meshDict_.lookup("keepCellsIntersectingPatches")); + if( meshDict_.isDict("keepCellsIntersectingPatches") ) + { + const dictionary& dict = + meshDict_.subDict("keepCellsIntersectingPatches"); + + const wordList patchNames = dict.toc(); + patchNames.size(); + } + else + { + wordList kcip(meshDict_.lookup("keepCellsIntersectingPatches")); + } } } -void checkMeshDict::checkRemoveCellsIntersectingPatches() +void checkMeshDict::checkRemoveCellsIntersectingPatches() const { if( meshDict_.found("removeCellsIntersectingPatches") ) { - wordList kcip(meshDict_.lookup("removeCellsIntersectingPatches")); + if( meshDict_.isDict("removeCellsIntersectingPatches") ) + { + const dictionary& dict = + meshDict_.subDict("removeCellsIntersectingPatches"); + + const wordList patchNames = dict.toc(); + patchNames.size(); + } + else + { + wordList kcip(meshDict_.lookup("removeCellsIntersectingPatches")); + } } } - -void checkMeshDict::checkObjectRefinements() + +void checkMeshDict::checkObjectRefinements() const { if( meshDict_.found("objectRefinements") ) { PtrList<objectRefinement> refObjects; - Istream& is = meshDict_.lookup("objectRefinements"); - PtrList<entry> objectEntries(is); - refObjects.setSize(objectEntries.size()); - - forAll(refObjects, objectI) + if( meshDict_.isDict("objectRefinements") ) { - refObjects.set - ( - objectI, - objectRefinement::New + const dictionary& dict = meshDict_.subDict("objectRefinements"); + const wordList objectNames = dict.toc(); + + refObjects.setSize(objectNames.size()); + + forAll(refObjects, objectI) + { + const entry& objectEntry = + dict.lookupEntry(objectNames[objectI], false, false); + + refObjects.set ( - objectEntries[objectI].keyword(), - objectEntries[objectI].dict() - ) - ); + objectI, + objectRefinement::New + ( + objectEntry.keyword(), + objectEntry.dict() + ) + ); + } + } + else + { + Istream& is = meshDict_.lookup("objectRefinements"); + + PtrList<entry> objectEntries(is); + refObjects.setSize(objectEntries.size()); + + forAll(refObjects, objectI) + { + refObjects.set + ( + objectI, + objectRefinement::New + ( + objectEntries[objectI].keyword(), + objectEntries[objectI].dict() + ) + ); + } } } } -void checkMeshDict::checkBoundaryLayers() +void checkMeshDict::checkBoundaryLayers() const { if( meshDict_.found("boundaryLayers") ) { - wordList bl(meshDict_.lookup("boundaryLayers")); + const dictionary& bndLayers = meshDict_.subDict("boundaryLayers"); + + //- read global properties + if( bndLayers.found("nLayers") ) + { + readLabel(bndLayers.lookup("nLayers")); + } + if( bndLayers.found("thicknessRatio") ) + { + readScalar(bndLayers.lookup("thicknessRatio")); + } + if( bndLayers.found("maxFirstLayerThickness") ) + { + readScalar(bndLayers.lookup("maxFirstLayerThickness")); + } + + //- patch-based properties + if( bndLayers.isDict("patchBoundaryLayers") ) + { + const dictionary& patchBndLayers = + bndLayers.subDict("patchBoundaryLayers"); + const wordList patchNames = patchBndLayers.toc(); + + forAll(patchNames, patchI) + { + const word pName = patchNames[patchI]; + + if( patchBndLayers.isDict(pName) ) + { + const dictionary& patchDict = + patchBndLayers.subDict(pName); + + if( patchDict.found("nLayers") ) + { + readLabel(patchDict.lookup("nLayers")); + } + if( patchDict.found("thicknessRatio") ) + { + readScalar(patchDict.lookup("thicknessRatio")); + } + if( patchDict.found("maxFirstLayerThickness") ) + { + readScalar(patchDict.lookup("maxFirstLayerThickness")); + } + if( patchDict.found("allowDiscontinuity") ) + { + readBool(patchDict.lookup("allowDiscontinuity")); + } + } + else + { + Warning << "Cannot refine layer for patch " + << patchNames[patchI] << endl; + } + } + } } } -void checkMeshDict::checkRenameBoundary() +void checkMeshDict::checkRenameBoundary() const { if( meshDict_.found("renameBoundary") ) { const dictionary& dict = meshDict_.subDict("renameBoundary"); if( dict.found("newPatchNames") ) { - PtrList<entry> patchesToRename(dict.lookup("newPatchNames")); + if( dict.isDict("newPatchNames") ) + { + const dictionary& patchDicts = dict.subDict("newPatchNames"); + + const wordList patchNames = patchDicts.toc(); + + forAll(patchNames, patchI) + { + const word& pName = patchNames[patchI]; + + if( !patchDicts.isDict(pName) ) + FatalErrorIn + ( + "void checkMeshDict::checkRenameBoundary() const" + ) << "Entry " << pName + << " is not a dictionary" << exit(FatalError); + + const dictionary dict = patchDicts.subDict(pName); + + if( !dict.found("newName") ) + FatalErrorIn + ( + "void checkMeshDict::checkRenameBoundary() const" + ) << "Dictionary " << pName + << " does not contain a newName keyword" + << exit(FatalError); + } + } + else + { + const PtrList<entry> patchesToRename + ( + dict.lookup("newPatchNames") + ); + + forAll(patchesToRename, patchI) + { + const word& pName = patchesToRename[patchI].keyword(); + + const dictionary dict = patchesToRename[patchI].dict(); + + if( !dict.found("newName") ) + FatalErrorIn + ( + "void checkMeshDict::checkRenameBoundary() const" + ) << "Dictionary " << pName + << " does not contain a newName keyword" + << exit(FatalError); + } + } } } } -void checkMeshDict::checkEntries() +void checkMeshDict::checkEntries() const { checkPatchCellSize(); - + + checkSubsetCellSize(); + checkKeepCellsIntersectingPatches(); - + checkRemoveCellsIntersectingPatches(); - + checkObjectRefinements(); - + checkBoundaryLayers(); - + checkRenameBoundary(); } +void checkMeshDict::updatePatchCellSize +( + const std::map<word, wordList>& patchesFromPatch +) +{ + if( meshDict_.found("patchCellSize") ) + { + LongList<patchRefinement> updatedPatchRefinement; + + if( meshDict_.isDict("patchCellSize") ) + { + const dictionary dict = meshDict_.subDict("patchCellSize"); + + const wordList patchNames = dict.toc(); + + forAll(patchNames, patchI) + { + const word& pName = patchNames[patchI]; + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + if( it == patchesFromPatch.end() ) + continue; + + const wordList& updatedPatchNames = it->second; + + const dictionary& pDict = dict.subDict(pName); + const scalar cellSize = readScalar(pDict.lookup("cellSize")); + + forAll(updatedPatchNames, nameI) + updatedPatchRefinement.append + ( + patchRefinement + ( + updatedPatchNames[nameI], + cellSize + ) + ); + } + } + else + { + patchRefinementList prl(meshDict_.lookup("patchCellSize")); + forAll(prl, prlI) + { + const word& pName = prl[prlI].patchName(); + const scalar cellSize = prl[prlI].cellSize(); + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + + if( it == patchesFromPatch.end() ) + continue; + + const wordList& updatedPatchNames = it->second; + forAll(updatedPatchNames, nameI) + updatedPatchRefinement.append + ( + patchRefinement + ( + updatedPatchNames[nameI], + cellSize + ) + ); + } + } + + meshDict_.add("patchCellSize", updatedPatchRefinement, true); + } +} + +void checkMeshDict::updateSubsetCellSize +( + const std::map<word, wordList>& patchesFromPatch +) +{ + +} + +void checkMeshDict::updateLocalRefinementLevel +( + const std::map<word, wordList>& patchesFromPatch +) +{ + if( meshDict_.found("localRefinement") ) + { + if( meshDict_.isDict("localRefinement") ) + { + dictionary& dict = meshDict_.subDict("localRefinement"); + + const wordList entries = dict.toc(); + + forAll(entries, dictI) + { + const word& pName = entries[dictI]; + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + if( it == patchesFromPatch.end() ) + continue; + + const wordList& updatedPatchNames = it->second; + + const dictionary& pDict = dict.subDict(pName); + dictionary copy; + if( pDict.found("additionalRefinementLevels") ) + { + const label nLevels = + readLabel(pDict.lookup("additionalRefinementLevels")); + + copy.add("additionalRefinementLevels", nLevels); + } + else if( pDict.found("cellSize") ) + { + const scalar cs = readScalar(pDict.lookup("cellSize")); + + copy.add("cellSize", cs); + } + + //- add new patches + forAll(updatedPatchNames, nameI) + dict.add(updatedPatchNames[nameI], copy); + + //- remove the current patch + dict.remove(pName); + } + } + } +} + +void checkMeshDict::updateKeepCellsIntersectingPatches +( + const std::map<word, wordList>& patchesFromPatch +) +{ + if( meshDict_.found("keepCellsIntersectingPatches") ) + { + LongList<word> updatedPatchNames; + if( meshDict_.isDict("keepCellsIntersectingPatches") ) + { + const dictionary& dict = + meshDict_.subDict("keepCellsIntersectingPatches"); + + const wordList patchNames = dict.toc(); + forAll(patchNames, patchI) + { + const word& pName = patchNames[patchI]; + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + + if( it == patchesFromPatch.end() ) + updatedPatchNames.append(pName); + + const wordList& newPatchNames = it->second; + + forAll(newPatchNames, nameI) + updatedPatchNames.append(newPatchNames[nameI]); + } + } + else + { + wordList kcip(meshDict_.lookup("keepCellsIntersectingPatches")); + + forAll(kcip, i) + { + const word& pName = kcip[i]; + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + + if( it == patchesFromPatch.end() ) + updatedPatchNames.append(pName); + + const wordList& newPatchNames = it->second; + + forAll(newPatchNames, nameI) + updatedPatchNames.append(newPatchNames[nameI]); + } + } + + meshDict_.add("keepCellsIntersectingPatches", updatedPatchNames, true); + } +} + + +void checkMeshDict::updateRemoveCellsIntersectingPatches +( + const std::map<word, wordList>& patchesFromPatch +) +{ + if( meshDict_.found("removeCellsIntersectingPatches") ) + { + LongList<word> updatedPatchNames; + if( meshDict_.isDict("removeCellsIntersectingPatches") ) + { + const dictionary& dict = + meshDict_.subDict("removeCellsIntersectingPatches"); + + const wordList patchNames = dict.toc(); + forAll(patchNames, patchI) + { + const word& pName = patchNames[patchI]; + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + + if( it == patchesFromPatch.end() ) + updatedPatchNames.append(pName); + + const wordList& newPatchNames = it->second; + + forAll(newPatchNames, nameI) + updatedPatchNames.append(newPatchNames[nameI]); + } + } + else + { + wordList kcip(meshDict_.lookup("removeCellsIntersectingPatches")); + + forAll(kcip, i) + { + const word& pName = kcip[i]; + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + + if( it == patchesFromPatch.end() ) + updatedPatchNames.append(pName); + + const wordList& newPatchNames = it->second; + + forAll(newPatchNames, nameI) + updatedPatchNames.append(newPatchNames[nameI]); + } + } + + meshDict_.add + ( + "removeCellsIntersectingPatches", + updatedPatchNames, + true + ); + } +} + +void checkMeshDict::updateObjectRefinements +( + const std::map<word, wordList>& patchesFromPatch +) +{ + +} + +void checkMeshDict::updateBoundaryLayers +( + const std::map<word, wordList>& patchesFromPatch +) +{ + if( meshDict_.isDict("boundaryLayers") ) + { + dictionary& bndLayersDict = meshDict_.subDict("boundaryLayers"); + if( bndLayersDict.isDict("patchBoundaryLayers") ) + { + dictionary& patchBndLayers = + bndLayersDict.subDict("patchBoundaryLayers"); + + const wordList patchLayers = patchBndLayers.toc(); + + forAll(patchLayers, patchI) + { + const word& pName = patchLayers[patchI]; + + dictionary dict = patchBndLayers.subDict(pName); + + const std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + const wordList& newNames = it->second; + + forAll(newNames, i) + { + patchBndLayers.add(newNames[i], dict); + } + + patchBndLayers.remove(pName); + } + } + } +} + +void checkMeshDict::updateRenameBoundary +( + const std::map<word, wordList>& patchesFromPatch, + const std::map<word, word>& patchTypes +) +{ + dictionary newDict; + + newDict.add("newPatchNames", dictionary()); + + if( meshDict_.found("renameBoundary") ) + { + const dictionary& dict = meshDict_.subDict("renameBoundary"); + + //- transfer or generate the default name entry + if( dict.found("defaultName") ) + { + const word name(dict.lookup("defaultName")); + newDict.add("defaultName", name); + } + else + { + newDict.add("defaultName", "walls"); + } + + //- transfer or generate the defaultType entry + if( dict.found("defaultType") ) + { + const word type(dict.lookup("defaultType")); + newDict.add("defaultType", type); + } + else + { + newDict.add("defaultType", "wall"); + } + + if( dict.found("newPatchNames") ) + { + //- stores the updated dictionary + dictionary& newPatchesDict = newDict.subDict("newPatchNames"); + + if( dict.isDict("newPatchNames") ) + { + //- current state of the dictionary + const dictionary& patchDicts = dict.subDict("newPatchNames"); + + std::map<word, wordList>::const_iterator it; + for(it=patchesFromPatch.begin();it!=patchesFromPatch.end();++it) + { + const word& pName = it->first; + const wordList& newNames = it->second; + + if( patchDicts.found(pName) ) + { + //- patch renaming is already requested by the user + //- use the new name for all newly created patches + const dictionary& patchDict = patchDicts.subDict(pName); + if( !patchDict.found("newName") ) + continue; + if( !patchDict.found("type") ) + continue; + + const word newName(patchDict.lookup("newName")); + const word newType(patchDict.lookup("type")); + + forAll(newNames, i) + { + dictionary newPatchDict; + newPatchDict.add("newName", newName); + newPatchDict.add("type", newType); + + newPatchesDict.add(newNames[i], newPatchDict); + } + } + else + { + //- rename all newly create patches + //- with the original name + forAll(newNames, i) + { + dictionary newPatchDict; + + newPatchDict.add("newName", it->first); + std::map<word, word>::const_iterator tIter = + patchTypes.find(it->first); + newPatchDict.add("type", tIter->second); + + newPatchesDict.add(newNames[i], newPatchDict); + } + } + } + } + else + { + const PtrList<entry> patchEntries(dict.lookup("newPatchNames")); + + forAll(patchEntries, entryI) + { + const word& pName = patchEntries[entryI].keyword(); + dictionary patchDict(patchEntries[entryI].dict()); + + std::map<word, wordList>::const_iterator it = + patchesFromPatch.find(pName); + + if( it == patchesFromPatch.end() ) + continue; + + const wordList& newNames = it->second; + + forAll(newNames, i) + newPatchesDict.add(newNames[i], patchDict, true); + } + + std::map<word, wordList>::const_iterator it; + for(it=patchesFromPatch.begin();it!=patchesFromPatch.end();++it) + { + const word& pName = it->first; + const wordList& newNames = it->second; + + if( newPatchesDict.found(pName) ) + continue; + + //- rename all newly created patches + //- with the original name + forAll(newNames, i) + { + dictionary newPatchDict; + + newPatchDict.add("newName", it->first); + std::map<word, word>::const_iterator tIter = + patchTypes.find(it->first); + newPatchDict.add("type", tIter->second); + + newPatchesDict.add(newNames[i], newPatchDict); + } + } + } + } + else + { + //- newPatchNames is not used + dictionary& newPatchesDict = newDict.subDict("newPatchNames"); + + std::map<word, wordList>::const_iterator it; + for(it=patchesFromPatch.begin();it!=patchesFromPatch.end();++it) + { + const wordList& newPatchNames = it->second; + + forAll(newPatchNames, i) + { + const word& pName = newPatchNames[i]; + dictionary newPatchDict; + newPatchDict.add("newName", it->first); + std::map<word, word>::const_iterator tIter = + patchTypes.find(it->first); + newPatchDict.add("type", tIter->second); + + newPatchesDict.add(pName, newPatchDict); + } + } + } + + //- delete all previus entries from the dictionary + meshDict_.subDict("renameBoundary").clear(); + } + else + { + //- create the dictionary if it has not existed before + newDict.add("defaultName", "walls"); + newDict.add("defaultType", "wall"); + + dictionary& newPatchesDict = newDict.subDict("newPatchNames"); + + std::map<word, wordList>::const_iterator it; + for(it=patchesFromPatch.begin();it!=patchesFromPatch.end();++it) + { + const wordList& newPatchNames = it->second; + + forAll(newPatchNames, i) + { + const word& pName = newPatchNames[i]; + dictionary newPatchDict; + newPatchDict.add("newName", it->first); + std::map<word, word>::const_iterator tIter = + patchTypes.find(it->first); + newPatchDict.add("type", tIter->second); + + newPatchesDict.add(pName, newPatchDict); + } + } + } + + meshDict_.add("renameBoundary", newDict, true); +} + // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // checkMeshDict::checkMeshDict ( - const IOdictionary& meshDict + IOdictionary& meshDict ) : meshDict_(meshDict) @@ -137,7 +867,33 @@ checkMeshDict::checkMeshDict // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // checkMeshDict::~checkMeshDict() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void checkMeshDict::updateDictionaries +( + const std::map<word, wordList>& patchesFromPatch, + const std::map<word, word>& patchTypes, + const bool renamePatches +) { + updatePatchCellSize(patchesFromPatch); + + updateSubsetCellSize(patchesFromPatch); + + updateLocalRefinementLevel(patchesFromPatch); + + updateKeepCellsIntersectingPatches(patchesFromPatch); + + updateRemoveCellsIntersectingPatches(patchesFromPatch); + + updateObjectRefinements(patchesFromPatch); + + updateBoundaryLayers(patchesFromPatch); + + if( renamePatches ) + updateRenameBoundary(patchesFromPatch, patchTypes); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/checkMeshDict/checkMeshDict.H b/meshLibrary/utilities/checkMeshDict/checkMeshDict.H index da6a22950da92861a82826b57b3e4ff5a3ac459d..c97d2addb6bc4c5bfd06f9ec27a5c6f7c662a50a 100644 --- a/meshLibrary/utilities/checkMeshDict/checkMeshDict.H +++ b/meshLibrary/utilities/checkMeshDict/checkMeshDict.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class checkMeshDict @@ -38,53 +37,103 @@ SourceFiles #include "IOdictionary.H" +#include <map> + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { /*---------------------------------------------------------------------------*\ - Class checkMeshDict Declaration + Class checkMeshDict Declaration \*---------------------------------------------------------------------------*/ class checkMeshDict { - //- Reference to the mesh - const IOdictionary& meshDict_; - - // Private member functions + //- Reference to the mesh + IOdictionary& meshDict_; + + // Private member functions //- check patchCellSize entry - void checkPatchCellSize(); - + void checkPatchCellSize() const; + + //- check subsetCellSize entry + void checkSubsetCellSize() const; + + //- check local refinement level + void checkLocalRefinementLevel() const; + //- check keepCellsIntersectingPatches entry - void checkKeepCellsIntersectingPatches(); - + void checkKeepCellsIntersectingPatches() const; + //- check removeCellsIntersectingPatches entry - void checkRemoveCellsIntersectingPatches(); - + void checkRemoveCellsIntersectingPatches() const; + //- check objectRefinements entry - void checkObjectRefinements(); - + void checkObjectRefinements() const; + //- check entry for boundary layers - void checkBoundaryLayers(); - + void checkBoundaryLayers() const; + //- check renameBoundary entry - void checkRenameBoundary(); - + void checkRenameBoundary() const; + //- perform all checks - void checkEntries(); - - public: - - // Constructors - - //- Construct from IOdictionary - checkMeshDict(const IOdictionary& meshDict); - - // Destructor - ~checkMeshDict(); - - // Public member functions + void checkEntries() const; + + //- update patchCellSize entry + void updatePatchCellSize(const std::map<word, wordList>&); + + //- update subsetCellSize entry + void updateSubsetCellSize(const std::map<word, wordList>&); + + //- update local refinement + void updateLocalRefinementLevel(const std::map<word, wordList>&); + + //- check keepCellsIntersectingPatches entry + void updateKeepCellsIntersectingPatches + ( + const std::map<word, wordList>& + ); + + //- check removeCellsIntersectingPatches entry + void updateRemoveCellsIntersectingPatches + ( + const std::map<word, wordList>& + ); + + //- check objectRefinements entry + void updateObjectRefinements(const std::map<word, wordList>&); + + //- check entry for boundary layers + void updateBoundaryLayers(const std::map<word, wordList>&); + + //- check renameBoundary entry + void updateRenameBoundary + ( + const std::map<word, wordList>&, + const std::map<word, word>& + ); + + public: + + // Constructors + + //- Construct from IOdictionary + checkMeshDict(IOdictionary& meshDict); + + // Destructor + ~checkMeshDict(); + + // Public member functions + + //- update meshDict based on modification of patches in the surface + void updateDictionaries + ( + const std::map<word, wordList>& patchesForPatch, + const std::map<word, word>& patchTypes, + const bool renamePatches = true + ); }; diff --git a/meshLibrary/utilities/containers/DynList/DynList.C b/meshLibrary/utilities/containers/DynList/DynList.C index 2140b7700474ad5146ff82ca0fbc1ca5d94ae2da..2bf3a2a47721d4c00e563d9bae97a2954668165e 100644 --- a/meshLibrary/utilities/containers/DynList/DynList.C +++ b/meshLibrary/utilities/containers/DynList/DynList.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ diff --git a/meshLibrary/utilities/containers/DynList/DynList.H b/meshLibrary/utilities/containers/DynList/DynList.H index 4adf574d0425452ba8cdb62f4c3d19a6d78da53b..1b550836b83f1ef36956c1eb601cb9732fbad098 100644 --- a/meshLibrary/utilities/containers/DynList/DynList.H +++ b/meshLibrary/utilities/containers/DynList/DynList.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class DynList @@ -87,7 +86,7 @@ class DynList // Private member functions //- allocate list size inline void allocateSize(const label); - + //- check if index is inside the scope (used for debugging only) inline void checkIndex(const label) const; @@ -101,9 +100,16 @@ public: //- Construct given size explicit inline DynList(const label); + //- Construct from given size and defualt value + explicit inline DynList(const label, const T&); + //- Construct from UList. nextFree_ set to size(). explicit inline DynList(const UList<T>&); + //- Construct from other ListType + template<class ListType> + inline DynList(const ListType&); + //- Copy constructor inline DynList(const DynList<T, staticSize>&); @@ -122,7 +128,7 @@ public: //- Size of the active part of the list. //- Direct over-ride of list size member function inline label size() const; - + //- Number of bytes used by the active part of the list //- Direct over-ride of list byteSize member function inline label byteSize() const; @@ -145,36 +151,56 @@ public: //- Append an element at the end of the list inline void append(const T& e); - - //- Append an element at the end of the list if it is not yet - //- present in the list (takes linear time) - inline void appendIfNotIn(const T& e); - - //- check if the element is in the list (takes linear time) - inline bool contains(const T& e) const; - inline label containsAtPosition(const T& e) const; - - //- Return and remove the top element + + //- Append an element at the end of the list if it is not yet + //- present in the list (takes linear time) + inline void appendIfNotIn(const T& e); + + //- check if the element is in the list (takes linear time) + inline bool contains(const T& e) const; + inline label containsAtPosition(const T& e) const; + + //- return a const reference to the last element + inline const T& lastElement() const; + + //- Return and remove the last element inline T removeLastElement(); - inline T removeElement(const label i); - - //- return a refence to the element. Resize the list if necessary - inline T& newElmt(const label); + inline T removeElement(const label i); + + //- return a refence to the element. Resize the list if necessary + inline T& newElmt(const label); //- Return non-const access to an element, //- resizing the list if necessary inline T& operator()(const label); - + //- return access to an element inline const T& operator[](const label) const; inline T& operator[](const label); + //- return forward and reverse circular indices + inline label fcIndex(const label index, const label offset = 1) const; + inline label rcIndex(const label index, const label offset = 1) const; + + //- return forward and reverse circular elements + inline const T& fcElement + ( + const label index, + const label offset = 1 + ) const; + + inline const T& rcElement + ( + const label index, + const label offset = 1 + ) const; + //- Assignment of all entries to the given value inline void operator=(const T&); - + //- Copy of another list inline void operator=(const DynList<T, staticSize>&); - + //- Copy of another list type template<class ListType> inline void operator=(const ListType&); diff --git a/meshLibrary/utilities/containers/DynList/DynListI.H b/meshLibrary/utilities/containers/DynList/DynListI.H index 79f70250af3a15543c7b950b32f91aa35b3b18b4..5e1e2ae9f2fa35ed5e577b97a12d225ae897448d 100644 --- a/meshLibrary/utilities/containers/DynList/DynListI.H +++ b/meshLibrary/utilities/containers/DynList/DynListI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -31,41 +30,41 @@ inline void Foam::DynList<T, staticSize>::allocateSize(const label s) if( s > UList<T>::size() ) { T* newData = new T[s]; - - forAll(*this, i) + + for(label i=0;i<nextFree_;++i) newData[i] = this->operator[](i); - + T* data = UList<T>::begin(); if( data && (data != staticData_) ) delete [] data; - - UList<T>::reset(newData, s); - //this->UList<T>::operator=(UList<T>(newData, s)); + + //UList<T>::reset(newData, s); + this->UList<T>::operator=(UList<T>(newData, s)); } else if( (s > staticSize) && (s < UList<T>::size()) ) { T* newData = new T[s]; - + for(label i=0;i<s;++i) newData[i] = this->operator[](i); - + T* data = UList<T>::begin(); delete [] data; - - UList<T>::reset(newData, s); - //this->UList<T>::operator=(UList<T>(newData, s)); + + //UList<T>::reset(newData, s); + this->UList<T>::operator=(UList<T>(newData, s)); } else if( (s <= staticSize) && (UList<T>::size() > staticSize) ) { for(label i=0;i<s;++i) staticData_[i] = UList<T>::operator[](i); - + T* data = UList<T>::begin(); if( data && (data != staticData_) ) delete [] data; - - UList<T>::reset(staticData_, staticSize); - //this->UList<T>::operator=(UList<T>(staticData_, staticSize)); + + //UList<T>::reset(staticData_, staticSize); + this->UList<T>::operator=(UList<T>(staticData_, staticSize)); } } @@ -75,12 +74,12 @@ inline void Foam::DynList<T, staticSize>::checkIndex(const label i) const if( (i < 0) || (i >= nextFree_) ) { FatalErrorIn - ( - "void Foam::DynList<T, label, Offset>::" - "checkIndex(const label i) const" - ) << "Index " << i << " is not in range " << 0 - << " and " << nextFree_ << abort(FatalError); - } + ( + "void Foam::DynList<T, label, Offset>::" + "checkIndex(const label i) const" + ) << "Index " << i << " is not in range " << 0 + << " and " << nextFree_ << abort(FatalError); + } } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -94,30 +93,51 @@ inline Foam::DynList<T, staticSize>::DynList() {} -//- Construct given size template<class T, Foam::label staticSize> inline Foam::DynList<T, staticSize>::DynList(const label s) : UList<T>(staticData_, staticSize), nextFree_(0) { - allocateSize(s); + setSize(s); } +template<class T, Foam::label staticSize> +inline Foam::DynList<T, staticSize>::DynList(const label s, const T& val) +: + UList<T>(staticData_, staticSize), + nextFree_(0) +{ + setSize(s); + + for(label i=0;i<s;++i) + this->operator[](i) = val; +} -//- Construct given size template<class T, Foam::label staticSize> inline Foam::DynList<T, staticSize>::DynList(const UList<T>& ul) : UList<T>(staticData_, staticSize), - nextFree_(ul.size()) + nextFree_(0) { - allocateSize(ul.size()); - + setSize(ul.size()); + forAll(ul, i) this->operator[](i) = ul[i]; } +template<class T, Foam::label staticSize> +template<class ListType> +inline Foam::DynList<T, staticSize>::DynList(const ListType& l) +: + UList<T>(staticData_, staticSize), + nextFree_(0) +{ + setSize(l.size()); + for(label i=0;i<nextFree_;++i) + this->operator[](i) = l[i]; +} + //- Copy construct template<class T, Foam::label staticSize> inline Foam::DynList<T, staticSize>::DynList @@ -126,9 +146,9 @@ inline Foam::DynList<T, staticSize>::DynList ) : UList<T>(staticData_, staticSize), - nextFree_(dl.size()) + nextFree_(0) { - allocateSize(nextFree_); + setSize(dl.size()); for(label i=0;i<nextFree_;++i) this->operator[](i) = dl[i]; } @@ -193,39 +213,48 @@ inline void Foam::DynList<T, staticSize>::append(const T& e) const label newSize = 2*UList<T>::size()+2; allocateSize(newSize); } - + UList<T>::operator[](nextFree_++) = e; } template<class T, Foam::label staticSize> inline void Foam::DynList<T, staticSize>::appendIfNotIn(const T& e) { - if( !contains(e) ) - append(e); + if( !contains(e) ) + append(e); } template<class T, Foam::label staticSize> inline bool Foam::DynList<T, staticSize>::contains(const T& e) const { - for(label i=0;i<nextFree_;++i) + for(label i=0;i<nextFree_;++i) { - if( UList<T>::operator[](i) == e ) - return true; + if( UList<T>::operator[](i) == e ) + return true; } - - return false; + + return false; } template<class T, Foam::label staticSize> -inline Foam::label Foam::DynList<T, staticSize>::containsAtPosition(const T& e) const +inline Foam::label Foam::DynList<T, staticSize>::containsAtPosition +( + const T& e +) const { - for(label i=0;i<nextFree_;++i) + for(label i=0;i<nextFree_;++i) { - if( UList<T>::operator[](i) == e ) - return i; + if( UList<T>::operator[](i) == e ) + return i; } - - return -1; + + return -1; +} + +template<class T, Foam::label staticSize> +inline const T& Foam::DynList<T, staticSize>::lastElement() const +{ + return this->operator[](nextFree_-1); } template<class T, Foam::label staticSize> @@ -246,25 +275,25 @@ inline T Foam::DynList<T, staticSize>::removeLastElement() template<class T, Foam::label staticSize> inline T Foam::DynList<T, staticSize>::removeElement(const label i) { - if( nextFree_ == 0 ) + if( nextFree_ == 0 ) { FatalErrorIn ( "void Foam::DynList<T, staticSize>::remove()" ) << "List is empty" << abort(FatalError); } - + T el = this->operator[](i); - this->operator[](i) = this->operator[](nextFree_-1); + this->operator[](i) = this->operator[](nextFree_-1); --nextFree_; - + return el; } template<class T, Foam::label staticSize> inline T& Foam::DynList<T, staticSize>::newElmt(const label i) { - return this->operator()(i); + return this->operator()(i); } // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * // @@ -288,7 +317,7 @@ inline const T& Foam::DynList<T, staticSize>::operator[](const label i) const # ifdef FULLDEBUG checkIndex(i); # endif - + return UList<T>::operator[](i); } @@ -298,10 +327,49 @@ inline T& Foam::DynList<T, staticSize>::operator[](const label i) # ifdef FULLDEBUG checkIndex(i); # endif - + return UList<T>::operator[](i); } +template<class T, Foam::label staticSize> +inline Foam::label Foam::DynList<T, staticSize>::fcIndex +( + const label index, + const label offset +) const +{ + return (index + offset) % nextFree_; +} + +template<class T, Foam::label staticSize> +inline Foam::label Foam::DynList<T, staticSize>::rcIndex +( + const label index, + const label offset +) const +{ + return (index + nextFree_ - offset) % nextFree_; +} + +template<class T, Foam::label staticSize> +inline const T& Foam::DynList<T, staticSize>::fcElement +( + const label index, + const label offset +) const +{ + return operator[](fcIndex(index, offset)); +} + +template<class T, Foam::label staticSize> +inline const T& Foam::DynList<T, staticSize>::rcElement +( + const label index, + const label offset +) const +{ + return operator[](rcIndex(index, offset)); +} template<class T, Foam::label staticSize> inline void Foam::DynList<T, staticSize>::operator=(const T& t) diff --git a/meshLibrary/utilities/containers/FRWGraph/FRWGraph.C b/meshLibrary/utilities/containers/FRWGraph/FRWGraph.C index 55e6496ab0109c4e49ea3253e363fc4f3fcda93d..190d1f4c4b0e0793673e6901c6c3c3a810f02521 100644 --- a/meshLibrary/utilities/containers/FRWGraph/FRWGraph.C +++ b/meshLibrary/utilities/containers/FRWGraph/FRWGraph.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -35,15 +34,15 @@ Foam::Ostream& Foam::operator<< const Foam::FRWGraph<T, width>& DL ) { - os << DL.size() << "(" << endl; - for(register label i=0;i<DL.size();++i) - { - os << width << "("; - for(label j=0;j<width;++j) - os << DL(i, j) << " " << endl; - os << ")" << endl; - } - os << ")"; + os << DL.size() << "(" << endl; + for(register label i=0;i<DL.size();++i) + { + os << width << "("; + for(label j=0;j<width;++j) + os << DL(i, j) << " " << endl; + os << ")" << endl; + } + os << ")"; return os; } @@ -55,15 +54,15 @@ Foam::Istream& Foam::operator>> Foam::FRWGraph<T, width>& DL ) { - label size; - T e; - is >> size; - DL.setSize(size); - for(IndexType i=0;i<size;++i) - { - is >> e; - DL[i] = e; - } + label size; + T e; + is >> size; + DL.setSize(size); + for(IndexType i=0;i<size;++i) + { + is >> e; + DL[i] = e; + } return is; } diff --git a/meshLibrary/utilities/containers/FRWGraph/FRWGraph.H b/meshLibrary/utilities/containers/FRWGraph/FRWGraph.H index 5c95f0d8fc6f7b9d6ee56259fc27b7e9463fdacb..012a3b71f511e70e79815cecf14603bee180d033 100644 --- a/meshLibrary/utilities/containers/FRWGraph/FRWGraph.H +++ b/meshLibrary/utilities/containers/FRWGraph/FRWGraph.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class FRWGraph Description This class is an implementation of a graph with the fixed row width. - The implementation is memory efficient. + The implementation is memory efficient. SourceFiles FRWGraphI.H diff --git a/meshLibrary/utilities/containers/FRWGraph/FRWGraphI.H b/meshLibrary/utilities/containers/FRWGraph/FRWGraphI.H index 6998098c4c9f1a33339d028f89a929cc75379ca5..36bf6cf82e415b5e1374fd3d9e43c40e0186e1e4 100644 --- a/meshLibrary/utilities/containers/FRWGraph/FRWGraphI.H +++ b/meshLibrary/utilities/containers/FRWGraph/FRWGraphI.H @@ -1,51 +1,50 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ template<class T, Foam::label width> void Foam::FRWGraph<T, width>::checkIndex(const label i, const label j) const { - if( (i < 0) || (i >= nRows_) ) - { - FatalErrorIn - ( - "void Foam::FRWGraph<T,width>::" - "checkIndex(const label i, const label j) const" - ) << "Row index " << Foam::label(i) - << " is not in range " << Foam::label(0) - << " and " << nRows_ << abort(FatalError); - } - - if( (j < 0) || (j >= width) ) - FatalErrorIn - ( - "void Foam::FRWGraph<T,width>::" - "checkIndex(label const i) const" - ) << "Column index " << Foam::label(j) - << " is not in range " << Foam::label(0) - << " and " << width << abort(FatalError); + if( (i < 0) || (i >= nRows_) ) + { + FatalErrorIn + ( + "void Foam::FRWGraph<T,width>::" + "checkIndex(const label i, const label j) const" + ) << "Row index " << Foam::label(i) + << " is not in range " << Foam::label(0) + << " and " << nRows_ << abort(FatalError); + } + + if( (j < 0) || (j >= width) ) + FatalErrorIn + ( + "void Foam::FRWGraph<T,width>::" + "checkIndex(label const i) const" + ) << "Column index " << Foam::label(j) + << " is not in range " << Foam::label(0) + << " and " << width << abort(FatalError); } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -54,8 +53,8 @@ void Foam::FRWGraph<T, width>::checkIndex(const label i, const label j) const template<class T, Foam::label width> inline Foam::FRWGraph<T,width>::FRWGraph() : - data_(), - nRows_(0) + data_(), + nRows_(0) { } @@ -66,8 +65,8 @@ inline Foam::FRWGraph<T,width>::FRWGraph const label s ) : - data_(s * width), - nRows_(s) + data_(s * width), + nRows_(s) { } @@ -77,22 +76,22 @@ template<class T, Foam::label width> inline Foam::FRWGraph<T,width>::FRWGraph ( const label s, - const T& t + const T& t ) : - data_(s * width, t), - nRows_(s) + data_(s * width, t), + nRows_(s) { } template<class T, Foam::label width> inline Foam::FRWGraph<T,width>::FRWGraph ( - const FRWGraph<T,width>& ol + const FRWGraph<T,width>& ol ) : - data_(ol.data_), - nRows_(ol.nRows_) + data_(ol.data_), + nRows_(ol.nRows_) { } @@ -113,111 +112,111 @@ inline Foam::label Foam::FRWGraph<T,width>::size() const template<class T, Foam::label width> inline Foam::label Foam::FRWGraph<T,width>::sizeOfRow(const label rowI) const { - return width; + return width; } template<class T, Foam::label width> inline void Foam::FRWGraph<T,width>::setSize(const label i) { - data_.setSize(i * width); - nRows_ = i; + data_.setSize(i * width); + nRows_ = i; } template<class T, Foam::label width> inline void Foam::FRWGraph<T,width>::clear() { data_.clear(); - nRows_ = 0; + nRows_ = 0; } template<class T, Foam::label width> inline void Foam::FRWGraph<T,width>::appendFixedList ( - const FixedList<T, width>& l + const FixedList<T, width>& l ) { - forAll(l, elI) - data_.append(l[elI]); - ++nRows_; + forAll(l, elI) + data_.append(l[elI]); + ++nRows_; } template<class T, Foam::label width> inline void Foam::FRWGraph<T,width>::setRow ( - const label rowI, - const FixedList<T, width>& l + const label rowI, + const FixedList<T, width>& l ) { - const label start = rowI * width; - forAll(l, elI) - data_[start+elI] = l[elI]; + const label start = rowI * width; + forAll(l, elI) + data_[start+elI] = l[elI]; } template<class T, Foam::label width> inline bool Foam::FRWGraph<T,width>::contains ( - const label rowI, + const label rowI, const T& e ) const { - const label start = rowI * width; - for(register label i=0;i<width;++i) - if( data_[start+i] == e ) - return true; - - return false; + const label start = rowI * width; + for(register label i=0;i<width;++i) + if( data_[start+i] == e ) + return true; + + return false; } template<class T, Foam::label width> inline Foam::label Foam::FRWGraph<T,width>::containsAtPosition ( - const label rowI, + const label rowI, const T& e ) const { - const label start = rowI * width; - for(register label i=0;i<width;++i) - if( data_[start+i] == e ) - return i; - - return -1; + const label start = rowI * width; + for(register label i=0;i<width;++i) + if( data_[start+i] == e ) + return i; + + return -1; } // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * // template<class T, Foam::label width> inline const T& Foam::FRWGraph<T,width>::operator() ( - const label i, - const label j + const label i, + const label j ) const { - #ifdef FULLDEBUG - checkIndex(i, j); - #endif - - return data_[i * width + j]; + #ifdef FULLDEBUG + checkIndex(i, j); + #endif + + return data_[i * width + j]; } template<class T, Foam::label width> inline T& Foam::FRWGraph<T,width>::operator() ( - const label i, const label j + const label i, const label j ) { - #ifdef FULLDEBUG - checkIndex(i, j); - #endif - - return data_[i * width + j]; + #ifdef FULLDEBUG + checkIndex(i, j); + #endif + + return data_[i * width + j]; } template<class T, Foam::label width> inline void Foam::FRWGraph<T,width>::operator= ( - const FRWGraph<T, width>& l + const FRWGraph<T, width>& l ) { - data_ = l.data_; + data_ = l.data_; } diff --git a/meshLibrary/utilities/containers/Graphs/cellIOGraph.C b/meshLibrary/utilities/containers/Graphs/cellIOGraph.C index 80e752c28350585012d19ec7057d5dc4c2b00b2c..6a809865c87a2443fc096d9df9f0061ef9a6ab90 100644 --- a/meshLibrary/utilities/containers/Graphs/cellIOGraph.C +++ b/meshLibrary/utilities/containers/Graphs/cellIOGraph.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description An graph of faces which supports automated output. @@ -39,14 +38,13 @@ namespace Foam cellIOGraph::cellIOGraph(const IOobject& io) : regIOobject(io), - VRWGraph() -{ -} + VRWGraph() +{} cellIOGraph::cellIOGraph ( - const IOobject& io, - const label size + const IOobject& io, + const label size ) : regIOobject(io), @@ -55,18 +53,17 @@ cellIOGraph::cellIOGraph cellIOGraph::cellIOGraph ( - const IOobject& io, - const VRWGraph& g + const IOobject& io, + const VRWGraph& g ) : regIOobject(io), VRWGraph(g) -{ -} +{} void cellIOGraph::operator=(const cellIOGraph& rhs) { - VRWGraph::operator=(rhs); + VRWGraph::operator=(rhs); } void cellIOGraph::operator=(const VRWGraph& rhs) @@ -81,7 +78,7 @@ bool cellIOGraph::writeData(Ostream& os) const // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -defineTemplateTypeNameAndDebugWithName(cellIOGraph, "cellList", 0); +defineTypeNameWithName(cellIOGraph, "cellList"); // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Graphs/cellIOGraph.H b/meshLibrary/utilities/containers/Graphs/cellIOGraph.H index d708de383ee4a141bce9279503e60cd459443935..89359a7e3aa89ffa94bdf1461ba89d7343092929 100644 --- a/meshLibrary/utilities/containers/Graphs/cellIOGraph.H +++ b/meshLibrary/utilities/containers/Graphs/cellIOGraph.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class cellIOGraph @@ -57,7 +56,7 @@ class cellIOGraph public: //- Runtime type information - TypeName("cellIOGraph"); + TypeName("cellIOGraph"); // Constructors @@ -78,7 +77,7 @@ public: // Member operators - void operator=(const cellIOGraph&); + void operator=(const cellIOGraph&); void operator=(const VRWGraph&); }; diff --git a/meshLibrary/utilities/containers/Graphs/faceIOGraph.C b/meshLibrary/utilities/containers/Graphs/faceIOGraph.C index 96ac4340d0b9f6fe4e4816523a73c51d2de0aba1..4a11e51fe58c3d6d6a34175a178a879eca5ce247 100644 --- a/meshLibrary/utilities/containers/Graphs/faceIOGraph.C +++ b/meshLibrary/utilities/containers/Graphs/faceIOGraph.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description An graph of faces which supports automated output. @@ -39,14 +38,13 @@ namespace Foam faceIOGraph::faceIOGraph(const IOobject& io) : regIOobject(io), - VRWGraph() -{ -} + VRWGraph() +{} faceIOGraph::faceIOGraph ( - const IOobject& io, - const label size + const IOobject& io, + const label size ) : regIOobject(io), @@ -55,18 +53,17 @@ faceIOGraph::faceIOGraph faceIOGraph::faceIOGraph ( - const IOobject& io, - const VRWGraph& g + const IOobject& io, + const VRWGraph& g ) : regIOobject(io), VRWGraph(g) -{ -} +{} void faceIOGraph::operator=(const faceIOGraph& rhs) { - VRWGraph::operator=(rhs); + VRWGraph::operator=(rhs); } void faceIOGraph::operator=(const VRWGraph& rhs) @@ -81,7 +78,7 @@ bool faceIOGraph::writeData(Ostream& os) const // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -defineTemplateTypeNameAndDebugWithName(faceIOGraph, "faceList", 0); +defineTypeNameWithName(faceIOGraph, "faceList"); // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Graphs/faceIOGraph.H b/meshLibrary/utilities/containers/Graphs/faceIOGraph.H index 1dbbf0edac4917a67521837df285c0793f73dd93..4ae84b564f6c657ed0d4bafe2d2a9f71b7eb36c5 100644 --- a/meshLibrary/utilities/containers/Graphs/faceIOGraph.H +++ b/meshLibrary/utilities/containers/Graphs/faceIOGraph.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class faceIOGraph @@ -57,7 +56,7 @@ class faceIOGraph public: //- Runtime type information - TypeName("faceIOGraph"); + TypeName("faceIOGraph"); // Constructors @@ -78,7 +77,7 @@ public: // Member operators - void operator=(const faceIOGraph&); + void operator=(const faceIOGraph&); void operator=(const VRWGraph&); }; diff --git a/meshLibrary/utilities/containers/IODynList/IODynList.C b/meshLibrary/utilities/containers/IODynList/IODynList.C index e2e129203e02c8d78bd2cd857e00df202af5db29..337aef406d412b9c9e56a9dd603c423a64dbf236 100644 --- a/meshLibrary/utilities/containers/IODynList/IODynList.C +++ b/meshLibrary/utilities/containers/IODynList/IODynList.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description An IODynList of a given type is a List of that type which supports automated @@ -41,7 +40,7 @@ template<class T, class IndexType> IODynList<T, IndexType>::IODynList(const IOobject& io) : regIOobject(io), - DynList<T, IndexType>() + DynList<T, IndexType>() { if ( @@ -58,8 +57,8 @@ IODynList<T, IndexType>::IODynList(const IOobject& io) template<class T, class IndexType> IODynList<T, IndexType>::IODynList ( - const IOobject& io, - const IndexType size + const IOobject& io, + const IndexType size ) : regIOobject(io), @@ -70,8 +69,8 @@ IODynList<T, IndexType>::IODynList template<class T, class IndexType> IODynList<T, IndexType>::IODynList ( - const IOobject& io, - const DynList<T, IndexType>& list + const IOobject& io, + const DynList<T, IndexType>& list ) : regIOobject(io), @@ -82,15 +81,15 @@ IODynList<T, IndexType>::IODynList readStream(typeName) >> *this; close(); } - - DynList<T, IndexType>::operator=(list); + + DynList<T, IndexType>::operator=(list); } template<class T, class IndexType> void IODynList<T, IndexType>::operator= ( - const IODynList<T, IndexType>& rhs + const IODynList<T, IndexType>& rhs ) { DynList<T, IndexType>::operator=(rhs); @@ -100,7 +99,7 @@ void IODynList<T, IndexType>::operator= template<class T, class IndexType> void IODynList<T, IndexType>::operator= ( - const DynList<T, IndexType>& rhs + const DynList<T, IndexType>& rhs ) { DynList<T, IndexType>::operator=(rhs); diff --git a/meshLibrary/utilities/containers/IODynList/IODynList.H b/meshLibrary/utilities/containers/IODynList/IODynList.H index acf398fbc6c680d5c2478996a8c440740e5fa6a9..ef512a3461bf8fb924bf9f4972755d931ad2f272 100644 --- a/meshLibrary/utilities/containers/IODynList/IODynList.H +++ b/meshLibrary/utilities/containers/IODynList/IODynList.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class IODynList diff --git a/meshLibrary/utilities/containers/IOLongList/IOLongList.C b/meshLibrary/utilities/containers/IOLongList/IOLongList.C index bd278523e74ebae95a1d16e02e2cad24ef304a2e..8297c8e2419a15478f3aaac0460e5a1190f7e620 100644 --- a/meshLibrary/utilities/containers/IOLongList/IOLongList.C +++ b/meshLibrary/utilities/containers/IOLongList/IOLongList.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description An IOLongList of a given type is a list which supports automated @@ -41,7 +40,7 @@ template<class T, label Offset> IOLongList<T, Offset>::IOLongList(const IOobject& io) : regIOobject(io), - LongList<T, Offset>() + LongList<T, Offset>() { if ( @@ -58,8 +57,8 @@ IOLongList<T, Offset>::IOLongList(const IOobject& io) template<class T, label Offset> IOLongList<T, Offset>::IOLongList ( - const IOobject& io, - const label size + const IOobject& io, + const label size ) : regIOobject(io), @@ -70,8 +69,8 @@ IOLongList<T, Offset>::IOLongList template<class T, label Offset> IOLongList<T, Offset>::IOLongList ( - const IOobject& io, - const LongList<T, Offset>& list + const IOobject& io, + const LongList<T, Offset>& list ) : regIOobject(io), @@ -82,15 +81,15 @@ IOLongList<T, Offset>::IOLongList readStream(typeName) >> *this; close(); } - - LongList<T, Offset>::operator=(list); + + LongList<T, Offset>::operator=(list); } template<class T, label Offset> void IOLongList<T, Offset>::operator= ( - const IOLongList<T, Offset>& rhs + const IOLongList<T, Offset>& rhs ) { LongList<T, Offset>::operator=(rhs); @@ -100,7 +99,7 @@ void IOLongList<T, Offset>::operator= template<class T, label Offset> void IOLongList<T, Offset>::operator= ( - const LongList<T, Offset>& rhs + const LongList<T, Offset>& rhs ) { LongList<T, Offset>::operator=(rhs); diff --git a/meshLibrary/utilities/containers/IOLongList/IOLongList.H b/meshLibrary/utilities/containers/IOLongList/IOLongList.H index 7ae448c6722b86646800c588af11576f58ec0acd..57f9ee8e950a01ae584e56d4f03a1cfec2fe7563 100644 --- a/meshLibrary/utilities/containers/IOLongList/IOLongList.H +++ b/meshLibrary/utilities/containers/IOLongList/IOLongList.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class IOLongList diff --git a/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.C b/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.C index c99007ef355fddaf8adbace3a86230c01912b57e..6c3a547d2f7001a3d8f80adb668953a676e6b0dd 100644 --- a/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.C +++ b/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description Declaration of IOLongList ClassNames for IOLists that do not have .C files. @@ -35,15 +34,15 @@ Description namespace Foam { defineCompoundTypeName(IOLongList<label>, labelIOListPMG); - defineCompoundTypeName(IOLongList<point>, pointIOFieldPMG); - //defineCompoundTypeName(IOLongList<face>, faceIOListPMG); - //defineCompoundTypeName(IOLongList<cell>, cellIOListPMG); + defineCompoundTypeName(IOLongList<point>, pointIOFieldPMG); + //defineCompoundTypeName(IOLongList<face>, faceIOListPMG); + //defineCompoundTypeName(IOLongList<cell>, cellIOListPMG); //addCompoundToRunTimeSelectionTable(IOLongList<label>, labelIOLongList); defineTemplateTypeNameAndDebugWithName(labelIOListPMG, "labelList", 0); - defineTemplateTypeNameAndDebugWithName(pointIOFieldPMG, "vectorField", 0); - //defineTemplateTypeNameAndDebugWithName(faceIOListPMG, "faceList", 0); - //defineTemplateTypeNameAndDebugWithName(cellIOListPMG, "cellList", 0); + defineTemplateTypeNameAndDebugWithName(pointIOFieldPMG, "vectorField", 0); + //defineTemplateTypeNameAndDebugWithName(faceIOListPMG, "faceList", 0); + //defineTemplateTypeNameAndDebugWithName(cellIOListPMG, "cellList", 0); } // ************************************************************************* // diff --git a/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.H b/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.H index bc7f26953dd403947aeb3d14502ef171d80344d5..21be5407ef87827f54eee6ddd04ed473cddb2051 100644 --- a/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.H +++ b/meshLibrary/utilities/containers/IOLongList/IOLongListInstances.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Type IOLongList @@ -44,8 +43,8 @@ namespace Foam { typedef IOLongList<point> pointIOFieldPMG; typedef IOLongList<face> faceIOListPMG; - typedef IOLongList<cell> cellIOListPMG; - typedef IOLongList<label> labelIOListPMG; + typedef IOLongList<cell> cellIOListPMG; + typedef IOLongList<label> labelIOListPMG; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Lists/cellListPMG.H b/meshLibrary/utilities/containers/Lists/cellListPMG.H index d7e62ef36a302fd7befe1475cd00975b4cd070b0..6b794d051191d589fd6819f531625c58215c9cf7 100644 --- a/meshLibrary/utilities/containers/Lists/cellListPMG.H +++ b/meshLibrary/utilities/containers/Lists/cellListPMG.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class cellListPMG Description This is a container with additional size to prevent re-allocation - every time it is resized + every time it is resized SourceFiles @@ -49,51 +48,51 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // class cellListPMG - : public cellList + : public cellList { - // Private data - //- number of used elements - label nElmts_; - - // Disallow bitwise assignment - void operator=(const cellListPMG&); - - cellListPMG(const cellListPMG&); - - // Disallow transfer from cellList - void transfer(cellList&); - + // Private data + //- number of used elements + label nElmts_; + + // Disallow bitwise assignment + void operator=(const cellListPMG&); + + cellListPMG(const cellListPMG&); + + // Disallow transfer from cellList + void transfer(cellList&); + public: - - // Constructors - //- null construct - inline cellListPMG(); - - // Destructor - inline ~cellListPMG(); - - // Member functions - //- return the number of used elements - inline label size() const; - - //- set the number of used elements - inline void setSize(const label nElmts); - - //- set the size to zero - inline void clear(); - - //- add a cell at the end of the list - inline void append(const cell&); - - //- return an element with bound checking - inline cell& newElmt(const label); - - // Member operators - inline void operator=(const cellList&); - - friend inline Ostream& operator<<(Ostream&, const cellListPMG&); - - friend inline Istream& operator>>(Istream&, cellListPMG&); + + // Constructors + //- null construct + inline cellListPMG(); + + // Destructor + inline ~cellListPMG(); + + // Member functions + //- return the number of used elements + inline label size() const; + + //- set the number of used elements + inline void setSize(const label nElmts); + + //- set the size to zero + inline void clear(); + + //- add a cell at the end of the list + inline void append(const cell&); + + //- return an element with bound checking + inline cell& newElmt(const label); + + // Member operators + inline void operator=(const cellList&); + + friend inline Ostream& operator<<(Ostream&, const cellListPMG&); + + friend inline Istream& operator>>(Istream&, cellListPMG&); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Lists/cellListPMGI.H b/meshLibrary/utilities/containers/Lists/cellListPMGI.H index 31e71675ef335f70c5cfa643bef2d73035ee3f50..a85205a09bdb009d3e36e1ff3faa61526591e5bc 100644 --- a/meshLibrary/utilities/containers/Lists/cellListPMGI.H +++ b/meshLibrary/utilities/containers/Lists/cellListPMGI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,8 +39,8 @@ namespace Foam inline cellListPMG::cellListPMG() : - cellList(), - nElmts_(0) + cellList(), + nElmts_(0) { } @@ -53,76 +52,76 @@ inline cellListPMG::~cellListPMG() } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + inline label cellListPMG::size() const { - return nElmts_; + return nElmts_; } inline void cellListPMG::setSize(const label nElmts) { - if( nElmts >= cellList::size() ) - { - if( cellList::size() != 0 ) - { - Info << "Resizing cells!" << endl; - cellList copy(label(1.5*nElmts)); - for(label i=0;i<nElmts_;++i) - copy[i].transfer(this->operator[](i)); - - cellList::transfer(copy); - } - else - { - cellList::setSize(label(1.5*nElmts)); - } - } - - nElmts_ = nElmts; + if( nElmts >= cellList::size() ) + { + if( cellList::size() != 0 ) + { + Info << "Resizing cells!" << endl; + cellList copy(label(1.5*nElmts)); + for(label i=0;i<nElmts_;++i) + copy[i].transfer(this->operator[](i)); + + cellList::transfer(copy); + } + else + { + cellList::setSize(label(1.5*nElmts)); + } + } + + nElmts_ = nElmts; } inline void cellListPMG::clear() { - nElmts_ = 0; + nElmts_ = 0; } inline void cellListPMG::append(const cell& c) { - const label i = nElmts_; - setSize(i+1); - this->operator[](i) = c; + const label i = nElmts_; + setSize(i+1); + this->operator[](i) = c; } inline cell& cellListPMG::newElmt(const label cI) { - setSize(cI+1); - return this->operator[](cI); + setSize(cI+1); + return this->operator[](cI); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // inline void cellListPMG::operator=(const cellList& cls) { - setSize(cls.size()); - forAll(cls, cI) - this->operator[](cI) = cls[cI]; + setSize(cls.size()); + forAll(cls, cI) + this->operator[](cI) = cls[cI]; } - + inline Ostream& operator<<(Ostream& os, const cellListPMG& cls) { - SubList<cell> c(cls, cls.nElmts_, 0); - - os << c; - return os; + SubList<cell> c(cls, cls.nElmts_, 0); + + os << c; + return os; } inline Istream& operator>>(Istream& is, cellListPMG& cls) { - cellList& cells = static_cast<cellList&>(cls); - is >> cells; - cls.nElmts_ = cells.size(); - - return is; + cellList& cells = static_cast<cellList&>(cls); + is >> cells; + cls.nElmts_ = cells.size(); + + return is; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/dataConversion/foamToEnsight/writeMeshEnsight.H b/meshLibrary/utilities/containers/Lists/edgeLongList.H similarity index 57% rename from meshLibrary/utilities/dataConversion/foamToEnsight/writeMeshEnsight.H rename to meshLibrary/utilities/containers/Lists/edgeLongList.H index 3d72d8ed7f2f18ab84bb97ec4c32820cdeb52e3e..25dfbeb988410204652f787b2ec833651aaf8953 100644 --- a/meshLibrary/utilities/dataConversion/foamToEnsight/writeMeshEnsight.H +++ b/meshLibrary/utilities/containers/Lists/edgeLongList.H @@ -1,51 +1,50 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class - ensightMesh + edgeLongList Description + This is a typedef for LongList<edge> SourceFiles - ensightMesh.C \*---------------------------------------------------------------------------*/ -#ifndef writeEnsightMesh_H -#define writeEnsightMesh_H +#ifndef edgeLongList_H +#define edgeLongList_H -#include "OFstream.H" -#include "word.H" +#include "edge.H" +#include "LongList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { -class polyMeshGen; - -void writeMeshEnsight(const polyMeshGen& mesh, const word& fName); +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +typedef LongList<edge> edgeLongList; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Lists/faceListPMG.C b/meshLibrary/utilities/containers/Lists/faceListPMG.C index 762fb463d4482c3fc6899b75d73372fb2bb04842..ec648f7f20bc4332fe482b48eed9f00c47a10580 100644 --- a/meshLibrary/utilities/containers/Lists/faceListPMG.C +++ b/meshLibrary/utilities/containers/Lists/faceListPMG.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description Declaration of IODynListHP ClassNames for IOLists that do not have .C files. @@ -34,15 +33,7 @@ Description namespace Foam { - //defineCompoundTypeName(IODynListHP<label>, labelIOListPMG); - //defineCompoundTypeName(IODynListHP<point>, pointIOFieldPMG); - //defineCompoundTypeName(IODynListHP<face>, faceIOListPMG); - //defineCompoundTypeName(IODynListHP<cell>, cellIOListPMG); - //addCompoundToRunTimeSelectionTable(IODynListHP<label>, labelIODynListHP); - - defineTemplateTypeNameAndDebugWithName(faceListPMG, "faceList", 0); - //defineTemplateTypeNameAndDebugWithName(faceIOListPMG, "faceList", 0); - //defineTemplateTypeNameAndDebugWithName(cellIOListPMG, "cellList", 0); +defineTypeNameWithName(faceListPMG, "faceList"); } // ************************************************************************* // diff --git a/meshLibrary/utilities/containers/Lists/faceListPMG.H b/meshLibrary/utilities/containers/Lists/faceListPMG.H index 67afcc28351d50235384a765024298fea6774890..d17c5d78c5a3ee97f66a9c048f7e35e1a5067273 100644 --- a/meshLibrary/utilities/containers/Lists/faceListPMG.H +++ b/meshLibrary/utilities/containers/Lists/faceListPMG.H @@ -1,36 +1,35 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class faceListPMG Description This is a container with additional size to prevent re-allocation - every time it is resized + every time it is resized SourceFiles - + \*---------------------------------------------------------------------------*/ @@ -50,63 +49,63 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // class faceListPMG -: public regIOobject, - public faceList +: public regIOobject, + public faceList { - // Private data - //- number of used elements - label nElmts_; - - // Disallow bitwise assignment - void operator=(const faceListPMG&); - - faceListPMG(const faceListPMG&); - - // Disallow transfer from faceList - void transfer(faceList&); - + // Private data + //- number of used elements + label nElmts_; + + // Disallow bitwise assignment + void operator=(const faceListPMG&); + + faceListPMG(const faceListPMG&); + + // Disallow transfer from faceList + void transfer(faceList&); + public: - - TypeName("List"); - - // Constructors - //- construct from IOobject - inline faceListPMG(const IOobject&); - - //- construct from IOobject and size - inline faceListPMG(const IOobject&, const label); - - //- construct from IOobject and faceList - inline faceListPMG(const IOobject&, const faceList&); - - // Destructor - inline ~faceListPMG(); - - // Member functions - //- return the number of used elements - inline label size() const; - - //- set the number of used elements - inline void setSize(const label nElmts); - - //- set the size to zero - inline void clear(); - - //- add a face at the end of the list - inline void append(const face&); - - //- return an element with bound checking - inline face& newElmt(const label); - - //- read/write the list onto disk - inline bool writeData(Ostream&) const; - - // Member operators - inline void operator=(const faceList&); - - friend inline Ostream& operator<<(Ostream&, const faceListPMG&); - - friend inline Istream& operator>>(Istream&, faceListPMG&); + + TypeName("faceList"); + + // Constructors + //- construct from IOobject + inline faceListPMG(const IOobject&); + + //- construct from IOobject and size + inline faceListPMG(const IOobject&, const label); + + //- construct from IOobject and faceList + inline faceListPMG(const IOobject&, const faceList&); + + // Destructor + inline ~faceListPMG(); + + // Member functions + //- return the number of used elements + inline label size() const; + + //- set the number of used elements + inline void setSize(const label nElmts); + + //- set the size to zero + inline void clear(); + + //- add a face at the end of the list + inline void append(const face&); + + //- return an element with bound checking + inline face& newElmt(const label); + + //- read/write the list onto disk + inline bool writeData(Ostream&) const; + + // Member operators + inline void operator=(const faceList&); + + friend inline Ostream& operator<<(Ostream&, const faceListPMG&); + + friend inline Istream& operator>>(Istream&, faceListPMG&); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Lists/faceListPMGI.H b/meshLibrary/utilities/containers/Lists/faceListPMGI.H index 2d8c5f76be30e66a2f8f5900cc5ca892b6157723..a1e6bb245517ab95b801058557b64e3a13ccac6b 100644 --- a/meshLibrary/utilities/containers/Lists/faceListPMGI.H +++ b/meshLibrary/utilities/containers/Lists/faceListPMGI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,25 +39,25 @@ namespace Foam inline faceListPMG::faceListPMG(const IOobject& io) : - regIOobject(io), - faceList(readStream(typeName)), - nElmts_(faceList::size()) + regIOobject(io), + faceList(readStream(typeName)), + nElmts_(faceList::size()) { } inline faceListPMG::faceListPMG(const IOobject& io, const label s) : - regIOobject(io), - faceList(s), - nElmts_(s) + regIOobject(io), + faceList(s), + nElmts_(s) { } inline faceListPMG::faceListPMG(const IOobject& io, const faceList& fcs) : - regIOobject(io), - faceList(fcs), - nElmts_(fcs.size()) + regIOobject(io), + faceList(fcs), + nElmts_(fcs.size()) { } @@ -70,81 +69,81 @@ inline faceListPMG::~faceListPMG() } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + inline label faceListPMG::size() const { - return nElmts_; + return nElmts_; } inline void faceListPMG::setSize(const label nElmts) { - if( nElmts >= faceList::size() ) - { - if( faceList::size() != 0 ) - { - Info << "Resizing faces!" << endl; - faceList copy(label(1.5*nElmts)); - for(label i=0;i<nElmts_;++i) - copy[i].transfer(this->operator[](i)); - - faceList::transfer(copy); - } - else - { - faceList::setSize(label(1.5*nElmts)); - } - } - - nElmts_ = nElmts; + if( nElmts >= faceList::size() ) + { + if( faceList::size() != 0 ) + { + Info << "Resizing faces!" << endl; + faceList copy(label(1.5*nElmts)); + for(label i=0;i<nElmts_;++i) + copy[i].transfer(this->operator[](i)); + + faceList::transfer(copy); + } + else + { + faceList::setSize(label(1.5*nElmts)); + } + } + + nElmts_ = nElmts; } inline void faceListPMG::clear() { - nElmts_ = 0; + nElmts_ = 0; } inline void faceListPMG::append(const face& f) { - const label i = nElmts_; - setSize(i+1); - this->operator[](i) = f; + const label i = nElmts_; + setSize(i+1); + this->operator[](i) = f; } inline face& faceListPMG::newElmt(const label fI) { - setSize(fI+1); - return this->operator[](fI); + setSize(fI+1); + return this->operator[](fI); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // inline bool faceListPMG::writeData(Ostream& os) const { - return (os << *this).good(); + return (os << *this).good(); } inline void faceListPMG::operator=(const faceList& fcs) { - setSize(fcs.size()); - forAll(fcs, fI) - this->operator[](fI) = fcs[fI]; + setSize(fcs.size()); + forAll(fcs, fI) + this->operator[](fI) = fcs[fI]; } - + inline Ostream& operator<<(Ostream& os, const faceListPMG& fcs) { - SubList<face> f(fcs, fcs.nElmts_, 0); - - os << f; - return os; + SubList<face> f(fcs, fcs.nElmts_, 0); + + os << f; + return os; } inline Istream& operator>>(Istream& is, faceListPMG& fcs) { - faceList& faces = static_cast<faceList&>(fcs); - is >> faces; - fcs.nElmts_ = faces.size(); - - return is; + faceList& faces = static_cast<faceList&>(fcs); + is >> faces; + fcs.nElmts_ = faces.size(); + + return is; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Lists/labelListPMG.H b/meshLibrary/utilities/containers/Lists/labelLongList.H similarity index 65% rename from meshLibrary/utilities/containers/Lists/labelListPMG.H rename to meshLibrary/utilities/containers/Lists/labelLongList.H index 347b950c4e2208966bdae80d628ffc44c6e20fa9..0236a4f9c7366f0bd530433e89942578f757a140 100644 --- a/meshLibrary/utilities/containers/Lists/labelListPMG.H +++ b/meshLibrary/utilities/containers/Lists/labelLongList.H @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class - labelListPMG + labelLongList Description This is a typedef for LongList<label> @@ -32,8 +31,8 @@ SourceFiles \*---------------------------------------------------------------------------*/ -#ifndef labelListPMG_H -#define labelListPMG_H +#ifndef labelLongList_H +#define labelLongList_H #include "label.H" #include "LongList.H" @@ -45,7 +44,7 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -typedef LongList<label> labelListPMG; +typedef LongList<label> labelLongList; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Lists/pointFieldPMG.C b/meshLibrary/utilities/containers/Lists/pointFieldPMG.C index 968078c2c6d016e2604c4edec2a1b1d8b00d9d0e..c67b6d4e8cb0b298b617160bd62e53484323c581 100644 --- a/meshLibrary/utilities/containers/Lists/pointFieldPMG.C +++ b/meshLibrary/utilities/containers/Lists/pointFieldPMG.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description Declaration of IODynListHP ClassNames for IOLists that do not have .C files. @@ -34,13 +33,7 @@ Description namespace Foam { - //defineCompoundTypeName(IODynListHP<label>, labelIOListPMG); - //defineCompoundTypeName(IODynListHP<point>, pointIOFieldPMG); - //defineCompoundTypeName(IODynListHP<face>, faceIOListPMG); - //defineCompoundTypeName(IODynListHP<cell>, cellIOListPMG); - //addCompoundToRunTimeSelectionTable(IODynListHP<label>, labelIODynListHP); - - defineTemplateTypeNameAndDebugWithName(pointFieldPMG, "vectorField", 0); + defineTypeNameWithName(pointFieldPMG, "vectorField"); } // ************************************************************************* // diff --git a/meshLibrary/utilities/containers/Lists/pointFieldPMG.H b/meshLibrary/utilities/containers/Lists/pointFieldPMG.H index 34a020926c2056ce9c823dffe0a6b537a1f490b5..8a58e4b03e4de19ecbd5e51922b641b5d3a34e10 100644 --- a/meshLibrary/utilities/containers/Lists/pointFieldPMG.H +++ b/meshLibrary/utilities/containers/Lists/pointFieldPMG.H @@ -1,36 +1,35 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class pointFieldPMG Description This is a container with additional size to prevent re-allocation - every time it is resized + every time it is resized SourceFiles - + \*---------------------------------------------------------------------------*/ @@ -50,63 +49,70 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // class pointFieldPMG -: public regIOobject, - public pointField +: public regIOobject, + public pointField { - // Private data - //- number of used elements - label nElmts_; - - // Disallow bitwise assignment - void operator=(const pointFieldPMG&); - - pointFieldPMG(const pointFieldPMG&); - - // Disallow transfer from pointField - void transfer(pointField&); - + // Private data + //- number of used elements + label nElmts_; + + // Disallow bitwise assignment + void operator=(const pointFieldPMG&); + + pointFieldPMG(const pointFieldPMG&); + + // Disallow transfer from pointField + void transfer(pointField&); + public: - - TypeName("Field"); - - // Constructors - //- construct from IOobject - inline pointFieldPMG(const IOobject&); - - //- construct from IOobject and size - inline pointFieldPMG(const IOobject&, const label); - - //- construct from IOobject and pointField - inline pointFieldPMG(const IOobject&, const pointField&); - - // Destructor - inline ~pointFieldPMG(); - - // Member functions - //- return the number of used elements - inline label size() const; - - //- set the number of used elements - inline void setSize(const label nElmts); - - //- set the size to zero - inline void clear(); - - //- add a point at the end of the list - inline void append(const point&); - - //- return an element with bound checking - inline point& newElmt(const label); - - //- read/write the list onto disk - inline bool writeData(Ostream&) const; - - // Member operators - inline void operator=(const pointField&); - - friend inline Ostream& operator<<(Ostream&, const pointFieldPMG&); - - friend inline Istream& operator>>(Istream&, pointFieldPMG&); + + // Declare type name + TypeName("vectorField"); + + // Constructors + //- construct from IOobject + inline pointFieldPMG(const IOobject&); + + //- construct from IOobject and size + inline pointFieldPMG(const IOobject&, const label); + + //- construct from IOobject and pointField + inline pointFieldPMG(const IOobject&, const pointField&); + + // Destructor + inline ~pointFieldPMG(); + + // Member functions + //- return the number of used elements + inline label size() const; + + //- set the number of used elements + inline void setSize(const label nElmts); + + //- reserve the memory for the specified number of elements + //- the request is ignored if the specified value is smaller than + //- the current number of elements + //- does not change the size + inline void reserve(const label capacity); + + //- set the size to zero + inline void clear(); + + //- add a point at the end of the list + inline void append(const point&); + + //- return an element with bound checking + inline point& newElmt(const label); + + //- read/write the list onto disk + inline bool writeData(Ostream&) const; + + // Member operators + inline void operator=(const pointField&); + + friend inline Ostream& operator<<(Ostream&, const pointFieldPMG&); + + friend inline Istream& operator>>(Istream&, pointFieldPMG&); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/Lists/pointFieldPMGI.H b/meshLibrary/utilities/containers/Lists/pointFieldPMGI.H index 5f7c9667122e37b4de127996ff04d8263305d080..33f860756d46367723b2a25430952361655e8690 100644 --- a/meshLibrary/utilities/containers/Lists/pointFieldPMGI.H +++ b/meshLibrary/utilities/containers/Lists/pointFieldPMGI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,101 +39,104 @@ namespace Foam inline pointFieldPMG::pointFieldPMG(const IOobject& io) : - regIOobject(io), - pointField(readStream(typeName)), - nElmts_(pointField::size()) + regIOobject(io), + pointField(readStream(typeName)), + nElmts_(pointField::size()) { - close(); + close(); } inline pointFieldPMG::pointFieldPMG(const IOobject& io, const label s) : - regIOobject(io), - pointField(s), - nElmts_(s) -{ -} + regIOobject(io), + pointField(s), + nElmts_(s) +{} inline pointFieldPMG::pointFieldPMG(const IOobject& io, const pointField& pts) : - regIOobject(io), - pointField(pts), - nElmts_(pts.size()) -{ -} + regIOobject(io), + pointField(pts), + nElmts_(pts.size()) +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Destructor inline pointFieldPMG::~pointFieldPMG() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + inline label pointFieldPMG::size() const { - return nElmts_; + return nElmts_; } inline void pointFieldPMG::setSize(const label nElmts) { - if( nElmts >= pointField::size() ) - { - Info << "Resizing points!" << endl; - pointField::setSize(label(1.5*nElmts)+1); - } + if( nElmts >= pointField::size() ) + { + Info << "Resizing points!" << endl; + pointField::setSize(label(1.5*nElmts)+1); + } + + nElmts_ = nElmts; +} - nElmts_ = nElmts; +inline void pointFieldPMG::reserve(const label capacity) +{ + if( capacity > size() ) + this->setSize(capacity); } inline void pointFieldPMG::clear() { - nElmts_ = 0; + nElmts_ = 0; } inline void pointFieldPMG::append(const point& p) { - const label i = nElmts_; - setSize(i+1); - this->operator[](i) = p; + const label i = nElmts_; + setSize(i+1); + this->operator[](i) = p; } inline point& pointFieldPMG::newElmt(const label pI) { - setSize(pI+1); - return this->operator[](pI); + setSize(pI+1); + return this->operator[](pI); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // inline bool pointFieldPMG::writeData(Ostream& os) const { - return (os << *this).good(); + return (os << *this).good(); } inline void pointFieldPMG::operator=(const pointField& pts) { - setSize(pts.size()); - forAll(pts, pI) - this->operator[](pI) = pts[pI]; + setSize(pts.size()); + forAll(pts, pI) + this->operator[](pI) = pts[pI]; } - + inline Ostream& operator<<(Ostream& os, const pointFieldPMG& pts) { - SubList<point> p(pts, pts.nElmts_, 0); - - os << p; - return os; + SubList<point> p(pts, pts.nElmts_, 0); + + os << p; + return os; } inline Istream& operator>>(Istream& is, pointFieldPMG& pts) { - pointField& points = static_cast<pointField&>(pts); - is >> points; - pts.nElmts_ = points.size(); - - return is; + pointField& points = static_cast<pointField&>(pts); + is >> points; + pts.nElmts_ = points.size(); + + return is; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/LongList/LongList.C b/meshLibrary/utilities/containers/LongList/LongList.C index 40b37762eaa3d296a534d852a6a256c09249183a..05ba461d5642bb5b8ec3675df791c092b192f004 100644 --- a/meshLibrary/utilities/containers/LongList/LongList.C +++ b/meshLibrary/utilities/containers/LongList/LongList.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -31,14 +30,14 @@ License #include "Time.H" // * * * * * * * * * * * * * * * IOstream Operators * * * * * * * * * * * * // - + template<class T, Foam::label Offset> void Foam::LongList<T, Offset>::writeEntry(Ostream& os) const { - if + if ( size() && - token::compound::isCompound + token::compound::isCompound ( "LongList<" + word(pTraits<T>::typeName) + '>' ) @@ -46,18 +45,18 @@ void Foam::LongList<T, Offset>::writeEntry(Ostream& os) const { os << word("LongList<" + word(pTraits<T>::typeName) + '>') << " "; } - + os << *this; } template<class T, Foam::label Offset> void Foam::LongList<T, Offset>::writeEntry ( - const word& keyword, - Ostream& os + const word& keyword, + Ostream& os ) const { - os.writeKeyword(keyword); + os.writeKeyword(keyword); writeEntry(os); os << token::END_STATEMENT << endl; } @@ -75,14 +74,14 @@ Foam::Ostream& Foam::operator<< { // Write size of list and start contents delimiter os << DL.size() << token::BEGIN_LIST; - + // Write list contents forAll(DL, i) { if( i != 0 ) os << token::SPACE; os << DL[i]; } - + // Write end of contents delimiter os << token::END_LIST; } @@ -90,13 +89,13 @@ Foam::Ostream& Foam::operator<< { // Write size of list and start contents delimiter os << nl << DL.size() << nl << token::BEGIN_LIST; - + // Write list contents forAll(DL, i) { os << nl << DL[i]; } - + // Write end of contents delimiter os << nl << token::END_LIST << nl; } @@ -110,26 +109,26 @@ Foam::Ostream& Foam::operator<< label currBlock(0); label currPos(0); - + while( currPos < DL.nextFree_ ) { const label bs = Foam::min(DL.nextFree_ - currPos, blockSize); - + os.write ( reinterpret_cast<const char*>(DL.dataPtr_[currBlock]), bs * sizeof(T) ); - + currPos += bs; ++currBlock; } } } - - // Check state of IOstream + + // Check state of IOstream os.check("Ostream& operator<<(Ostream&, const LongList&)"); - + return os; } @@ -159,9 +158,6 @@ Foam::Istream& Foam::operator>> // Set list length to that read DL.setSize(size); - - if( size == 0 ) - return is; // Read list contents depending on data format if( (is.format() == IOstream::ASCII) || !contiguous<T>() ) @@ -169,6 +165,42 @@ Foam::Istream& Foam::operator>> // Read beginning of contents char listDelimiter = is.readBeginList("List"); + if( size == 0 ) + { + if( listDelimiter != token::BEGIN_LIST ) + { + WarningIn + ( + "template<class T, Foam::label Offset>" + + "Foam::Istream& Foam::operator>>" + "(" + "Foam::Istream& ," + "Foam::LongList<T, Offset>& DL" + ")" + ) << "Missing ( after 0" << endl; + + return is; + } + + listDelimiter = is.readEndList("List"); + if( listDelimiter != token::END_LIST ) + { + WarningIn + ( + "template<class T, Foam::label Offset>" + + "Foam::Istream& Foam::operator>>" + "(" + "Foam::Istream& ," + "Foam::LongList<T, Offset>& DL" + ")" + ) << "Missing ) after 0(" << endl; + } + + return is; + } + if( listDelimiter == token::BEGIN_LIST ) { for(register label i=0;i<size;++i) @@ -197,27 +229,27 @@ Foam::Istream& Foam::operator>> DL[i] = element; } } - + // Read end of contents is.readEndList("List"); } else { const label blockSize = (1<<DL.shift_); - + label currBlock(0); label currPos(0); - + while( currPos < size ) { const label bs = Foam::min(size - currPos, blockSize); - + is.read ( reinterpret_cast<char*>(DL.dataPtr_[currBlock]), bs * sizeof(T) ); - + currPos += bs; ++currBlock; } @@ -255,13 +287,13 @@ void Foam::LongList<T, Offset>::appendFromStream(Istream& is) if( firstToken.isLabel() ) { const label size = firstToken.labelToken(); - + if( size == 0 ) { Pout << "Appending empty stream" << endl; return; } - + label origSize(this->size()); // Set list length to that read @@ -303,7 +335,7 @@ void Foam::LongList<T, Offset>::appendFromStream(Istream& is) ++origSize; } } - + // Read end of contents is.readEndList("List"); } @@ -311,31 +343,31 @@ void Foam::LongList<T, Offset>::appendFromStream(Istream& is) { List<T> buf(size); is.read(reinterpret_cast<char*>(buf.begin()), size * sizeof(T)); - + forAll(buf, i) this->operator[](origSize++) = buf[i]; - + /*const label blockSize = 1<<shift_; - + Info << "nextFree_ " << nextFree_ << endl; - + //- append elements by reading binary block while( origSize < nextFree_ ) { const label currBlock = origSize >> shift_; const label currPos = origSize & mask_; - + Info << "Orig size " << origSize << nl << "currBlock " << currBlock << nl << "currPos " << currPos << endl; - + T* data = &dataPtr_[currBlock][currPos]; - + label bs = Foam::min(nextFree_-origSize, blockSize); bs = Foam::min(blockSize - currPos, bs); - + Info << "bs " << bs << endl; - + is.read(reinterpret_cast<char*>(data), bs * sizeof(T)); origSize += bs; } */ diff --git a/meshLibrary/utilities/containers/LongList/LongList.H b/meshLibrary/utilities/containers/LongList/LongList.H index 30e89ffad22bf20f491343170620f7f92369d1e1..68e72e63f1f936f18c0b8e088501f763f6f7b7a8 100644 --- a/meshLibrary/utilities/containers/LongList/LongList.H +++ b/meshLibrary/utilities/containers/LongList/LongList.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class LongList @@ -29,8 +28,8 @@ Description A dynamic list is a 1-D vector of objects of type T which resizes itself as necessary to accept the new objects. Internal storage is a 2-D graph with a fixed size of the chunks used to store the data. - This way the data does not get copied every time array is resized, but - only the pointers to the chunks of data. + This way the data does not get copied every time array is resized, but + only the pointers to the chunks of data. SourceFiles LongListI.H @@ -76,41 +75,41 @@ template<class T, label Offset = 19> class LongList { // Private data - //- number of allocated elements - label N_; - - //- number of elements in the list - label nextFree_; + //- number of allocated elements + label N_; + + //- number of elements in the list + label nextFree_; //- number of used blocks of data - label numBlocks_; + label numBlocks_; //- maximum number of blocks that can be allocated //- without reallocating the list containing pointers //- to the chunks of data label numAllocatedBlocks_; - - //- size of blocks is calculated by powers of 2 - //- and therefore the access can be done using shift and mask - label shift_; - label mask_; + + //- size of blocks is calculated by powers of 2 + //- and therefore the access can be done using shift and mask + label shift_; + label mask_; - //- array of pointers to the blocks of data, each of the size WIDTH - T** dataPtr_; - - // Private member functions - //- check index - void checkIndex(label const i) const; - - //- initialize width and mask - void initializeParameters(); + //- array of pointers to the blocks of data, each of the size WIDTH + T** dataPtr_; + + // Private member functions + //- check index + void checkIndex(label const i) const; + + //- initialize width and mask + void initializeParameters(); //- Allocate memory for the list void allocateSize(const label); - - //- delete all elements - void clearOut(); - + + //- delete all elements + void clearOut(); + public: // Constructors @@ -121,15 +120,15 @@ public: //- Construct given size explicit inline LongList(const label size); - //- Construct to given size and initialize - explicit inline LongList(const label size, const T& t); + //- Construct to given size and initialize + explicit inline LongList(const label size, const T& t); //- Copy contructor - inline LongList(const LongList<T, Offset>&); + inline LongList(const LongList<T, Offset>&); - // Destructor + // Destructor - inline ~LongList(); + inline ~LongList(); // Member Functions @@ -154,52 +153,52 @@ public: //- Shrink the list to the number of elements used inline LongList<T, Offset>& shrink(); - - //- transfer the list from another one without allocating it - inline void transfer(LongList<T, Offset>&); + + //- transfer the list from another one without allocating it + inline void transfer(LongList<T, Offset>&); // Member Operators //- Append an element at the end of the list inline void append(const T& e); - - //- Append an element at the end of the list if it is not yet - //- present in the list (takes linear time) - inline void appendIfNotIn(const T& e); - - //- check if the element is in the list (takes linear time) - inline bool contains(const T& e) const; - inline label containsAtPosition(const T& e) const; + + //- Append an element at the end of the list if it is not yet + //- present in the list (takes linear time) + inline void appendIfNotIn(const T& e); + + //- check if the element is in the list (takes linear time) + inline bool contains(const T& e) const; + inline label containsAtPosition(const T& e) const; //- Return and remove the element inline T remove(const label i); inline T removeLastElement(); - - //- get and set operators - inline const T& operator[](const label i) const; - inline T& operator[](const label i); + + //- get and set operators + inline const T& operator[](const label i) const; + inline T& operator[](const label i); //- Return non-const access to an element, // resizing the list if necessary inline T& operator()(const label); - - //- return a non-const access to an element, - // resize the list if necessary - inline T& newElmt(const label); + + //- return a non-const access to an element, + // resize the list if necessary + inline T& newElmt(const label); //- Assignment of all entries to the given value inline void operator=(const T&); - - //- Assignment operator - inline void operator=(const LongList<T, Offset>&); + + //- Assignment operator + inline void operator=(const LongList<T, Offset>&); // IOstream operators //- Read from stream and append to the current content void appendFromStream(Istream&); - //- Write as a dictionary entry. + //- Write as a dictionary entry. void writeEntry(Ostream& os) const; //- Write as a dictionary entry with keyword. diff --git a/meshLibrary/utilities/containers/LongList/LongListI.H b/meshLibrary/utilities/containers/LongList/LongListI.H index 76c5dcf2eaf3b4f8046c6ca8d6d3b0c544a4242c..a55dfb1d3e22bdc40640dfd255593e49ec179060 100644 --- a/meshLibrary/utilities/containers/LongList/LongListI.H +++ b/meshLibrary/utilities/containers/LongList/LongListI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -29,53 +28,53 @@ License template<class T, Foam::label Offset> void Foam::LongList<T, Offset>::checkIndex(const label i) const { - if( (i < 0) || (i >= nextFree_) ) - { - FatalErrorIn - ( - "void Foam::LongList<T, label, Offset>::" - "checkIndex(const label i) const" - ) << "Index " << Foam::label(i) << " is not in range " << Foam::label(0) - << " and " << Foam::label(nextFree_) << abort(FatalError); - } + if( (i < 0) || (i >= nextFree_) ) + { + FatalErrorIn + ( + "void Foam::LongList<T, label, Offset>::" + "checkIndex(const label i) const" + ) << "Index " << Foam::label(i) << " is not in range " << Foam::label(0) + << " and " << Foam::label(nextFree_) << abort(FatalError); + } } template<class T, Foam::label Offset> void Foam::LongList<T, Offset>::initializeParameters() { - unsigned int t = sizeof(T); - label it(0); + unsigned int t = sizeof(T); + label it(0); - while( t > 1 ) - { - t >>= 1; - ++it; - } + while( t > 1 ) + { + t >>= 1; + ++it; + } - shift_ = Foam::max(10, Offset - it); + shift_ = Foam::max(10, Offset - it); mask_ = 1<<shift_; - mask_ -= 1; + mask_ -= 1; } template<class T, Foam::label Offset> inline void Foam::LongList<T, Offset>::allocateSize(const label s) { - if( s == 0 ) - { - clearOut(); - return; - } + if( s == 0 ) + { + clearOut(); + return; + } - const label numblock1 = ((s-1)>>shift_) + 1; + const label numblock1 = ((s-1)>>shift_) + 1; const label blockSize = 1<<shift_; - if( numblock1 < numBlocks_ ) - { - for(register label i=numblock1;i<numBlocks_;++i) - delete [] dataPtr_[i]; - } - else if( numblock1 > numBlocks_ ) - { + if( numblock1 < numBlocks_ ) + { + for(register label i=numblock1;i<numBlocks_;++i) + delete [] dataPtr_[i]; + } + else if( numblock1 > numBlocks_ ) + { if( numblock1 >= numAllocatedBlocks_ ) { do @@ -92,30 +91,30 @@ inline void Foam::LongList<T, Offset>::allocateSize(const label s) dataPtr_ = dataptr1; } - for(register label i=numBlocks_;i<numblock1;++i) - dataPtr_[i] = new T[blockSize]; - } - - numBlocks_ = numblock1; - N_ = numBlocks_ * blockSize; + for(register label i=numBlocks_;i<numblock1;++i) + dataPtr_[i] = new T[blockSize]; + } + + numBlocks_ = numblock1; + N_ = numBlocks_ * blockSize; } template<class T, Foam::label Offset> void Foam::LongList<T, Offset>::clearOut() { - for(register label i=0;i<numBlocks_;++i) - delete [] dataPtr_[i]; - - if( dataPtr_ ) - { - delete [] dataPtr_; - dataPtr_ = NULL; - } - - N_ = 0; - numBlocks_ = 0; + for(register label i=0;i<numBlocks_;++i) + delete [] dataPtr_[i]; + + if( dataPtr_ ) + { + delete [] dataPtr_; + dataPtr_ = NULL; + } + + N_ = 0; + numBlocks_ = 0; numAllocatedBlocks_ = 0; - nextFree_ = 0; + nextFree_ = 0; } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -124,31 +123,31 @@ void Foam::LongList<T, Offset>::clearOut() template<class T, Foam::label Offset> inline Foam::LongList<T, Offset>::LongList() : - N_(0), - nextFree_(0), - numBlocks_(0), + N_(0), + nextFree_(0), + numBlocks_(0), numAllocatedBlocks_(0), - shift_(), - mask_(), - dataPtr_(NULL) + shift_(), + mask_(), + dataPtr_(NULL) { - initializeParameters(); + initializeParameters(); } //- Construct given size template<class T, Foam::label Offset> inline Foam::LongList<T, Offset>::LongList(const label s) : - N_(0), - nextFree_(0), - numBlocks_(0), + N_(0), + nextFree_(0), + numBlocks_(0), numAllocatedBlocks_(0), - shift_(), - mask_(), - dataPtr_(NULL) + shift_(), + mask_(), + dataPtr_(NULL) { - initializeParameters(); - setSize(s); + initializeParameters(); + setSize(s); } @@ -156,37 +155,37 @@ inline Foam::LongList<T, Offset>::LongList(const label s) template<class T, Foam::label Offset> inline Foam::LongList<T, Offset>::LongList(const label s, const T& t) : - N_(0), - nextFree_(0), - numBlocks_(0), + N_(0), + nextFree_(0), + numBlocks_(0), numAllocatedBlocks_(0), - shift_(), - mask_(), - dataPtr_(NULL) + shift_(), + mask_(), + dataPtr_(NULL) { - initializeParameters(); - setSize(s); - *this = t; + initializeParameters(); + setSize(s); + *this = t; } template<class T, Foam::label Offset> inline Foam::LongList<T, Offset>::LongList(const LongList<T, Offset>& ol) : - N_(0), - nextFree_(0), - numBlocks_(0), + N_(0), + nextFree_(0), + numBlocks_(0), numAllocatedBlocks_(0), - shift_(ol.shift_), - mask_(ol.mask_), - dataPtr_(NULL) + shift_(ol.shift_), + mask_(ol.mask_), + dataPtr_(NULL) { - *this = ol; + *this = ol; } template<class T, Foam::label Offset> inline Foam::LongList<T, Offset>::~LongList() { - clearOut(); + clearOut(); } // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // @@ -214,8 +213,8 @@ inline Foam::label Foam::LongList<T, Offset>::byteSize() const template<class T, Foam::label Offset> inline void Foam::LongList<T, Offset>::setSize(const label i) { - allocateSize(i); - nextFree_ = i; + allocateSize(i); + nextFree_ = i; } template<class T, Foam::label Offset> @@ -236,19 +235,19 @@ Foam::LongList<T, Offset>::shrink() template<class T, Foam::label Offset> inline void Foam::LongList<T, Offset>::transfer(LongList<T, Offset>& ol) { - clearOut(); - dataPtr_ = ol.dataPtr_; - N_ = ol.N_; - nextFree_ = ol.nextFree_; - numBlocks_ = ol.numBlocks_; + clearOut(); + dataPtr_ = ol.dataPtr_; + N_ = ol.N_; + nextFree_ = ol.nextFree_; + numBlocks_ = ol.numBlocks_; numAllocatedBlocks_ = ol.numAllocatedBlocks_; - shift_ = ol.shift_; - mask_ = ol.mask_; - - ol.dataPtr_ = NULL; - ol.N_ = 0; - ol.nextFree_ = 0; - ol.numBlocks_ = 0; + shift_ = ol.shift_; + mask_ = ol.mask_; + + ol.dataPtr_ = NULL; + ol.N_ = 0; + ol.nextFree_ = 0; + ol.numBlocks_ = 0; ol.numAllocatedBlocks_ = 0; } @@ -256,29 +255,29 @@ inline void Foam::LongList<T, Offset>::transfer(LongList<T, Offset>& ol) template<class T, Foam::label Offset> inline void Foam::LongList<T, Offset>::append(const T& e) { - if( nextFree_ >= N_ ) + if( nextFree_ >= N_ ) { - allocateSize(nextFree_+1); + allocateSize(nextFree_+1); } - - operator[](nextFree_++) = e; + + operator[](nextFree_++) = e; } template<class T, Foam::label Offset> inline void Foam::LongList<T, Offset>::appendIfNotIn(const T& e) { - if( !contains(e) ) - append(e); + if( !contains(e) ) + append(e); } template<class T, Foam::label Offset> inline bool Foam::LongList<T, Offset>::contains(const T& e) const { - for(register label i=0;i<nextFree_;++i) - if( (*this)[i] == e ) - return true; - - return false; + for(register label i=0;i<nextFree_;++i) + if( (*this)[i] == e ) + return true; + + return false; } template<class T, Foam::label Offset> @@ -287,11 +286,11 @@ inline Foam::label Foam::LongList<T, Offset>::containsAtPosition const T& e ) const { - for(register label i=0;i<nextFree_;++i) - if( (*this)[i] == e ) - return i; - - return -1; + for(register label i=0;i<nextFree_;++i) + if( (*this)[i] == e ) + return i; + + return -1; } template<class T, Foam::label Offset> @@ -304,9 +303,9 @@ inline T Foam::LongList<T, Offset>::remove(const label i) "void Foam::LongList<T, Offset>::remove()" ) << "List is empty" << abort(FatalError); } - + T el = operator[](i); - operator[](i) = operator[](nextFree_-1); + operator[](i) = operator[](nextFree_-1); --nextFree_; return el; } @@ -333,28 +332,28 @@ inline T Foam::LongList<T, Offset>::removeLastElement() template<class T, Foam::label Offset> inline const T& Foam::LongList<T, Offset>::operator[](const label i) const { - #ifdef FULLDEBUG - checkIndex(i); - #endif - - return dataPtr_[i>>shift_][i&mask_]; + #ifdef FULLDEBUG + checkIndex(i); + #endif + + return dataPtr_[i>>shift_][i&mask_]; } template<class T, Foam::label Offset> inline T& Foam::LongList<T, Offset>::operator[](const label i) { - #ifdef FULLDEBUG - checkIndex(i); - #endif - - return dataPtr_[i>>shift_][i&mask_]; + #ifdef FULLDEBUG + checkIndex(i); + #endif + + return dataPtr_[i>>shift_][i&mask_]; } template<class T, Foam::label Offset> inline T& Foam::LongList<T, Offset>::operator()(const label i) { if( i >= nextFree_ ) - setSize(i+1); + setSize(i+1); return operator[](i); } @@ -363,22 +362,22 @@ inline T& Foam::LongList<T, Offset>::operator()(const label i) template<class T, Foam::label Offset> inline T& Foam::LongList<T, Offset>::newElmt(const label i) { - return operator()(i); + return operator()(i); } template<class T, Foam::label Offset> inline void Foam::LongList<T, Offset>::operator=(const T& t) { for(register label i=0;i<nextFree_;++i) - operator[](i) = t; + operator[](i) = t; } template<class T, Foam::label Offset> inline void Foam::LongList<T, Offset>::operator=(const LongList<T, Offset>& l) { - setSize(l.size()); - for(register label i=0;i<l.nextFree_;++i) - operator[](i) = l[i]; + setSize(l.size()); + for(register label i=0;i<l.nextFree_;++i) + operator[](i) = l[i]; } diff --git a/meshLibrary/utilities/containers/VRWGraph/VRWGraph.C b/meshLibrary/utilities/containers/VRWGraph/VRWGraph.C index b8da9352c0f7c0a705d637548041f1964ec3caf8..b3b46a812252c61238bf1f6872a5b09b0d90aba1 100644 --- a/meshLibrary/utilities/containers/VRWGraph/VRWGraph.C +++ b/meshLibrary/utilities/containers/VRWGraph/VRWGraph.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -36,22 +35,22 @@ Foam::Ostream& Foam::operator<< const Foam::VRWGraph& DL ) { - os << DL.size() << nl << token::BEGIN_LIST; - - for(register label i=0;i<DL.size();++i) - { - os << nl << DL.sizeOfRow(i) << token::BEGIN_LIST; - for(label j=0;j<DL.sizeOfRow(i);++j) - { - if( j > 0 ) os << token::SPACE; - - os << DL(i, j); - } - - os << token::END_LIST; - } - - os << nl << token::END_LIST; + os << DL.size() << nl << token::BEGIN_LIST; + + for(register label i=0;i<DL.size();++i) + { + os << nl << DL.sizeOfRow(i) << token::BEGIN_LIST; + for(label j=0;j<DL.sizeOfRow(i);++j) + { + if( j > 0 ) os << token::SPACE; + + os << DL(i, j); + } + + os << token::END_LIST; + } + + os << nl << token::END_LIST; return os; } @@ -63,15 +62,15 @@ Foam::Istream& Foam::operator>> Foam::VRWGraph<T, width>& DL ) { - label size; - T e; - is >> size; - DL.setSize(size); - for(IndexType i=0;i<size;++i) - { - is >> e; - DL[i] = e; - } + label size; + T e; + is >> size; + DL.setSize(size); + for(IndexType i=0;i<size;++i) + { + is >> e; + DL[i] = e; + } return is; } @@ -79,31 +78,31 @@ Foam::Istream& Foam::operator>> void Foam::VRWGraph::optimizeMemoryUsage() { - labelListPMG newPosForNode(data_.size()); - label pos(0), nElements; - nElements = data_.size(); - for(label elI=0;elI<nElements;++elI) - if( data_[elI] != FREEENTRY ) - { - newPosForNode[elI] = pos++; - } - else - { - newPosForNode[elI] = -1; - } - - //- create new data - for(label elI=0;elI<nElements;++elI) - if( (newPosForNode[elI] != -1) && (newPosForNode[elI] < elI) ) - data_[newPosForNode[elI]] = data_[elI]; - - data_.setSize(pos); - - //- renumber rows - nElements = rows_.size(); - for(label rowI=0;rowI<nElements;++rowI) - if( rows_[rowI].start() != INVALIDROW ) - rows_[rowI].start() = newPosForNode[rows_[rowI].start()]; + labelLongList newPosForNode(data_.size()); + label pos(0), nElements; + nElements = data_.size(); + for(label elI=0;elI<nElements;++elI) + if( data_[elI] != FREEENTRY ) + { + newPosForNode[elI] = pos++; + } + else + { + newPosForNode[elI] = -1; + } + + //- create new data + for(label elI=0;elI<nElements;++elI) + if( (newPosForNode[elI] != -1) && (newPosForNode[elI] < elI) ) + data_[newPosForNode[elI]] = data_[elI]; + + data_.setSize(pos); + + //- renumber rows + nElements = rows_.size(); + for(label rowI=0;rowI<nElements;++rowI) + if( rows_[rowI].start() != INVALIDROW ) + rows_[rowI].start() = newPosForNode[rows_[rowI].start()]; } // ************************************************************************* // diff --git a/meshLibrary/utilities/containers/VRWGraph/VRWGraph.H b/meshLibrary/utilities/containers/VRWGraph/VRWGraph.H index 506cc9c2998e6efdf0a0126f59d8507679a565d1..d0c311c9ab0e3a9fa39fb77692e24b88b7719603 100644 --- a/meshLibrary/utilities/containers/VRWGraph/VRWGraph.H +++ b/meshLibrary/utilities/containers/VRWGraph/VRWGraph.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class VRWGraph Description This class is an implementation of a graph with variable column width. - The imoplementation is memory efficient. + The imoplementation is memory efficient. SourceFiles VRWGraphI.H @@ -38,7 +37,7 @@ SourceFiles #ifndef VRWGraph_H #define VRWGraph_H -#include "labelListPMG.H" +#include "labelLongList.H" #include "graphRow.H" #include "DynList.H" #include "bool.H" @@ -48,49 +47,49 @@ SourceFiles namespace Foam { - + class VRWGraphModifier; - + class rowElement { - // Private data - label start_; - label size_; - - public: - - inline rowElement() - : - start_(), - size_() - {} - - inline rowElement(const label i, const label j) - : - start_(i), - size_(j) - {} - - inline ~rowElement() - {} - - inline label start() const - { - return start_; - } - inline label& start() - { - return start_; - } - - inline label size() const - { - return size_; - } - inline label& size() - { - return size_; - } + // Private data + label start_; + label size_; + + public: + + inline rowElement() + : + start_(), + size_() + {} + + inline rowElement(const label i, const label j) + : + start_(i), + size_(j) + {} + + inline ~rowElement() + {} + + inline label start() const + { + return start_; + } + inline label& start() + { + return start_; + } + + inline label size() const + { + return size_; + } + inline label& size() + { + return size_; + } }; /*---------------------------------------------------------------------------*\ @@ -100,30 +99,30 @@ class rowElement class VRWGraph { // Private data - //- list containing the data - labelListPMG data_; - - //- number of rows - LongList<rowElement> rows_; - - // Private member functions - //- check index - inline void checkIndex(const label i, const label j) const; - - // Enumerators - enum typeOfEntries - { - NONE = 0, - INVALIDROW=-10, - FREEENTRY=-11, - FREESTART=-12 - }; - + //- list containing the data + labelLongList data_; + + //- number of rows + LongList<rowElement> rows_; + + // Private member functions + //- check index + inline void checkIndex(const label i, const label j) const; + + // Enumerators + enum typeOfEntries + { + NONE = 0, + INVALIDROW=-10, + FREEENTRY=-11, + FREESTART=-12 + }; + public: - - // Friend classes + + // Friend classes - friend class VRWGraphSMPModifier; + friend class VRWGraphSMPModifier; // Constructors @@ -135,25 +134,25 @@ public: //- Construct given number of rows and row size explicit inline VRWGraph - ( - const label nRows, - const label nColumnsInRow + ( + const label nRows, + const label nColumnsInRow ); - //- Construct to given number of rows, row size and initialize - explicit inline VRWGraph - ( - const label nRows, - const label nColumnsInRow, - const label t - ); + //- Construct to given number of rows, row size and initialize + explicit inline VRWGraph + ( + const label nRows, + const label nColumnsInRow, + const label t + ); //- Copy contructor - inline VRWGraph(const VRWGraph&); + inline VRWGraph(const VRWGraph&); - // Destructor + // Destructor - inline ~VRWGraph(); + inline ~VRWGraph(); // Member Functions @@ -161,18 +160,18 @@ public: //- Returns the number of rows inline label size() const; - - //- Returns the number of elements in the given row - inline label sizeOfRow(const label rowI) const; + + //- Returns the number of elements in the given row + inline label sizeOfRow(const label rowI) const; // Edit //- Reset the number of rows inline void setSize(const label); - - //- Reset the number of rows. The second argument specifies - //- the reserved column width - inline void setSizeAndColumnWidth + + //- Reset the number of rows. The second argument specifies + //- the reserved column width + inline void setSizeAndColumnWidth ( const label newNumRows, const label rcWidth @@ -181,9 +180,9 @@ public: //- Set the number of rows and the size of each row template<class ListType> inline void setSizeAndRowSize(const ListType&); - - //- Reset the size of the given row - inline void setRowSize(const label rowI, const label newSize); + + //- Reset the size of the given row + inline void setRowSize(const label rowI, const label newSize); //- Clear the graph inline void clear(); @@ -191,18 +190,18 @@ public: // Member Operators //- Append a list as a row at the end of the graph - template<class ListType> + template<class ListType> inline void appendList(const ListType& l); - - //- Append an element to the given row - inline void append(const label rowI, const label); - - //- Append an element to the given row if it does not exist there - inline void appendIfNotIn(const label rowI, const label); - - //- Set row with the list - template<class ListType> - inline void setRow(const label rowI, const ListType& l); + + //- Append an element to the given row + inline void append(const label rowI, const label); + + //- Append an element to the given row if it does not exist there + inline void appendIfNotIn(const label rowI, const label); + + //- Set row with the list + template<class ListType> + inline void setRow(const label rowI, const ListType& l); //- merge graphs with the identical number of rows //- into a single one. Use for SMP parallelisation @@ -228,24 +227,24 @@ public: ); inline void reverseAddressing(const VRWGraph& origGraph); - - //- optimize memory usage - // this should be used once the graph will not be resized any more - void optimizeMemoryUsage(); - - //- check if the element is in the given row (takes linear time) - inline bool contains(const label rowI, const label e) const; - inline label containsAtPosition(const label rowI, const label e) const; - - //- get and set operators - inline label operator()(const label i, const label j) const; - inline label& operator()(const label i, const label j); - - inline constRow operator[](const label i) const; - inline row operator[](const label i); - - //- Assignment operator - inline void operator=(const VRWGraph&); + + //- optimize memory usage + // this should be used once the graph will not be resized any more + void optimizeMemoryUsage(); + + //- check if the element is in the given row (takes linear time) + inline bool contains(const label rowI, const label e) const; + inline label containsAtPosition(const label rowI, const label e) const; + + //- get and set operators + inline label operator()(const label i, const label j) const; + inline label& operator()(const label i, const label j); + + inline constRow operator[](const label i) const; + inline row operator[](const label i); + + //- Assignment operator + inline void operator=(const VRWGraph&); // IOstream operators @@ -274,7 +273,7 @@ public: // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // #define forAllRow(graph, rowI, index) \ - for(Foam::label index=0;index<(graph).sizeOfRow(rowI);++index) + for(Foam::label index=0;index<(graph).sizeOfRow(rowI);++index) // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/VRWGraph/VRWGraphI.H b/meshLibrary/utilities/containers/VRWGraph/VRWGraphI.H index 9bfc9ec2daadf23a26a63be67f28adc22b9d0479..b25e4659b60554699f7b1a169097492f3f37c602 100644 --- a/meshLibrary/utilities/containers/VRWGraph/VRWGraphI.H +++ b/meshLibrary/utilities/containers/VRWGraph/VRWGraphI.H @@ -1,50 +1,49 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ inline void Foam::VRWGraph::checkIndex(const label i, const label j) const { - if( (i < 0) || (i >= rows_.size()) ) - { - FatalErrorIn - ( - "void Foam::VRWGraph<T,width>::" - "checkIndex(const label i, const label j) const" - ) << "Row index " << Foam::label(i) - << " is not in range " << Foam::label(0) - << " and " << rows_.size() << abort(FatalError); - } - - if( (j < 0) || (j >= rows_[i].size()) ) - FatalErrorIn - ( - "void Foam::VRWGraph<T,width>::" - "checkIndex(label const i) const" - ) << "Column index " << Foam::label(j) - << " is not in range " << Foam::label(0) - << " and " << rows_[i].size() << abort(FatalError); + if( (i < 0) || (i >= rows_.size()) ) + { + FatalErrorIn + ( + "void Foam::VRWGraph<T,width>::" + "checkIndex(const label i, const label j) const" + ) << "Row index " << Foam::label(i) + << " is not in range " << Foam::label(0) + << " and " << rows_.size() << abort(FatalError); + } + + if( (j < 0) || (j >= rows_[i].size()) ) + FatalErrorIn + ( + "void Foam::VRWGraph<T,width>::" + "checkIndex(label const i) const" + ) << "Column index " << Foam::label(j) + << " is not in range " << Foam::label(0) + << " and " << rows_[i].size() << abort(FatalError); } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -52,8 +51,8 @@ inline void Foam::VRWGraph::checkIndex(const label i, const label j) const //- Construct null inline Foam::VRWGraph::VRWGraph() : - data_(), - rows_() + data_(), + rows_() { } @@ -63,14 +62,14 @@ inline Foam::VRWGraph::VRWGraph const label size ) : - data_(), - rows_(size) + data_(), + rows_(size) { - for(label rowI=0;rowI<size;++rowI) - { - rows_[rowI].start() = INVALIDROW; - rows_[rowI].size() = NONE; - } + for(label rowI=0;rowI<size;++rowI) + { + rows_[rowI].start() = INVALIDROW; + rows_[rowI].size() = NONE; + } } inline Foam::VRWGraph::VRWGraph @@ -80,39 +79,39 @@ inline Foam::VRWGraph::VRWGraph ) : data_(nRows * nColumnsInRow), - rows_(nRows) + rows_(nRows) { for(label rowI=0;rowI<nRows;++rowI) - { - rows_[rowI].start() = rowI*nColumnsInRow; - rows_[rowI].size() = nColumnsInRow; - } + { + rows_[rowI].start() = rowI*nColumnsInRow; + rows_[rowI].size() = nColumnsInRow; + } } inline Foam::VRWGraph::VRWGraph ( const label nRows, - const label nColumnsInRow, - const label t + const label nColumnsInRow, + const label t ) : - data_(nRows * nColumnsInRow, t), - rows_(nRows) + data_(nRows * nColumnsInRow, t), + rows_(nRows) { - for(label rowI=0;rowI<nRows;++rowI) - { - rows_[rowI].start() = rowI*nColumnsInRow; - rows_[rowI].size() = nColumnsInRow; - } + for(label rowI=0;rowI<nRows;++rowI) + { + rows_[rowI].start() = rowI*nColumnsInRow; + rows_[rowI].size() = nColumnsInRow; + } } inline Foam::VRWGraph::VRWGraph ( - const VRWGraph& ol + const VRWGraph& ol ) : - data_(ol.data_), - rows_(ol.rows_) + data_(ol.data_), + rows_(ol.rows_) { } @@ -130,52 +129,52 @@ inline Foam::label Foam::VRWGraph::size() const inline Foam::label Foam::VRWGraph::sizeOfRow(const label rowI) const { - return rows_[rowI].size(); + return rows_[rowI].size(); } inline void Foam::VRWGraph::setSize(const label size) { - if( size > rows_.size() ) - { - rowElement rowInfo(INVALIDROW, NONE); - - for(label i=rows_.size();i<size;++i) - rows_.append(rowInfo); - } - else - { - rows_.setSize(size); - } + if( size > rows_.size() ) + { + rowElement rowInfo(INVALIDROW, NONE); + + for(label i=rows_.size();i<size;++i) + rows_.append(rowInfo); + } + else + { + rows_.setSize(size); + } } void Foam::VRWGraph::setSizeAndColumnWidth ( - const label newNumRows, - const label rcWidth + const label newNumRows, + const label rcWidth ) { - if( rows_.size() != 0 ) - FatalErrorIn - ( - "void Foam::VRWGraph::setSizeAndColumnWidth" - "(const label size, const label rcWidth)" - ) << "This function should be used for empty graphs, only!" - << exit(FatalError); - - data_.setSize(newNumRows * rcWidth); - data_ = FREEENTRY; - - rows_.setSize(newNumRows); - label start(0); - - for(label i=0;i<newNumRows;++i) - { - rows_[i].start() = start; - rows_[i].size() = 0; - data_[start] = FREESTART; - - start += rcWidth; - } + if( rows_.size() != 0 ) + FatalErrorIn + ( + "void Foam::VRWGraph::setSizeAndColumnWidth" + "(const label size, const label rcWidth)" + ) << "This function should be used for empty graphs, only!" + << exit(FatalError); + + data_.setSize(newNumRows * rcWidth); + data_ = FREEENTRY; + + rows_.setSize(newNumRows); + label start(0); + + for(label i=0;i<newNumRows;++i) + { + rows_[i].start() = start; + rows_[i].size() = 0; + data_[start] = FREESTART; + + start += rcWidth; + } } template<class ListType> @@ -207,88 +206,88 @@ inline void Foam::VRWGraph::setSizeAndRowSize(const ListType& l) inline void Foam::VRWGraph::setRowSize(const label rowI, const label newSize) { - # ifdef FULLDEBUG - if( (rowI < 0) || (rowI >= rows_.size()) ) - FatalErrorIn - ( - "void Foam::VRWGraph<T,width>::" - "checkIndex(const label rowI, const label size) const" - ) << "Row index " << Foam::label(rowI) - << " is not in range " << Foam::label(0) - << " and " << rows_.size() << abort(FatalError); - # endif - - const label start = rows_[rowI].start(); - if( start == INVALIDROW ) - { - if( newSize > 0 ) - { - rows_[rowI].start() = data_.size(); - for(label i=0;i<newSize;++i) - data_.append(NONE); - rows_[rowI].size() = newSize; - } - } - else if( newSize > rows_[rowI].size() ) - { - //- check if there is some unused space after the last element - bool foundUnused(true); - - for(label i=rows_[rowI].size();i<newSize;++i) - { - const label j = start + i; - if( - (j >= data_.size()) || - (data_[j] != FREEENTRY) || - (data_[j] == FREESTART) - ) - { - foundUnused = false; - break; - } - } - - if( foundUnused ) - { - //- row can be extended without copying - for(label i=rows_[rowI].size();i<newSize;++i) - data_[start+i] = NONE; - } - else - { - //- row is copied at the end of the data list - rows_[rowI].start() = data_.size(); - for(label i=0;i<rows_[rowI].size();++i) - { - data_.append(data_[start+i]); - data_[start+i] = FREEENTRY; - } - for(label i=rows_[rowI].size();i<newSize;++i) - data_.append(NONE); - } - - rows_[rowI].size() = newSize; - } - else if( newSize < rows_[rowI].size() ) - { - for(label i=newSize;i<rows_[rowI].size();++i) - data_[start+i] = FREEENTRY; - rows_[rowI].size() = newSize; - if( newSize == 0 ) - rows_[rowI].start() = INVALIDROW; - } + # ifdef FULLDEBUG + if( (rowI < 0) || (rowI >= rows_.size()) ) + FatalErrorIn + ( + "void Foam::VRWGraph<T,width>::" + "checkIndex(const label rowI, const label size) const" + ) << "Row index " << Foam::label(rowI) + << " is not in range " << Foam::label(0) + << " and " << rows_.size() << abort(FatalError); + # endif + + const label start = rows_[rowI].start(); + if( start == INVALIDROW ) + { + if( newSize > 0 ) + { + rows_[rowI].start() = data_.size(); + for(label i=0;i<newSize;++i) + data_.append(NONE); + rows_[rowI].size() = newSize; + } + } + else if( newSize > rows_[rowI].size() ) + { + //- check if there is some unused space after the last element + bool foundUnused(true); + + for(label i=rows_[rowI].size();i<newSize;++i) + { + const label j = start + i; + if( + (j >= data_.size()) || + (data_[j] != FREEENTRY) || + (data_[j] == FREESTART) + ) + { + foundUnused = false; + break; + } + } + + if( foundUnused ) + { + //- row can be extended without copying + for(label i=rows_[rowI].size();i<newSize;++i) + data_[start+i] = NONE; + } + else + { + //- row is copied at the end of the data list + rows_[rowI].start() = data_.size(); + for(label i=0;i<rows_[rowI].size();++i) + { + data_.append(data_[start+i]); + data_[start+i] = FREEENTRY; + } + for(label i=rows_[rowI].size();i<newSize;++i) + data_.append(NONE); + } + + rows_[rowI].size() = newSize; + } + else if( newSize < rows_[rowI].size() ) + { + for(label i=newSize;i<rows_[rowI].size();++i) + data_[start+i] = FREEENTRY; + rows_[rowI].size() = newSize; + if( newSize == 0 ) + rows_[rowI].start() = INVALIDROW; + } } inline void Foam::VRWGraph::clear() { data_.setSize(0); - rows_.setSize(0); + rows_.setSize(0); } template<class ListType> inline void Foam::VRWGraph::appendList ( - const ListType& l + const ListType& l ) { if( l.size() == 0 ) @@ -297,16 +296,16 @@ inline void Foam::VRWGraph::appendList return; } - rowElement rowInfo(data_.size(), l.size()); - const label size = l.size(); - for(label elI=0;elI<size;++elI) - data_.append(l[elI]); - rows_.append(rowInfo); + rowElement rowInfo(data_.size(), l.size()); + const label size = l.size(); + for(label elI=0;elI<size;++elI) + data_.append(l[elI]); + rows_.append(rowInfo); } inline void Foam::VRWGraph::append(const label rowI, const label el) { - rowElement& re = rows_[rowI]; + rowElement& re = rows_[rowI]; if( re.start() == INVALIDROW ) { @@ -315,11 +314,11 @@ inline void Foam::VRWGraph::append(const label rowI, const label el) data_.append(el); } else - { + { const label oldStart = re.start(); const label oldSize = re.size(); ++re.size(); - + if( oldStart + oldSize < data_.size() ) { if( @@ -349,22 +348,22 @@ inline void Foam::VRWGraph::append(const label rowI, const label el) inline void Foam::VRWGraph::appendIfNotIn(const label rowI, const label el) { - if( !contains(rowI, el) ) - append(rowI, el); + if( !contains(rowI, el) ) + append(rowI, el); } template<class ListType> inline void Foam::VRWGraph::setRow ( - const label rowI, - const ListType& l + const label rowI, + const ListType& l ) { - this->setRowSize(rowI, l.size()); - const label start = rows_[rowI].start(); - const label size = l.size(); - for(label elI=0;elI<size;++elI) - data_[start+elI] = l[elI]; + this->setRowSize(rowI, l.size()); + const label start = rows_[rowI].start(); + const label size = l.size(); + for(label elI=0;elI<size;++elI) + data_[start+elI] = l[elI]; } inline void Foam::VRWGraph::mergeGraphs(const List<VRWGraph>& graphParts) @@ -381,7 +380,7 @@ inline void Foam::VRWGraph::mergeGraphs(const List<VRWGraph>& graphParts) } //- find the number of elements in each row - labelListPMG nElmtsInRow(nRows); + labelLongList nElmtsInRow(nRows); for(label rowI=0;rowI<nRows;++rowI) { label sum(0); @@ -413,7 +412,7 @@ inline void Foam::VRWGraph::reverseAddressing ) { const label origSize = origGraph.size(); - labelListPMG nElmtsInRow(nRows); + labelLongList nElmtsInRow(nRows); for(label rowI=0;rowI<nRows;++rowI) nElmtsInRow[rowI] = 0; @@ -466,7 +465,7 @@ inline void Foam::VRWGraph::reverseAddressing ) { const label origSize = origGraph.size(); - labelListPMG nElmtsInRow(nRows); + labelLongList nElmtsInRow(nRows); for(label rowI=0;rowI<nRows;++rowI) nElmtsInRow[rowI] = 0; @@ -513,85 +512,85 @@ inline void Foam::VRWGraph::reverseAddressing(const VRWGraph& origGraph) inline bool Foam::VRWGraph::contains ( - const label rowI, + const label rowI, const label e ) const { - const label start = rows_[rowI].start(); - if( start == INVALIDROW ) - return false; - const label size = rows_[rowI].size(); - - for(register label i=0;i<size;++i) - if( data_[start+i] == e ) - return true; - - return false; + const label start = rows_[rowI].start(); + if( start == INVALIDROW ) + return false; + const label size = rows_[rowI].size(); + + for(register label i=0;i<size;++i) + if( data_[start+i] == e ) + return true; + + return false; } inline Foam::label Foam::VRWGraph::containsAtPosition ( - const label rowI, + const label rowI, const label e ) const { - const label start = rows_[rowI].start(); - if( start == INVALIDROW ) - return -1; - - const label size = rows_[rowI].size(); - for(register label i=0;i<size;++i) - if( data_[start+i] == e ) - return i; - - return -1; + const label start = rows_[rowI].start(); + if( start == INVALIDROW ) + return -1; + + const label size = rows_[rowI].size(); + for(register label i=0;i<size;++i) + if( data_[start+i] == e ) + return i; + + return -1; } // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * // inline Foam::label Foam::VRWGraph::operator() ( - const label i, - const label j + const label i, + const label j ) const { - #ifdef FULLDEBUG - checkIndex(i, j); - #endif - - return data_[rows_[i].start() + j]; + #ifdef FULLDEBUG + checkIndex(i, j); + #endif + + return data_[rows_[i].start() + j]; } inline Foam::label& Foam::VRWGraph::operator() ( - const label i, const label j + const label i, const label j ) { - #ifdef FULLDEBUG - checkIndex(i, j); - #endif - - return data_[rows_[i].start() + j]; + #ifdef FULLDEBUG + checkIndex(i, j); + #endif + + return data_[rows_[i].start() + j]; } inline Foam::constRow Foam::VRWGraph::operator[](const label i) const { - return constRow(*this, i); + return constRow(*this, i); } inline Foam::row Foam::VRWGraph::operator[](const label i) { - return row(*this, i); + return row(*this, i); } inline void Foam::VRWGraph::operator= ( - const VRWGraph& l + const VRWGraph& l ) { - data_ = l.data_; - rows_ = l.rows_; + data_ = l.data_; + rows_ = l.rows_; } diff --git a/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.C b/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.C index 199a8a15e9e0b4537b36ba68676958aa5f279fd3..bf17d7d3cad025f7c4a28ea8541d6883d67feeb5 100644 --- a/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.C +++ b/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.C @@ -1,39 +1,40 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "VRWGraphSMPModifier.H" #include "labelPair.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // VRWGraphSMPModifier::VRWGraphSMPModifier(VRWGraph& graph) @@ -43,12 +44,12 @@ VRWGraphSMPModifier::VRWGraphSMPModifier(VRWGraph& graph) VRWGraphSMPModifier::~VRWGraphSMPModifier() {} - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void VRWGraphSMPModifier::mergeGraphs(const List<VRWGraph>& graphParts) { - const label nGraphs = graphParts.size(); + const label nGraphs = graphParts.size(); const label nRows = graphParts[0].size(); forAll(graphParts, i) { @@ -58,25 +59,29 @@ void VRWGraphSMPModifier::mergeGraphs(const List<VRWGraph>& graphParts) "inline void Foam::VRWGraph::mergeGraphs(const List<VRWGraph>&)" ) << "Cannot merge graphs" << abort(FatalError); } - + //- find the number of elements in each row - labelListPMG nElmtsInRow(nRows); - + labelLongList nElmtsInRow(nRows); + + # ifdef USE_OMP # pragma omp parallel for schedule(static, 1) + # endif for(label rowI=0;rowI<nRows;++rowI) { label sum(0); for(label i=0;i<nGraphs;++i) sum += graphParts[i].sizeOfRow(rowI); - + nElmtsInRow[rowI] = sum; } - + //- set the size of graph setSizeAndRowSize(nElmtsInRow); - + //- Finally, assemble the merged graph + # ifdef USE_OMP # pragma omp parallel for schedule(static, 1) + # endif for(label rowI=0;rowI<nRows;++rowI) { forAll(graphParts, i) @@ -87,30 +92,42 @@ void VRWGraphSMPModifier::mergeGraphs(const List<VRWGraph>& graphParts) } } } - + void VRWGraphSMPModifier::reverseAddressing(const VRWGraph& origGraph) { graph_.setSize(0); - labelListPMG nAppearances; - + labelLongList nAppearances; + + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( origGraph.size() < 1000 ) nThreads = 1; - + # else + const label nThreads(1); + # endif + label minRow(INT_MAX), maxRow(-1); List<List<LongList<labelPair> > > dataForOtherThreads(nThreads); - + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); - + # else + const label threadI(0); + # endif + List<LongList<labelPair> >& dot = dataForOtherThreads[threadI]; dot.setSize(nThreads); - + //- find min and max entry in the graph //- they are used for assigning ranges of values local for each process label localMinRow(INT_MAX), localMaxRow(-1); + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAllRow(origGraph, rowI, i) @@ -120,40 +137,50 @@ void VRWGraphSMPModifier::reverseAddressing(const VRWGraph& origGraph) localMinRow = Foam::min(localMinRow, entryI); } } - + ++localMaxRow; - + + # ifdef USE_OMP # pragma omp critical + # endif { minRow = Foam::min(minRow, localMinRow); maxRow = Foam::max(maxRow, localMaxRow); nAppearances.setSize(maxRow); } - + + # ifdef USE_OMP # pragma omp barrier - + # endif + //- initialise appearances + # ifdef USE_OMP # pragma omp for schedule(static) + # endif for(label i=0;i<maxRow;++i) nAppearances[i] = 0; - + + # ifdef USE_OMP # pragma omp barrier + # endif const label range = (maxRow - minRow) / nThreads + 1; const label localMin = minRow + threadI * range; const label localMax = Foam::min(localMin + range, maxRow); - + //- find the number of appearances of each element in the original graph + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAllRow(origGraph, rowI, j) { const label entryI = origGraph(rowI, j); - + const label threadNo = (entryI - minRow) / range; - + if( threadNo == threadI ) { ++nAppearances[entryI]; @@ -164,39 +191,47 @@ void VRWGraphSMPModifier::reverseAddressing(const VRWGraph& origGraph) } } } - + + # ifdef USE_OMP # pragma omp barrier + # endif //- count the appearances which are not local to the processor for(label i=0;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) ++nAppearances[data[j].first()]; } - + + # ifdef USE_OMP # pragma omp barrier + # endif //- allocate graph + # ifdef USE_OMP # pragma omp master + # endif setSizeAndRowSize(nAppearances); - + + # ifdef USE_OMP # pragma omp barrier - + # endif + for(label i=localMin;i<localMax;++i) { nAppearances[i] = 0; } - + //- start filling reverse addressing graph //- update data from processors with smaller labels for(label i=0;i<threadI;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); @@ -205,7 +240,9 @@ void VRWGraphSMPModifier::reverseAddressing(const VRWGraph& origGraph) } //- update data local to the processor + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAllRow(origGraph, rowI, j) @@ -216,13 +253,13 @@ void VRWGraphSMPModifier::reverseAddressing(const VRWGraph& origGraph) graph_(entryI, nAppearances[entryI]++) = rowI; } } - + //- update data from the processors with higher labels for(label i=threadI+1;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); @@ -234,54 +271,70 @@ void VRWGraphSMPModifier::reverseAddressing(const VRWGraph& origGraph) void VRWGraphSMPModifier::optimizeMemoryUsage() { + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( graph_.size() < 1000 ) nThreads = 1; - - DynList<label> nRows, nEntries; + # else + const label nThreads(1); + # endif + + DynList<label> nRows, nEntries; nRows.setSize(nThreads); nEntries.setSize(nThreads); - + LongList<rowElement> newRows; - labelListPMG newData; + labelLongList newData; + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif nRows[threadI] = 0; nEntries[threadI] = 0; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(graph_.rows_, rowI) { if( graph_.rows_[rowI].start() == VRWGraph::INVALIDROW ) continue; - + ++nRows[threadI]; nEntries[threadI] += graph_.rows_[rowI].size(); } - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif { //- find the number of rows label counter(0); forAll(nRows, i) counter += nRows[i]; - + newRows.setSize(counter); - + //- find the number of data entries counter = 0; forAll(nEntries, i) counter += nEntries[i]; - + newData.setSize(counter); } - + + # ifdef USE_OMP # pragma omp barrier - + # endif + //- find the starting position for each thread label rowStart(0), entryStart(0); for(label i=0;i<threadI;++i) @@ -289,15 +342,17 @@ void VRWGraphSMPModifier::optimizeMemoryUsage() rowStart += nRows[i]; entryStart += nEntries[i]; } - + //- copy the data into the location + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(graph_, rowI) { rowElement& el = newRows[rowStart]; el.start() += entryStart; ++rowStart; - + el.size() = graph_.sizeOfRow(rowI); forAllRow(graph_, rowI, i) { @@ -306,7 +361,7 @@ void VRWGraphSMPModifier::optimizeMemoryUsage() } } } - + //- replace the original data with the compressed data graph_.rows_.transfer(newRows); graph_.data_.transfer(newData); @@ -314,16 +369,22 @@ void VRWGraphSMPModifier::optimizeMemoryUsage() void VRWGraphSMPModifier::operator=(const VRWGraph& og) { - graph_.data_.setSize(og.data_.size()); + graph_.data_.setSize(og.data_.size()); graph_.rows_.setSize(og.rows_.size()); - + + # ifdef USE_OMP # pragma omp parallel + # endif { + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(graph_.data_, i) graph_.data_[i] = og.data_[i]; - + + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(graph_.rows_, rowI) graph_.rows_[rowI] = og.rows_[rowI]; } diff --git a/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.H b/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.H index cf7d60e913a2a7c2b92b3a5b2e05da063648662a..1ab7a83dfce08459153e26d1b5d8d12ec3deb895 100644 --- a/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.H +++ b/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifier.H @@ -1,34 +1,33 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class VRWGraphModifier Description This class is a modifier for VRWGraph which allows for multi-threaded - execution of most time-consuimg functions - + execution of most time-consuimg functions + SourceFiles VRWGraphSMPModifier.H VRWGraphSMPModifier.C @@ -65,7 +64,7 @@ class VRWGraphSMPModifier //- Disallow bitwise assignment void operator=(const VRWGraphSMPModifier&); - + public: // Constructor @@ -102,7 +101,7 @@ public: template<class ListType> void reverseAddressing(const ListType&, const VRWGraph&); - + //- optimize memory usage // this should be used once the graph will not be resized any more void optimizeMemoryUsage(); diff --git a/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifierTemplates.C b/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifierTemplates.C index 78fe0aeb6273a8d2f64bb979db7a2d116051f906..6f6b9578287b225f4ebe0fabc02f364709dc9cd3 100644 --- a/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifierTemplates.C +++ b/meshLibrary/utilities/containers/VRWGraph/VRWGraphSMPModifierTemplates.C @@ -1,33 +1,34 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "VRWGraphSMPModifier.H" #include "labelPair.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -39,42 +40,64 @@ namespace Foam template<class ListType> void VRWGraphSMPModifier::setSizeAndRowSize(const ListType& s) { - graph_.rows_.setSize(s.size()); - + graph_.rows_.setSize(s.size()); + + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( s.size() < 1000 ) nThreads = 1; - + # else + const label nThreads(1); + # endif + label nEntries(0); DynList<label> procEntries; procEntries.setSize(nThreads); - + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP label& nLocalEntries = procEntries[omp_get_thread_num()]; + # else + label& nLocalEntries = procEntries[0]; + # endif nLocalEntries = 0; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(s, i) nLocalEntries += s[i]; - + + # ifdef USE_OMP # pragma omp critical + # endif nEntries += nLocalEntries; - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif { graph_.data_.setSize(nEntries); } - + + # ifdef USE_OMP # pragma omp barrier - + # endif + label start(0); + # ifdef USE_OMP for(label i=0;i<omp_get_thread_num();++i) start += procEntries[i]; - + # endif + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(s, i) { graph_.rows_[i].start() = start; @@ -88,26 +111,38 @@ template<class GraphType> void VRWGraphSMPModifier::reverseAddressing(const GraphType& origGraph) { graph_.setSize(0); - labelListPMG nAppearances; - + labelLongList nAppearances; + + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( origGraph.size() < 1000 ) nThreads = 1; - + # else + const label nThreads(1); + # endif + label minRow(INT_MAX), maxRow(-1); List<List<LongList<labelPair> > > dataForOtherThreads(nThreads); - + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); - + # else + const label threadI(0); + # endif + List<LongList<labelPair> >& dot = dataForOtherThreads[threadI]; dot.setSize(nThreads); - + //- find min and max entry in the graph //- they are used for assigning ranges of values local for each process label localMinRow(INT_MAX), localMaxRow(-1); + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAll(origGraph[rowI], i) @@ -117,40 +152,48 @@ void VRWGraphSMPModifier::reverseAddressing(const GraphType& origGraph) localMinRow = Foam::min(localMinRow, entryI); } } - + ++localMaxRow; - + + # ifdef USE_OMP # pragma omp critical + # endif { minRow = Foam::min(minRow, localMinRow); maxRow = Foam::max(maxRow, localMaxRow); nAppearances.setSize(maxRow); } - + + # ifdef USE_OMP # pragma omp barrier - + //- initialise appearances # pragma omp for schedule(static) + # endif for(label i=0;i<maxRow;++i) nAppearances[i] = 0; - + + # ifdef USE_OMP # pragma omp barrier + # endif const label range = (maxRow - minRow) / nThreads + 1; const label localMin = minRow + threadI * range; const label localMax = Foam::min(localMin + range, maxRow); - + //- find the number of appearances of each element in the original graph + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAll(origGraph[rowI], j) { const label entryI = origGraph[rowI][j]; - + const label threadNo = (entryI - minRow) / range; - + if( threadNo == threadI ) { ++nAppearances[entryI]; @@ -161,39 +204,45 @@ void VRWGraphSMPModifier::reverseAddressing(const GraphType& origGraph) } } } - + + # ifdef USE_OMP # pragma omp barrier + # endif //- count the appearances which are not local to the processor for(label i=0;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) ++nAppearances[data[j].first()]; } - + + # ifdef USE_OMP # pragma omp barrier //- allocate graph # pragma omp master + # endif setSizeAndRowSize(nAppearances); - + + # ifdef USE_OMP # pragma omp barrier - + # endif + for(label i=localMin;i<localMax;++i) { nAppearances[i] = 0; } - + //- start filling reverse addressing graph //- update data from processors with smaller labels for(label i=0;i<threadI;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); @@ -202,7 +251,9 @@ void VRWGraphSMPModifier::reverseAddressing(const GraphType& origGraph) } //- update data local to the processor + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAll(origGraph[rowI], j) @@ -213,13 +264,13 @@ void VRWGraphSMPModifier::reverseAddressing(const GraphType& origGraph) graph_(entryI, nAppearances[entryI]++) = rowI; } } - + //- update data from the processors with higher labels for(label i=threadI+1;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); @@ -237,25 +288,37 @@ void VRWGraphSMPModifier::reverseAddressing ) { ListType nAppearances; - + + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( origGraph.size() < 1000 ) nThreads = 1; - + # else + const label nThreads(1); + # endif + label minRow(INT_MAX), maxRow(-1); List<List<LongList<labelPair> > > dataForOtherThreads(nThreads); - + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); - + # else + const label threadI(0); + # endif + List<LongList<labelPair> >& dot = dataForOtherThreads[threadI]; dot.setSize(nThreads); - + //- find min and max entry in the graph //- they are used for assigning ranges of values local for each process label localMinRow(INT_MAX), localMaxRow(-1); + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAll(origGraph[rowI], i) @@ -265,39 +328,47 @@ void VRWGraphSMPModifier::reverseAddressing localMinRow = Foam::min(localMinRow, entryI); } } - + ++localMaxRow; - + + # ifdef USE_OMP # pragma omp critical + # endif { minRow = Foam::min(minRow, localMinRow); maxRow = Foam::max(maxRow, localMaxRow); nAppearances.setSize(maxRow); } - + + # ifdef USE_OMP # pragma omp barrier //- initialise appearances # pragma omp for schedule(static) + # endif for(label i=0;i<maxRow;++i) nAppearances[i] = 0; - + + # ifdef USE_OMP # pragma omp barrier + # endif const label range = (maxRow - minRow) / nThreads + 1; const label localMin = minRow + threadI * range; const label localMax = Foam::min(localMin + range, maxRow); - + //- find the number of appearances of each element in the original graph + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAll(origGraph[rowI], i) { const label entryI = mapper[origGraph[rowI][i]]; - + const label threadNo = (entryI - minRow) / range; - + if( threadNo == threadI ) { ++nAppearances[entryI]; @@ -309,40 +380,46 @@ void VRWGraphSMPModifier::reverseAddressing } } + # ifdef USE_OMP # pragma omp barrier + # endif //- count the appearances which are not local to the processor for(label i=0;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) ++nAppearances[data[j].first()]; } + # ifdef USE_OMP # pragma omp barrier //- allocate graph # pragma omp master + # endif { setSizeAndRowSize(nAppearances); } - + + # ifdef USE_OMP # pragma omp barrier - + # endif + for(label i=localMin;i<localMax;++i) { nAppearances[i] = 0; } - + //- start filling reverse addressing graph //- update data from processors with smaller labels for(label i=0;i<threadI;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); @@ -351,7 +428,9 @@ void VRWGraphSMPModifier::reverseAddressing } //- update data local to the processor + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAll(origGraph[rowI], j) @@ -362,13 +441,13 @@ void VRWGraphSMPModifier::reverseAddressing graph_(entryI, nAppearances[entryI]++) = rowI; } } - + //- update data from the processors with higher labels for(label i=threadI+1;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); @@ -386,25 +465,37 @@ void VRWGraphSMPModifier::reverseAddressing ) { ListType nAppearances; - + + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( origGraph.size() < 1000 ) nThreads = 1; - + # else + const label nThreads(1); + # endif + label minRow(INT_MAX), maxRow(-1); List<List<LongList<labelPair> > > dataForOtherThreads(nThreads); - + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); - + # else + const label threadI(0); + # endif + List<LongList<labelPair> >& dot = dataForOtherThreads[threadI]; dot.setSize(nThreads); - + //- find min and max entry in the graph //- they are used for assigning ranges of values local for each process label localMinRow(INT_MAX), localMaxRow(-1); + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAllRow(origGraph, rowI, i) @@ -414,39 +505,47 @@ void VRWGraphSMPModifier::reverseAddressing localMinRow = Foam::min(localMinRow, entryI); } } - + ++localMaxRow; - + + # ifdef USE_OMP # pragma omp critical + # endif { minRow = Foam::min(minRow, localMinRow); maxRow = Foam::max(maxRow, localMaxRow); nAppearances.setSize(maxRow); } - + + # ifdef USE_OMP # pragma omp barrier - + //- initialise appearances # pragma omp for schedule(static) + # endif for(label i=0;i<maxRow;++i) nAppearances[i] = 0; - + + # ifdef USE_OMP # pragma omp barrier + # endif const label range = (maxRow - minRow) / nThreads + 1; const label localMin = minRow + threadI * range; const label localMax = Foam::min(localMin + range, maxRow); - + //- find the number of appearances of each element in the original graph + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAllRow(origGraph, rowI, i) { const label entryI = mapper[origGraph(rowI, i)]; - + const label threadNo = (entryI - minRow) / range; - + if( threadNo == threadI ) { ++nAppearances[entryI]; @@ -457,39 +556,44 @@ void VRWGraphSMPModifier::reverseAddressing } } } - + + # ifdef USE_OMP # pragma omp barrier + # endif //- count the appearances which are not local to the processor for(label i=0;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) ++nAppearances[data[j].first()]; } - + + # ifdef USE_OMP # pragma omp barrier //- allocate graph # pragma omp master + # endif { setSizeAndRowSize(nAppearances); } - + + # ifdef USE_OMP # pragma omp barrier - + # endif for(label i=localMin;i<localMax;++i) nAppearances[i] = 0; - + //- start filling reverse addressing graph //- update data from processors with smaller labels for(label i=0;i<threadI;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); @@ -498,7 +602,9 @@ void VRWGraphSMPModifier::reverseAddressing } //- update data local to the processor + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(origGraph, rowI) { forAllRow(origGraph, rowI, j) @@ -509,13 +615,13 @@ void VRWGraphSMPModifier::reverseAddressing graph_(entryI, nAppearances[entryI]++) = rowI; } } - + //- update data from the processors with higher labels for(label i=threadI+1;i<nThreads;++i) { const LongList<labelPair>& data = dataForOtherThreads[i][threadI]; - + forAll(data, j) { const label entryI = data[j].first(); diff --git a/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.C b/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.C index 0f1f8fd1f96cd69c1fbc4ab1d3bfc0249420bde5..b68d52520b5cff000dc8a26c745412d5c1ac270f 100644 --- a/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.C +++ b/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -36,14 +35,14 @@ Foam::Ostream& Foam::operator<< const Foam::VRWGraphList& DL ) { - os << DL.size() << nl << token::BEGIN_LIST; - - for(register label i=0;i<DL.size();++i) - { - os << nl << DL[i]; - } - - os << nl << token::END_LIST; + os << DL.size() << nl << token::BEGIN_LIST; + + for(register label i=0;i<DL.size();++i) + { + os << nl << DL[i]; + } + + os << nl << token::END_LIST; return os; } @@ -55,15 +54,15 @@ Foam::Istream& Foam::operator>> Foam::VRWGraphList<T, width>& DL ) { - label size; - T e; - is >> size; - DL.setSize(size); - for(IndexType i=0;i<size;++i) - { - is >> e; - DL[i] = e; - } + label size; + T e; + is >> size; + DL.setSize(size); + for(IndexType i=0;i<size;++i) + { + is >> e; + DL[i] = e; + } return is; } diff --git a/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.H b/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.H index 96660cf95484b981fc529aafba8adfbc24948835..c8f2cb94bda7c39b6a32aa26a2d47a0885b8f98d 100644 --- a/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.H +++ b/meshLibrary/utilities/containers/VRWGraphList/VRWGraphList.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class VRWGraphList Description This class is an implementation of a list of graphs - with variable column width. The implementation is memory efficient. + with variable column width. The implementation is memory efficient. SourceFiles VRWGraphListI.H @@ -52,23 +51,23 @@ namespace Foam class VRWGraphList { - + // Private data - //- graph containing the data - VRWGraph data_; - - //- number of rows - LongList<rowElement> rows_; - - // Private member functions - //- check index - inline void checkIndex - ( - const label i, - const label j, - const label k - ) const; - + //- graph containing the data + VRWGraph data_; + + //- number of rows + LongList<rowElement> rows_; + + // Private member functions + //- check index + inline void checkIndex + ( + const label i, + const label j, + const label k + ) const; + public: // Constructors @@ -77,11 +76,11 @@ public: inline VRWGraphList(); //- Copy contructor - inline VRWGraphList(const VRWGraphList&); + inline VRWGraphList(const VRWGraphList&); - // Destructor + // Destructor - inline ~VRWGraphList(); + inline ~VRWGraphList(); // Member Functions @@ -89,12 +88,12 @@ public: //- Returns the number of graphs inline label size() const; - - //- Returns the number of rows in the graph at that position - inline label sizeOfGraph(const label posI) const; - - //- Return the number of element in the row at the given position - inline label sizeOfRow(const label posI, const label rowI) const; + + //- Returns the number of rows in the graph at that position + inline label sizeOfGraph(const label posI) const; + + //- Return the number of element in the row at the given position + inline label sizeOfRow(const label posI, const label rowI) const; //- Clear the graph inline void clear(); @@ -102,23 +101,23 @@ public: // Member Operators //- Append a graph at the end of the graphList - template<class GraphType> + template<class GraphType> inline void appendGraph(const GraphType& l); - - //- get and set operators - inline label operator() - ( - const label i, - const label j, - const label k - ) const; - - inline label& operator()(const label i, const label j, const label k); - - inline const subGraph<const VRWGraph> operator[](const label i) const; - - //- Assignment operator - inline void operator=(const VRWGraphList&); + + //- get and set operators + inline label operator() + ( + const label i, + const label j, + const label k + ) const; + + inline label& operator()(const label i, const label j, const label k); + + inline const subGraph<const VRWGraph> operator[](const label i) const; + + //- Assignment operator + inline void operator=(const VRWGraphList&); // IOstream operators diff --git a/meshLibrary/utilities/containers/VRWGraphList/VRWGraphListI.H b/meshLibrary/utilities/containers/VRWGraphList/VRWGraphListI.H index 78afff1743ad25d78a8a8cada49018034171285a..fbc9a27d2c4ef5305c6b08a4c264d58d9d3b688a 100644 --- a/meshLibrary/utilities/containers/VRWGraphList/VRWGraphListI.H +++ b/meshLibrary/utilities/containers/VRWGraphList/VRWGraphListI.H @@ -1,70 +1,69 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // inline void Foam::VRWGraphList::checkIndex ( - const label i, - const label j, - const label k + const label i, + const label j, + const label k ) const { - if( (i < 0) || (i >= rows_.size()) ) - { - FatalErrorIn - ( - "void Foam::VRWGraphList<T,width>::" - "checkIndex(const label i, const label j, const label k) const" - ) << "Position index " << Foam::label(i) - << " is not in range " << Foam::label(0) - << " and " << rows_.size() << abort(FatalError); - } - - if( (j < 0) || (j >= rows_[i].size()) ) - FatalErrorIn - ( - "void Foam::VRWGraphList<T,width>::" - "checkIndex(label const i, const label j, const label k) const" - ) << "Row index " << Foam::label(j) - << " is not in range " << Foam::label(0) - << " and " << rows_[i].size() << abort(FatalError); - - if( (k < 0) || (k >= data_.sizeOfRow(rows_[i].start()+j)) ) - FatalErrorIn - ( - "void Foam::VRWGraphList<T,width>::" - "checkIndex(label const i, const label j, const label k) const" - ) << "Data index " << Foam::label(k) - << " is not in range " << Foam::label(0) - << " and " << data_.sizeOfRow(rows_[i].start()+j) - << abort(FatalError); + if( (i < 0) || (i >= rows_.size()) ) + { + FatalErrorIn + ( + "void Foam::VRWGraphList<T,width>::" + "checkIndex(const label i, const label j, const label k) const" + ) << "Position index " << Foam::label(i) + << " is not in range " << Foam::label(0) + << " and " << rows_.size() << abort(FatalError); + } + + if( (j < 0) || (j >= rows_[i].size()) ) + FatalErrorIn + ( + "void Foam::VRWGraphList<T,width>::" + "checkIndex(label const i, const label j, const label k) const" + ) << "Row index " << Foam::label(j) + << " is not in range " << Foam::label(0) + << " and " << rows_[i].size() << abort(FatalError); + + if( (k < 0) || (k >= data_.sizeOfRow(rows_[i].start()+j)) ) + FatalErrorIn + ( + "void Foam::VRWGraphList<T,width>::" + "checkIndex(label const i, const label j, const label k) const" + ) << "Data index " << Foam::label(k) + << " is not in range " << Foam::label(0) + << " and " << data_.sizeOfRow(rows_[i].start()+j) + << abort(FatalError); } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -72,18 +71,18 @@ inline void Foam::VRWGraphList::checkIndex //- Construct null inline Foam::VRWGraphList::VRWGraphList() : - data_(), - rows_() + data_(), + rows_() { } inline Foam::VRWGraphList::VRWGraphList ( - const VRWGraphList& ol + const VRWGraphList& ol ) : - data_(ol.data_), - rows_(ol.rows_) + data_(ol.data_), + rows_(ol.rows_) { } @@ -101,79 +100,79 @@ inline Foam::label Foam::VRWGraphList::size() const inline Foam::label Foam::VRWGraphList::sizeOfGraph(const label posI) const { - return rows_[posI].size(); + return rows_[posI].size(); } inline Foam::label Foam::VRWGraphList::sizeOfRow ( - const label posI, - const label rowI + const label posI, + const label rowI ) const { - return data_.sizeOfRow(rows_[posI].start()+rowI); + return data_.sizeOfRow(rows_[posI].start()+rowI); } inline void Foam::VRWGraphList::clear() { data_.setSize(0); - rows_.setSize(0); + rows_.setSize(0); } template<class GraphType> inline void Foam::VRWGraphList::appendGraph ( - const GraphType& l + const GraphType& l ) { - rowElement re(data_.size(), l.size()); - - for(label i=0;i<l.size();++i) - data_.appendList(l[i]); - - rows_.append(re); + rowElement re(data_.size(), l.size()); + + for(label i=0;i<l.size();++i) + data_.appendList(l[i]); + + rows_.append(re); } // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * // inline Foam::label Foam::VRWGraphList::operator() ( - const label i, - const label j, - const label k + const label i, + const label j, + const label k ) const { - #ifdef FULLDEBUG - checkIndex(i, j, k); - #endif - - return data_(rows_[i].start() + j, k); + #ifdef FULLDEBUG + checkIndex(i, j, k); + #endif + + return data_(rows_[i].start() + j, k); } inline Foam::label& Foam::VRWGraphList::operator() ( - const label i, const label j, const label k + const label i, const label j, const label k ) { - #ifdef FULLDEBUG - checkIndex(i, j, k); - #endif - - return data_(rows_[i].start() + j, k); + #ifdef FULLDEBUG + checkIndex(i, j, k); + #endif + + return data_(rows_[i].start() + j, k); } inline const Foam::subGraph<const VRWGraph> Foam::VRWGraphList::operator[] ( - const label i + const label i ) const { - return Foam::subGraph<const VRWGraph>(data_, i, rows_[i].size()); + return Foam::subGraph<const VRWGraph>(data_, i, rows_[i].size()); } inline void Foam::VRWGraphList::operator=(const VRWGraphList& l) { - data_ = l.data_; - rows_ = l.rows_; + data_ = l.data_; + rows_ = l.rows_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/graphRow/graphRow.H b/meshLibrary/utilities/containers/graphRow/graphRow.H index 64e771c7e7997d5b5f67909e0e1aacc6c023d3a2..6b906901a5f6d45a52525d05a7eb8a512e14eaa1 100644 --- a/meshLibrary/utilities/containers/graphRow/graphRow.H +++ b/meshLibrary/utilities/containers/graphRow/graphRow.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class graphRow @@ -44,7 +43,7 @@ SourceFiles namespace Foam { - + class VRWGraph; template<class graphType> class graphRow; @@ -59,16 +58,16 @@ template<class graphType> class graphRow { // Private data - //- reference to the graph - graphType& data_; - - //- row number - const label rowI_; - - // Private member functions - //- check index - inline void checkIndex(const label i) const; - + //- reference to the graph + graphType& data_; + + //- row number + const label rowI_; + + // Private member functions + //- check index + inline void checkIndex(const label i) const; + public: // Constructors @@ -77,52 +76,52 @@ public: inline graphRow(graphType&, const label); //- Copy contructor - inline graphRow(const graphRow<graphType>&); + inline graphRow(const graphRow<graphType>&); - // Destructor + // Destructor - inline ~graphRow(); + inline ~graphRow(); // Member Functions - //- Returns the number of rows - inline label size() const; + //- Returns the number of rows + inline label size() const; - //- Reset the number of rows - inline void setSize(const label size); + //- Reset the number of rows + inline void setSize(const label size); - //- Clear the graph - inline void clear(); + //- Clear the graph + inline void clear(); // Member Operators - - //- Append an element to the given row - inline void append(const label); - - //- Append an element to the given row if it does not exist there - inline void appendIfNotIn(const label); - - //- check if the element is in the given row (takes linear time) - inline bool contains(const label e) const; - inline label containsAtPosition(const label e) const; - - //- set and get operators - inline label operator[](const label) const; - inline label& operator[](const label); - - //- Assignment operator - inline void operator=(const graphRow<graphType>&); - template<class listType> - inline void operator=(const listType&); + + //- Append an element to the given row + inline void append(const label); + + //- Append an element to the given row if it does not exist there + inline void appendIfNotIn(const label); + + //- check if the element is in the given row (takes linear time) + inline bool contains(const label e) const; + inline label containsAtPosition(const label e) const; + + //- set and get operators + inline label operator[](const label) const; + inline label& operator[](const label); + + //- Assignment operator + inline void operator=(const graphRow<graphType>&); + template<class listType> + inline void operator=(const listType&); // IOstream operators // Write graphRow to Ostream. friend Ostream& operator<< <graphType> - ( - Ostream&, - const graphRow<graphType>& - ); + ( + Ostream&, + const graphRow<graphType>& + ); //- Read from Istream, discarding contents of existing graphRow. /* friend Istream& operator>> <T, width> diff --git a/meshLibrary/utilities/containers/graphRow/graphRowI.H b/meshLibrary/utilities/containers/graphRow/graphRowI.H index ce43d9d6f1ee7377e64a4ce0aa3f21385df3ed56..35cf9dc70add6a4347b7ef3e493f832453ffacbc 100644 --- a/meshLibrary/utilities/containers/graphRow/graphRowI.H +++ b/meshLibrary/utilities/containers/graphRow/graphRowI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -30,16 +29,16 @@ namespace Foam template<class graphType> inline void Foam::graphRow<graphType>::checkIndex(const label i) const { - if( (i < 0) || (i >=data_.sizeOfRow(rowI_)) ) - { - FatalErrorIn - ( - "void Foam::graphRow<graphType>::" - "checkIndex(const label i) const" - ) << "Row index " << rowI_ - << " is not in range " << Foam::label(0) - << " and " << data_.sizeOfRow(rowI_) << abort(FatalError); - } + if( (i < 0) || (i >=data_.sizeOfRow(rowI_)) ) + { + FatalErrorIn + ( + "void Foam::graphRow<graphType>::" + "checkIndex(const label i) const" + ) << "Row index " << rowI_ + << " is not in range " << Foam::label(0) + << " and " << data_.sizeOfRow(rowI_) << abort(FatalError); + } } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -47,19 +46,19 @@ inline void Foam::graphRow<graphType>::checkIndex(const label i) const template<class graphType> inline Foam::graphRow<graphType>::graphRow(graphType& g, const label i) : - data_(g), - rowI_(i) + data_(g), + rowI_(i) { } template<class graphType> inline Foam::graphRow<graphType>::graphRow ( - const graphRow<graphType>& ol + const graphRow<graphType>& ol ) : - data_(ol.data_), - rowI_(ol.rowI_) + data_(ol.data_), + rowI_(ol.rowI_) { } @@ -80,31 +79,31 @@ inline Foam::label Foam::graphRow<graphType>::size() const template<class graphType> inline void Foam::graphRow<graphType>::setSize(const label s) { - data_.setRowSize(rowI_, s); + data_.setRowSize(rowI_, s); } template<class graphType> inline void Foam::graphRow<graphType>::clear() { - data_.setRowSize(rowI_, 0); + data_.setRowSize(rowI_, 0); } template<class graphType> inline void Foam::graphRow<graphType>::append(const label el) { - data_.append(rowI_, el); + data_.append(rowI_, el); } template<class graphType> inline void Foam::graphRow<graphType>::appendIfNotIn(const label el) { - data_.appendIfNotIn(rowI_, el); + data_.appendIfNotIn(rowI_, el); } template<class graphType> inline bool Foam::graphRow<graphType>::contains(const label e) const { - return data_.contains(rowI_, e); + return data_.contains(rowI_, e); } template<class graphType> @@ -113,7 +112,7 @@ inline Foam::label Foam::graphRow<graphType>::containsAtPosition const label e ) const { - return data_.containsAtPosition(rowI_, e); + return data_.containsAtPosition(rowI_, e); } // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * // @@ -121,48 +120,48 @@ inline Foam::label Foam::graphRow<graphType>::containsAtPosition template<class graphType> inline Foam::label Foam::graphRow<graphType>::operator[](const label i) const { - return data_(rowI_, i); + return data_(rowI_, i); } template<class graphType> inline Foam::label& Foam::graphRow<graphType>::operator[](const label i) { - return data_(rowI_, i); + return data_(rowI_, i); } template<class graphType> inline void Foam::graphRow<graphType>::operator= ( - const graphRow<graphType>& l + const graphRow<graphType>& l ) { - data_.setRowSize(rowI_, l.size()); - for(label i=0;i<l.size();++i) - data_(rowI_, i) = l[i]; + data_.setRowSize(rowI_, l.size()); + for(label i=0;i<l.size();++i) + data_(rowI_, i) = l[i]; } template<class graphType> template<class listType> inline void Foam::graphRow<graphType>::operator=(const listType& l) { - data_.setRowSize(rowI_, l.size()); - for(label i=0;i<l.size();++i) - data_(rowI_, i) = l[i]; + data_.setRowSize(rowI_, l.size()); + for(label i=0;i<l.size();++i) + data_(rowI_, i) = l[i]; } template<class graphType> inline Foam::Ostream& operator<< ( - Foam::Ostream& os, - const Foam::graphRow<graphType>& r + Foam::Ostream& os, + const Foam::graphRow<graphType>& r ) { - os << r.size() << "("; - for(Foam::label i=0;i<r.size();++i) - os << r[i] << " "; - os << ")"; - - return os; + os << r.size() << "("; + for(Foam::label i=0;i<r.size();++i) + os << r[i] << " "; + os << ")"; + + return os; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/subGraph/subGraph.H b/meshLibrary/utilities/containers/subGraph/subGraph.H index 5e825864d64c8808c8e8d4d7e5ab3de4c2f7eeaf..f5c46d67905a3d6c1493f86853937b9f2b63d763 100644 --- a/meshLibrary/utilities/containers/subGraph/subGraph.H +++ b/meshLibrary/utilities/containers/subGraph/subGraph.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class subGraph @@ -58,19 +57,19 @@ template<class graphType> class subGraph { // Private data - //- reference to the graph - graphType& data_; - - //- starts at row - const label start_; - - //- number of rows in the subGraph - const label size_; - - // Private member functions - //- check index - inline void checkIndex(const label i) const; - + //- reference to the graph + graphType& data_; + + //- starts at row + const label start_; + + //- number of rows in the subGraph + const label size_; + + // Private member functions + //- check index + inline void checkIndex(const label i) const; + public: // Constructors @@ -79,46 +78,46 @@ public: inline subGraph(graphType&, const label, const label); //- Copy contructor - inline subGraph(const subGraph<graphType>&); + inline subGraph(const subGraph<graphType>&); - // Destructor + // Destructor - inline ~subGraph(); + inline ~subGraph(); // Member Functions - //- Returns the number of rows - inline label size() const; + //- Returns the number of rows + inline label size() const; - //- Returns the size of a given row - inline label sizeOfRow(const label rowI) const; + //- Returns the size of a given row + inline label sizeOfRow(const label rowI) const; // Member Operators - - //- Append an element to the given row - inline void append(const label rowI, const label); - - //- Append an element to the given row if it does not exist there - inline void appendIfNotIn(const label rowI, const label); - - //- check if the element is in the given row (takes linear time) - inline bool contains(const label rowI, const label e) const; - inline label containsAtPosition(const label rowI, const label e) const; - - //- set and get operators - inline label operator()(const label i, const label j) const; - inline label& operator()(const label i, const label j); - inline const graphRow<const graphType> operator[](const label) const; - inline graphRow<graphType> operator[](const label); + + //- Append an element to the given row + inline void append(const label rowI, const label); + + //- Append an element to the given row if it does not exist there + inline void appendIfNotIn(const label rowI, const label); + + //- check if the element is in the given row (takes linear time) + inline bool contains(const label rowI, const label e) const; + inline label containsAtPosition(const label rowI, const label e) const; + + //- set and get operators + inline label operator()(const label i, const label j) const; + inline label& operator()(const label i, const label j); + inline const graphRow<const graphType> operator[](const label) const; + inline graphRow<graphType> operator[](const label); // IOstream operators // Write subGraph to Ostream. friend Ostream& operator<< <graphType> - ( - Ostream&, - const subGraph<graphType>& - ); + ( + Ostream&, + const subGraph<graphType>& + ); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/containers/subGraph/subGraphI.H b/meshLibrary/utilities/containers/subGraph/subGraphI.H index cc18f877bd5ac233ae4725658c10343d717b085b..0ac33821eca1f04ba31337545174bd2e2ead9756 100644 --- a/meshLibrary/utilities/containers/subGraph/subGraphI.H +++ b/meshLibrary/utilities/containers/subGraph/subGraphI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -30,16 +29,16 @@ namespace Foam template<class graphType> inline void Foam::subGraph<graphType>::checkIndex(const label i) const { - if( (i < 0) || (i >= size_) ) - { - FatalErrorIn - ( - "void Foam::subGraph<graphType>::" - "checkIndex(const label i) const" - ) << "Row index " << i - << " is not in range " << Foam::label(0) - << " and " << size_ << abort(FatalError); - } + if( (i < 0) || (i >= size_) ) + { + FatalErrorIn + ( + "void Foam::subGraph<graphType>::" + "checkIndex(const label i) const" + ) << "Row index " << i + << " is not in range " << Foam::label(0) + << " and " << size_ << abort(FatalError); + } } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -47,26 +46,26 @@ inline void Foam::subGraph<graphType>::checkIndex(const label i) const template<class graphType> inline Foam::subGraph<graphType>::subGraph ( - graphType& g, - const label start, - const label size + graphType& g, + const label start, + const label size ) : - data_(g), - start_(start), - size_(size) + data_(g), + start_(start), + size_(size) { } template<class graphType> inline Foam::subGraph<graphType>::subGraph ( - const subGraph<graphType>& ol + const subGraph<graphType>& ol ) : - data_(ol.data_), - start_(ol.start_), - size_(ol.size_) + data_(ol.data_), + start_(ol.start_), + size_(ol.size_) { } @@ -87,43 +86,43 @@ inline Foam::label Foam::subGraph<graphType>::size() const template<class graphType> inline Foam::label Foam::subGraph<graphType>::sizeOfRow(const label rowI) const { - return data_.sizeOfRow(start_+rowI); + return data_.sizeOfRow(start_+rowI); } template<class graphType> inline void Foam::subGraph<graphType>::append(const label rowI, const label el) { - data_.append(start_+rowI, el); + data_.append(start_+rowI, el); } template<class graphType> inline void Foam::subGraph<graphType>::appendIfNotIn ( - const label rowI, - const label el + const label rowI, + const label el ) { - data_.appendIfNotIn(start_+rowI, el); + data_.appendIfNotIn(start_+rowI, el); } template<class graphType> inline bool Foam::subGraph<graphType>::contains ( - const label rowI, - const label e + const label rowI, + const label e ) const { - return data_.contains(start_+rowI, e); + return data_.contains(start_+rowI, e); } template<class graphType> inline Foam::label Foam::subGraph<graphType>::containsAtPosition ( - const label rowI, + const label rowI, const label e ) const { - return data_.containsAtPosition(start_+rowI, e); + return data_.containsAtPosition(start_+rowI, e); } // * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * // @@ -131,25 +130,25 @@ inline Foam::label Foam::subGraph<graphType>::containsAtPosition template<class graphType> inline Foam::label Foam::subGraph<graphType>::operator() ( - const label i, - const label j + const label i, + const label j ) const { - # ifdef FULLDEBUG - checkIndex(i); - # endif - - return data_(start_+i, j); + # ifdef FULLDEBUG + checkIndex(i); + # endif + + return data_(start_+i, j); } template<class graphType> inline Foam::label& Foam::subGraph<graphType>::operator() ( - const label i, - const label j + const label i, + const label j ) { - return data_(start_+i, j); + return data_(start_+i, j); } @@ -157,43 +156,43 @@ template<class graphType> inline const Foam::graphRow<const graphType> Foam::subGraph<graphType>::operator[] ( - const label i + const label i ) const { - return data_[start_+i]; + return data_[start_+i]; } template<class graphType> inline Foam::graphRow<graphType> Foam::subGraph<graphType>::operator[](const label i) { - return data_[start_+i]; + return data_[start_+i]; } template<class graphType> inline Foam::Ostream& operator<< ( - Foam::Ostream& os, - const Foam::subGraph<graphType>& sg + Foam::Ostream& os, + const Foam::subGraph<graphType>& sg ) { - os << sg.size() << "\n" << "("; - for(Foam::label i=0;i<sg.size();++i) - { - os << "\n" << sg.sizeOfRow(i) << "("; - for(Foam::label j=0;j<sg.sizeOfRow(i);++j) - { - if( j > 0 ) os << " "; - - os << sg(i, j); - } - - os << ")"; - } - - os << "\n" << ")"; - - return os; + os << sg.size() << "\n" << "("; + for(Foam::label i=0;i<sg.size();++i) + { + os << "\n" << sg.sizeOfRow(i) << "("; + for(Foam::label j=0;j<sg.sizeOfRow(i);++j) + { + if( j > 0 ) os << " "; + + os << sg(i, j); + } + + os << ")"; + } + + os << "\n" << ")"; + + return os; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/dataConversion/foamToEnsight/ensightMesh.C b/meshLibrary/utilities/dataConversion/foamToEnsight/ensightMesh.C deleted file mode 100644 index 860cc81b6aa1a48627e9287a7cf14ed0210a64e4..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/foamToEnsight/ensightMesh.C +++ /dev/null @@ -1,227 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -\*---------------------------------------------------------------------------*/ - -#include "ensightMesh.H" -#include "IOmanip.H" - -namespace Foam -{ - -// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from polyMeshGen -Foam::ensightMesh::ensightMesh(const polyMeshGen& mesh) -: - mesh_(mesh) -{ -} - - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -Foam::ensightMesh::~ensightMesh() -{} - - -// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // - -void Foam::ensightMesh::writePoints -( - const Foam::scalarField& pointsComponent, - Foam::OFstream& ensightGeometryFile -) const -{ - forAll(pointsComponent, pointi) - { - ensightGeometryFile << setw(12) << pointsComponent[pointi] << nl; - } -} - -void ensightMesh::writePolys -( - const cellListPMG& cellFaces, - const faceListPMG& faces, - OFstream& ensightGeometryFile -) const -{ - ensightGeometryFile << "nfaced" << nl << setw(10) << cellFaces.size() << nl; - - forAll(cellFaces, cI) - { - ensightGeometryFile << setw(10) << cellFaces[cI].size() << nl; - } - - forAll(cellFaces, cI) - { - const labelList& cf = cellFaces[cI]; - - forAll(cf, faceI) - { - ensightGeometryFile << setw(10) << faces[cf[faceI]].size() << nl; - } - } - - forAll(cellFaces, cI) - { - const labelList& cf = cellFaces[cI]; - - forAll(cf, faceI) - { - const face& f = faces[cf[faceI]]; - - forAll(f, pointI) - { - ensightGeometryFile << setw(10) << f[pointI] + 1; - } - ensightGeometryFile << nl; - } - } -} - -void Foam::ensightMesh::writeFaces -( - const faceList& patchFaces, - OFstream& ensightGeometryFile -) const -{ - if (patchFaces.size()) - { - ensightGeometryFile - << "nsided" << nl << setw(10) << patchFaces.size() << nl; - - forAll(patchFaces, i) - { - ensightGeometryFile - << setw(10) << patchFaces[i].size() << nl; - } - - forAll(patchFaces, i) - { - const face& patchFace = patchFaces[i]; - - forAll(patchFace, pointi) - { - ensightGeometryFile << setw(10) << patchFace[pointi] + 1; - } - ensightGeometryFile << nl; - } - } -} - -void Foam::ensightMesh::writePatches -( - Foam::OFstream& ensightGeometryFile -) const -{ - const faceListPMG& faces = mesh_.faces(); - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - - forAll(boundaries, patchI) - { - ensightGeometryFile - << "part" << nl - << setw(10) << patchI + 2 << nl - << boundaries[patchI].patchName() << nl - << "coordinates" << nl - << setw(10) << mesh_.points().size() - << endl; - - for (direction d=0; d<vector::nComponents; d++) - { - writePoints - ( - mesh_.points().component(d), - ensightGeometryFile - ); - } - - faceList patchFaces(boundaries[patchI].patchSize()); - const label start = boundaries[patchI].patchStart(); - forAll(patchFaces, faceI) - patchFaces[faceI] = faces[start+faceI]; - - writeFaces - ( - patchFaces, - ensightGeometryFile - ); - } -} - - -void ensightMesh::write -( - OFstream& ensightGeometryFile -) const -{ - const pointFieldPMG& points = mesh_.points(); - const cellListPMG& cellFaces = mesh_.cells(); - const faceListPMG& faces = mesh_.faces(); - - // Set Format - ensightGeometryFile.setf - ( - ios_base::scientific, - ios_base::floatfield - ); - ensightGeometryFile.precision(5); - - ensightGeometryFile - << "FOAM Geometry File " << nl << nl - << "node id assign" << nl - << "element id assign" << nl; - - ensightGeometryFile - << "part" << nl - << setw(10) << 1 << nl - << "FOAM cells" << nl - << "coordinates" << nl - << setw(10) << points.size() - << endl; - - for (direction d=0; d<vector::nComponents; d++) - { - scalarField comp = points.component(d)(); - writePoints(comp, ensightGeometryFile); - } - - writePolys - ( - cellFaces, - faces, - ensightGeometryFile - ); - - writePatches(ensightGeometryFile); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/foamToEnsight/ensightMesh.H b/meshLibrary/utilities/dataConversion/foamToEnsight/ensightMesh.H deleted file mode 100644 index bc080e0457442fceec84a836e2d917b71d4c3c00..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/foamToEnsight/ensightMesh.H +++ /dev/null @@ -1,129 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - ensightMesh - -Description - -SourceFiles - ensightMesh.C - -\*---------------------------------------------------------------------------*/ - -#ifndef ensightMesh_H -#define ensightMesh_H - -#include "polyMeshGen.H" -#include "OFstream.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -/*---------------------------------------------------------------------------*\ - Class ensightMesh Declaration -\*---------------------------------------------------------------------------*/ - -class ensightMesh -{ - // Private data - - - // Private Member Functions - - //- Disallow default bitwise copy construct - ensightMesh(const ensightMesh&); - - //- Disallow default bitwise assignment - void operator=(const ensightMesh&); - - void writePoints - ( - const scalarField& pointsComponent, - OFstream& ensightGeometryFile - ) const; - - void writePolys - ( - const cellListPMG& cellFaces, - const faceListPMG& faces, - OFstream& ensightGeometryFile - ) const; - - void writeFaces - ( - const faceList& patchFaces, - OFstream& ensightGeometryFile - ) const; - - void writePatches - ( - OFstream& ensightGeometryFile - ) const; - -public: - - // Public data - - const polyMeshGen& mesh_; - - // Constructors - - //- Construct from polyMeshGen - ensightMesh(const polyMeshGen& mesh); - - - // Destructor - - ~ensightMesh(); - - - // Member Functions - - // Access - - // Check - - // Edit - - // Write - - void write - ( - OFstream& ensightGeometryFile - ) const; -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/foamToEnsight/writeMeshEnsight.C b/meshLibrary/utilities/dataConversion/foamToEnsight/writeMeshEnsight.C deleted file mode 100644 index a6400cde66c462cc4e9019575db9e37c592bb2fe..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/foamToEnsight/writeMeshEnsight.C +++ /dev/null @@ -1,119 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Description - Translates FOAM mesh to EnSight format - -\*---------------------------------------------------------------------------*/ - -#include "objectRegistry.H" -#include "Time.H" -#include "polyMeshGen.H" -#include "OFstream.H" -#include "IOmanip.H" -#include "fileName.H" - -#include "ensightMesh.H" -#include "writeMeshEnsight.H" - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void writeMeshEnsight(const polyMeshGen& mesh, const word& fName) -{ - const Time& time = mesh.returnTime(); - - const word postProcDir = "EnSight"+fName; - const word prepend = fName + '.'; - Info << "Writting mesh into " << postProcDir << endl; - - fileName postProcPath = time.path()/postProcDir; - - if( Foam::isDir(postProcPath) ) - { - Foam::rmDir(postProcPath); - } - - Foam::mkDir(postProcPath); - - // Open the Case file - fileName ensightCaseFileName = prepend + "case"; - -/* OFstream ensightCaseFile - ( - postProcPath/ensightCaseFileName, - IOstream::ASCII, - IOstream::currentVersion, - IOstream::UNCOMPRESSED - ); -*/ - OFstream ensightCaseFile(postProcPath/ensightCaseFileName); - - Info<< nl << "Case file is " << ensightCaseFileName << endl; - -/* OFstream ensightGeometryFile - ( - postProcPath/prepend+"000.mesh", - IOstream::ASCII, - IOstream::currentVersion, - IOstream::UNCOMPRESSED - ); -*/ - OFstream ensightGeometryFile(postProcPath/prepend+"000.mesh"); - - // Construct the EnSight mesh - ensightMesh eMesh(mesh); - eMesh.write(ensightGeometryFile); - - //- write the case file - ensightCaseFile << "FORMAT" << nl; - ensightCaseFile << "type: ensight gold" << nl << nl; - - word geomCaseFileName = prepend + "000"; - if( Pstream::master() ) - { - // test pre check variable if there is a moving mesh - ensightCaseFile - << "GEOMETRY" << nl - << "model: 1 " - << (geomCaseFileName + ".mesh").c_str() << nl; - } - - ensightCaseFile << nl << "TIME" << nl - << "time set: " << 1 << nl - << "number of steps: " << 1 << nl - << "filename start number: " << 0 << nl - << "filename increment: " << 1 << nl; - - ensightCaseFile << "time values:" << nl; - - ensightCaseFile.setf(ios_base::scientific, ios_base::floatfield); - ensightCaseFile.precision(5); -} - -} - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/foamToFLMA/flmaMesh.C b/meshLibrary/utilities/dataConversion/foamToFLMA/flmaMesh.C deleted file mode 100644 index 024b23e928ef590424936de21d2f67837fe688c9..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/foamToFLMA/flmaMesh.C +++ /dev/null @@ -1,455 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -\*---------------------------------------------------------------------------*/ - -#include "flmaMesh.H" -#include "IOmanip.H" -#include "tetMatcher.H" -#include "hexMatcher.H" -#include "prismMatcher.H" -#include "pyrMatcher.H" - -namespace Foam -{ - -// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // - -void Foam::flmaMesh::createPointsForDecomposition() -{ - const pointFieldPMG& points = mesh_.points(); - const faceListPMG& faces = mesh_.faces(); - - forAll(faces, faceI) - { - if( faces[faceI].size() < 5 ) - continue; - - const point p = faces[faceI].centre(points); - faceCentreLabel_.insert(faceI, points.size()+additionalPoints_.size()); - additionalPoints_.append(p); - } - - const labelList& owner = mesh_.owner(); - const cellListPMG& cells = mesh_.cells(); - cellType_.setSize(cells.size()); - cellType_ = -1; - - tetMatcher tet; - pyrMatcher pyr; - hexMatcher hex; - prismMatcher prism; - - forAll(cells, cellI) - { - if( tet.matchShape(true, faces, owner, cellI, cells[cellI]) ) - { - cellType_[cellI] = 4; - } - else if( hex.matchShape(true, faces, owner, cellI, cells[cellI]) ) - { - cellType_[cellI] = 5; - } - else if( prism.matchShape(true, faces, owner, cellI, cells[cellI]) ) - { - cellType_[cellI] = 8; - } - else if( pyr.matchShape(true, faces, owner, cellI, cells[cellI]) ) - { - cellType_[cellI] = 6; - } - else - { - FatalError << "Cell " << cellI << " is not a standard cell!!" - << exit(FatalError); - - const labelList cp = cells[cellI].labels(faces); - point p(vector::zero); - forAll(cp, i) - p += points[cp[i]]; - - p /= cp.size(); - - cellCentreLabel_.insert - ( - cellI, - points.size()+additionalPoints_.size() - ); - additionalPoints_.append(p); - } - } -} - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from polyMeshGen -Foam::flmaMesh::flmaMesh(const polyMeshGen& mesh) -: - mesh_(mesh), - cellType_(), - additionalPoints_(), - faceCentreLabel_(), - cellCentreLabel_() -{ - createPointsForDecomposition(); -} - - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -Foam::flmaMesh::~flmaMesh() -{} - - -// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // - -void Foam::flmaMesh::writePoints -( - Foam::OFstream& flmaGeometryFile -) const -{ - flmaGeometryFile << (mesh_.points().size()+additionalPoints_.size()) << nl; - const pointFieldPMG& points = mesh_.points(); - forAll(points, pointI) - { - const point& p = points[pointI]; - flmaGeometryFile << p.x() << ' ' << p.y() << ' ' << p.z() << ' '; - } - forAll(additionalPoints_, pointI) - { - const point& p = additionalPoints_[pointI]; - flmaGeometryFile << p.x() << ' ' << p.y() << ' ' << p.z() << ' '; - } - - flmaGeometryFile << nl; -} - -void flmaMesh::writeCells -( - OFstream& flmaGeometryFile -) const -{ - const labelList& owner = mesh_.owner(); - const faceListPMG& faces = mesh_.faces(); - const cellListPMG& cells = mesh_.cells(); - tetMatcher tet; - pyrMatcher pyr; - hexMatcher hex; - prismMatcher prism; - - flmaGeometryFile << cells.size() << nl; - - forAll(cells, cellI) - { - if( tet.matchShape(false, faces, owner, cellI, cells[cellI]) ) - { - const labelList& tetVrt = tet.vertLabels(); - flmaGeometryFile << tetVrt.size(); - forAll(tetVrt, i) - flmaGeometryFile << ' ' << tetVrt[i]; - flmaGeometryFile << nl; - } - else if( hex.matchShape(false, faces, owner, cellI, cells[cellI]) ) - { - const labelList& hexVrt = hex.vertLabels(); - flmaGeometryFile << hexVrt.size(); - forAll(hexVrt, i) - flmaGeometryFile << ' ' << hexVrt[i]; - flmaGeometryFile << nl; - } - else if( prism.matchShape(false, faces, owner, cellI, cells[cellI]) ) - { - const labelList& prismVrt = prism.vertLabels(); - flmaGeometryFile << prismVrt.size(); - forAll(prismVrt, i) - flmaGeometryFile << ' ' << prismVrt[i]; - flmaGeometryFile << nl; - } - else if( pyr.matchShape(false, faces, owner, cellI, cells[cellI]) ) - { - const labelList& pyrVrt = pyr.vertLabels(); - flmaGeometryFile << pyrVrt.size(); - forAll(pyrVrt, i) - flmaGeometryFile << ' ' << pyrVrt[i]; - flmaGeometryFile << nl; - } - } -} - -void Foam::flmaMesh::writeCellTypes -( - OFstream& flmaGeometryFile -) const -{ - flmaGeometryFile << nl << cellType_.size() << nl; - forAll(cellType_, cellI) - flmaGeometryFile << cellType_[cellI] << nl; - flmaGeometryFile << nl; -} - -void Foam::flmaMesh::writeSelections -( - Foam::OFstream& flmaGeometryFile -) const -{ - //- write patches as face selections - const PtrList<writePatch>& patches = mesh_.boundaries(); - const faceListPMG& faces = mesh_.faces(); - const labelList& owner = mesh_.owner(); - const cellListPMG& cells = mesh_.cells(); - tetMatcher tet; - pyrMatcher pyr; - hexMatcher hex; - prismMatcher prism; - - label nSubsets(0); - - nSubsets += patches.size(); - - DynList<label> indices; - mesh_.pointSubsetIndices(indices); - nSubsets += indices.size(); - Info << "Mesh has " << indices.size() << " point subsets" << endl; - mesh_.faceSubsetIndices(indices); - nSubsets += indices.size(); - Info << "Mesh has " << indices.size() << " face subsets" << endl; - mesh_.cellSubsetIndices(indices); - nSubsets += indices.size(); - Info << "Mesh has " << indices.size() << " cell subsets" << endl; - - flmaGeometryFile << nSubsets << nl; - - //- write patches as face selections - forAll(patches, patchI) - { - const writePatch& patch = patches[patchI]; - const label start = patch.patchStart(); - const label end = start + patch.patchSize(); - - flmaGeometryFile << patch.patchName() << nl; - flmaGeometryFile << 3 << nl; - flmaGeometryFile << 2 * patch.patchSize() << nl; - - for(label faceI=start;faceI<end;++faceI) - { - const label cellI = owner[faceI]; - const cell& c = cells[owner[faceI]]; - - if( tet.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = tet.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - else if( hex.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = hex.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - else if( prism.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = prism.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - else if( pyr.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = pyr.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - } - - flmaGeometryFile << nl; - } - - //- write node selections - mesh_.pointSubsetIndices(indices); - forAll(indices, indexI) - { - labelListPMG nodesInSubset; - mesh_.pointsInSubset(indices[indexI], nodesInSubset); - - flmaGeometryFile << mesh_.pointSubsetName(indices[indexI]) << nl; - flmaGeometryFile << 1 << nl; - flmaGeometryFile << nodesInSubset.size() << nl; - forAll(nodesInSubset, i) - flmaGeometryFile << nodesInSubset[i] << ' '; - flmaGeometryFile << nl; - } - - //- write face selections - mesh_.faceSubsetIndices(indices); - forAll(indices, indexI) - { - labelListPMG facesInSubset; - mesh_.facesInSubset(indices[indexI], facesInSubset); - - flmaGeometryFile << mesh_.faceSubsetName(indices[indexI]) << nl; - flmaGeometryFile << 3 << nl; - flmaGeometryFile << 2 * facesInSubset.size() << nl; - forAll(facesInSubset, i) - { - const label faceI = facesInSubset[i]; - const label cellI = owner[faceI]; - const cell& c = cells[owner[faceI]]; - - if( tet.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = tet.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - else if( hex.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = hex.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - else if( prism.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = prism.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - else if( pyr.matchShape(false, faces, owner, cellI, c) ) - { - const labelList& faceMap = pyr.faceMap(); - label dir(-1); - forAll(faces, i) - { - if( faceI == faceMap[i] ) - { - dir = i; - break; - } - } - - flmaGeometryFile << ' ' << cellI << ' ' << dir; - } - } - - flmaGeometryFile << nl; - } - - //- write cell selections - mesh_.cellSubsetIndices(indices); - forAll(indices, indexI) - { - labelListPMG cellsInSubset; - mesh_.cellsInSubset(indices[indexI], cellsInSubset); - - flmaGeometryFile << mesh_.cellSubsetName(indices[indexI]) << nl; - flmaGeometryFile << 2 << nl; - flmaGeometryFile << cellsInSubset.size() << nl; - forAll(cellsInSubset, i) - flmaGeometryFile << cellsInSubset[i] << ' '; - flmaGeometryFile << nl; - } -} - - -void flmaMesh::write -( - OFstream& flmaGeometryFile -) const -{ - writePoints(flmaGeometryFile); - - writeCells(flmaGeometryFile); - - writeCellTypes(flmaGeometryFile); - - writeSelections(flmaGeometryFile); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/foamToFLMA/flmaMesh.H b/meshLibrary/utilities/dataConversion/foamToFLMA/flmaMesh.H deleted file mode 100644 index 85db08c4783589f2b8c673c95c24266efe6b7299..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/foamToFLMA/flmaMesh.H +++ /dev/null @@ -1,137 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - fpmaMesh - -Description - -SourceFiles - flmaMesh.C - -\*---------------------------------------------------------------------------*/ - -#ifndef flmaMesh_H -#define flmaMesh_H - -#include "polyMeshGen.H" -#include "OFstream.H" -#include "LongList.H" -#include "Map.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -/*---------------------------------------------------------------------------*\ - Class flmaMesh Declaration -\*---------------------------------------------------------------------------*/ - -class flmaMesh -{ - // Private data - - //- Reference to the mesh - const polyMeshGen& mesh_; - - //- list of cell types - labelList cellType_; - - //- additional points - LongList<point> additionalPoints_; - - //- centre labels of decomposed faces - Map<label> faceCentreLabel_; - - //- centre labels of decomposed cells - Map<label> cellCentreLabel_; - - // Private Member Functions - - //- Create points for decomposed cells - void createPointsForDecomposition(); - - //- Disallow default bitwise copy construct - flmaMesh(const flmaMesh&); - - //- Disallow default bitwise assignment - void operator=(const flmaMesh&); - - void writePoints - ( - OFstream& flmaGeometryFile - ) const; - - void writeCellTypes - ( - OFstream& flmaGeometryFile - ) const; - - void writeCells - ( - OFstream& flmaGeometryFile - ) const; - - void writeSelections - ( - OFstream& flmaGeometryFile - ) const; - -public: - - // Constructors - - //- Construct from polyMeshGen - flmaMesh(const polyMeshGen& mesh); - - - // Destructor - - ~flmaMesh(); - - - // Member Functions - - // Access - - // Check - - // Edit - - // Write - - void write(OFstream& flmaGeometryFile) const; -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.C b/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.C index 9d4b58bcb556306525c42411b1fa3c45c90dfcbe..24b6b12b91c0bcee8b4e09c40ab5016217c6594e 100644 --- a/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.C +++ b/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -51,52 +50,52 @@ Foam::fpmaMesh::~fpmaMesh() void Foam::fpmaMesh::writePoints(Foam::OFstream& fpmaGeometryFile) const { - fpmaGeometryFile << mesh_.points().size() << nl; - const pointFieldPMG& points = mesh_.points(); - forAll(points, pointI) - { - const point& p = points[pointI]; - fpmaGeometryFile << p.x() << ' ' << p.y() << ' ' << p.z() << ' '; - } - - fpmaGeometryFile << nl; + fpmaGeometryFile << mesh_.points().size() << nl; + const pointFieldPMG& points = mesh_.points(); + forAll(points, pointI) + { + const point& p = points[pointI]; + fpmaGeometryFile << p.x() << ' ' << p.y() << ' ' << p.z() << ' '; + } + + fpmaGeometryFile << nl; } void fpmaMesh::writeCells(OFstream& fpmaGeometryFile) const { - const cellListPMG& cells = mesh_.cells(); - - fpmaGeometryFile << cells.size() << nl; - forAll(cells, cellI) - { - const cell& c = cells[cellI]; - - fpmaGeometryFile << c.size(); - forAll(c, fI) - fpmaGeometryFile << ' ' << c[fI]; - fpmaGeometryFile << nl; - } + const cellListPMG& cells = mesh_.cells(); + + fpmaGeometryFile << cells.size() << nl; + forAll(cells, cellI) + { + const cell& c = cells[cellI]; + + fpmaGeometryFile << c.size(); + forAll(c, fI) + fpmaGeometryFile << ' ' << c[fI]; + fpmaGeometryFile << nl; + } } void Foam::fpmaMesh::writeFaces(OFstream& fpmaGeometryFile) const { - const faceListPMG& faces = mesh_.faces(); - fpmaGeometryFile << faces.size() << nl; - forAll(faces, faceI) - { - const face& f = faces[faceI]; - - fpmaGeometryFile << f.size(); - forAllReverse(f, pI) - fpmaGeometryFile << ' ' << f[pI]; - fpmaGeometryFile << nl; - } + const faceListPMG& faces = mesh_.faces(); + fpmaGeometryFile << faces.size() << nl; + forAll(faces, faceI) + { + const face& f = faces[faceI]; + + fpmaGeometryFile << f.size(); + forAllReverse(f, pI) + fpmaGeometryFile << ' ' << f[pI]; + fpmaGeometryFile << nl; + } } void Foam::fpmaMesh::writeSubsets(Foam::OFstream& fpmaGeometryFile) const { //- write patches as face selections - const PtrList<writePatch>& patches = mesh_.boundaries(); + const PtrList<boundaryPatch>& patches = mesh_.boundaries(); label nSubsets(0); @@ -112,7 +111,7 @@ void Foam::fpmaMesh::writeSubsets(Foam::OFstream& fpmaGeometryFile) const nSubsets += indices.size(); Info << "Mesh has " << indices.size() << " cell subsets" << endl; - fpmaGeometryFile << nSubsets << nl; + fpmaGeometryFile << nSubsets << nl; //- write patches as face selections forAll(patches, patchI) @@ -132,7 +131,7 @@ void Foam::fpmaMesh::writeSubsets(Foam::OFstream& fpmaGeometryFile) const mesh_.pointSubsetIndices(indices); forAll(indices, indexI) { - labelListPMG nodesInSubset; + labelLongList nodesInSubset; mesh_.pointsInSubset(indices[indexI], nodesInSubset); fpmaGeometryFile << mesh_.pointSubsetName(indices[indexI]) << nl; @@ -147,7 +146,7 @@ void Foam::fpmaMesh::writeSubsets(Foam::OFstream& fpmaGeometryFile) const mesh_.faceSubsetIndices(indices); forAll(indices, indexI) { - labelListPMG facesInSubset; + labelLongList facesInSubset; mesh_.facesInSubset(indices[indexI], facesInSubset); fpmaGeometryFile << mesh_.faceSubsetName(indices[indexI]) << nl; @@ -162,7 +161,7 @@ void Foam::fpmaMesh::writeSubsets(Foam::OFstream& fpmaGeometryFile) const mesh_.cellSubsetIndices(indices); forAll(indices, indexI) { - labelListPMG cellsInSubset; + labelLongList cellsInSubset; mesh_.cellsInSubset(indices[indexI], cellsInSubset); fpmaGeometryFile << mesh_.cellSubsetName(indices[indexI]) << nl; @@ -177,13 +176,13 @@ void Foam::fpmaMesh::writeSubsets(Foam::OFstream& fpmaGeometryFile) const void fpmaMesh::write(OFstream& fpmaGeometryFile) const { - writePoints(fpmaGeometryFile); - - writeFaces(fpmaGeometryFile); + writePoints(fpmaGeometryFile); + + writeFaces(fpmaGeometryFile); - writeCells(fpmaGeometryFile); + writeCells(fpmaGeometryFile); - writeSubsets(fpmaGeometryFile); + writeSubsets(fpmaGeometryFile); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.H b/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.H index 517dd7a031709e7705440e7e0580af15bfa9565c..879b4718ed29f8a5737c165f16107dd2229d01f1 100644 --- a/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.H +++ b/meshLibrary/utilities/dataConversion/foamToFPMA/fpmaMesh.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class fpmaMesh @@ -61,12 +60,12 @@ class fpmaMesh void operator=(const fpmaMesh&); void writePoints(OFstream& fpmaGeometryFile) const; - - void writeFaces(OFstream& fpmaGeometryFile) const; + + void writeFaces(OFstream& fpmaGeometryFile) const; void writeCells(OFstream& fpmaGeometryFile) const; - - void writeSubsets(OFstream& fpmaGeometryFile) const; + + void writeSubsets(OFstream& fpmaGeometryFile) const; public: diff --git a/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.C b/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.C index 92c8cd73e87c8064358f978d9d3cbd4ccb5a3abd..d7367bc42080ede754219deb73d92622f10bcc1a 100644 --- a/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.C +++ b/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description Translates FOAM mesh to AVL's FPMA format @@ -46,79 +45,79 @@ namespace Foam void writeMeshFPMA(const polyMeshGen& mesh, const word& fName) { - const Time& time = mesh.returnTime(); - + const Time& time = mesh.returnTime(); + const word postProcDir = "FPMA"; fileName postProcPath = time.path()/postProcDir; - if( !Foam::isDir(postProcPath) ) - { - mkDir(postProcPath); - } - - // Open the Case file - const fileName fpmaFileName = fName + ".fpma"; - - Info << "Writting mesh into " << fpmaFileName << endl; - -/* OFstream fpmaGeometryFile - ( - postProcPath/fpmaFileName, - IOstream::ASCII, - IOstream::currentVersion, - IOstream::UNCOMPRESSED - ); + if( !Foam::isDir(postProcPath) ) + { + mkDir(postProcPath); + } + + // Open the Case file + const fileName fpmaFileName = fName + ".fpma"; + + Info << "Writting mesh into " << fpmaFileName << endl; + +/* OFstream fpmaGeometryFile + ( + postProcPath/fpmaFileName, + IOstream::ASCII, + IOstream::currentVersion, + IOstream::UNCOMPRESSED + ); */ - - OFstream fpmaGeometryFile(postProcPath/fpmaFileName); - - // Construct the EnSight mesh + + OFstream fpmaGeometryFile(postProcPath/fpmaFileName); + + // Construct the FIRE mesh fpmaMesh Mesh(mesh); - Mesh.write(fpmaGeometryFile); + Mesh.write(fpmaGeometryFile); } void createFIRESelections(polyMeshGen& mesh) { if( !Pstream::parRun() ) return; - + const faceListPMG& faces = mesh.faces(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh.procBoundaries(); - + //- create face selections from proc patches forAll(procBoundaries, patchI) { word sName = "InterFacesToProc"; sName += help::scalarToText(procBoundaries[patchI].neiProcNo()); const label sID = mesh.addFaceSubset(sName); - + label faceI = procBoundaries[patchI].patchStart(); const label end = faceI + procBoundaries[patchI].patchSize(); for(;faceI<end;++faceI) mesh.addFaceToSubset(sID, faceI); } - + //- create cell selections DynList<label> subsets; mesh.faceSubsetIndices(subsets); forAll(subsets, subsetI) { const word sName = mesh.faceSubsetName(subsets[subsetI]); - + if( sName.substr(0, 10) == "processor_" ) { const word newName = "Proc" + sName.substr(10, sName.size()-10); - - labelListPMG cellsInSubset; + + labelLongList cellsInSubset; mesh.cellsInSubset(subsets[subsetI], cellsInSubset); const label subsetID = mesh.addCellSubset(newName); forAll(cellsInSubset, i) mesh.addCellToSubset(subsetID, cellsInSubset[i]); } } - + //- creating node selections boolList bndVertex(mesh.points().size(), false); forAll(mesh.boundaries(), patchI) @@ -128,24 +127,24 @@ void createFIRESelections(polyMeshGen& mesh) for(;faceI<end;++faceI) { const face& f = mesh.faces()[faceI]; - + forAll(f, pI) bndVertex[f[pI]] = true; } } - + forAll(procBoundaries, patchI) { word sName = "InterSurfaceEdgesToProc"; sName += help::scalarToText(procBoundaries[patchI].neiProcNo()); const label subsetID = mesh.addPointSubset(sName); - + label faceI = procBoundaries[patchI].patchStart(); const label end = faceI + procBoundaries[patchI].patchSize(); for(;faceI<end;++faceI) { const face& f = faces[faceI]; - + forAll(f, pI) { if( bndVertex[f[pI]] ) diff --git a/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.H b/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.H index f22ed000136b16adab6dcf9191b62a466da02868..a96feeee244aff86342dbd0523e5495a1248f407 100644 --- a/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.H +++ b/meshLibrary/utilities/dataConversion/foamToFPMA/writeMeshFPMA.H @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class writeMeshFPMA Description - Write mesh into fpma format + Write mesh into fpma format SourceFiles writeMeshFPMA.C diff --git a/meshLibrary/utilities/dataConversion/octreeToEnsight/octreeMesh.C b/meshLibrary/utilities/dataConversion/octreeToEnsight/octreeMesh.C deleted file mode 100644 index 230ae7d333de585e687b8c6236a87ca6eb060e66..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToEnsight/octreeMesh.C +++ /dev/null @@ -1,226 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -\*---------------------------------------------------------------------------*/ - -#include "octreeMesh.H" -#include "cellModeller.H" -#include "IOmanip.H" - -namespace Foam -{ - -// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from meshOctree -Foam::octreeMesh::octreeMesh(const meshOctree& octree) -: - points_(3*octree.numberOfLeaves()), - boxes_(octree.numberOfLeaves()), - useBox_(octree.numberOfLeaves(), true), - octree_(octree) -{ - createPointsAndCells(); -} - -// Construct from meshOctree and cube type -Foam::octreeMesh::octreeMesh -( - const meshOctree& octree, - const direction cubeType -) -: - points_(3*octree.numberOfLeaves()), - boxes_(octree.numberOfLeaves()), - useBox_(octree.numberOfLeaves(), false), - octree_(octree) -{ - label i, nLeaves = octree.numberOfLeaves(); - for(i=0;i<nLeaves;++i) - if( octree_.returnLeaf(i).cubeType() & cubeType ) - useBox_[i] = true; - - createPointsAndCells(); -} - - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -Foam::octreeMesh::~octreeMesh() -{} - - -// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // - -void octreeMesh::createPointsAndCells() -{ - label boxI, nLeaves = octree_.numberOfLeaves(); - - const cellModel& hex = *cellModeller::lookup("hex"); - const boundBox& rootBox = octree_.rootBox(); - Info << "Root box for writting octree " << rootBox << endl; - - label pointI(0), boxJ(0); - - for(boxI=0;boxI<nLeaves;++boxI) - if( useBox_[boxI] ) - { - labelList cv(8); - - const meshOctreeCubeBasic& c = octree_.returnLeaf(boxI); - FixedList<point, 8> vrt; - c.vertices(rootBox, vrt); - - forAll(vrt, vI) - { - points_.newElmt(pointI) = vrt[vI]; - switch( vI ) - { - case 0: - { - cv[4] = pointI; - break; - } - case 1: - { - cv[5] = pointI; - break; - } - case 2: - { - cv[0] = pointI; - break; - } - case 3: - { - cv[1] = pointI; - break; - } - case 4: - { - cv[7] = pointI; - break; - } - case 5: - { - cv[6] = pointI; - break; - } - case 6: - { - cv[3] = pointI; - break; - } - case 7: - { - cv[2] = pointI; - break; - } - }; - - ++pointI; - } - - boxes_[boxJ++] = cellShape(hex, cv); - } - - points_.setSize(pointI); - boxes_.setSize(boxJ); -} - -void Foam::octreeMesh::writePoints -( - const Foam::scalarField& pointsComponent, - Foam::OFstream& ensightGeometryFile -) const -{ - forAll(pointsComponent, pointi) - { - ensightGeometryFile << setw(12) << pointsComponent[pointi] << nl; - } -} - -void Foam::octreeMesh::writeBoxes -( - OFstream& ensightGeometryFile -) const -{ - ensightGeometryFile << "hexa8" << nl << setw(10) << boxes_.size() << nl; - - forAll(boxes_, boxI) - { - const cellShape& box = boxes_[boxI]; - - forAll(box, pI) - ensightGeometryFile << setw(10) << box[pI] + 1; - - ensightGeometryFile << nl; - } -} - - -void octreeMesh::write -( - OFstream& ensightGeometryFile -) const -{ - // Set Format - ensightGeometryFile.setf - ( - ios_base::scientific, - ios_base::floatfield - ); - ensightGeometryFile.precision(5); - - ensightGeometryFile - << "FOAM Geometry File " << nl << nl - << "node id assign" << nl - << "element id assign" << nl; - - ensightGeometryFile - << "part" << nl - << setw(10) << 1 << nl - << "FOAM cells" << nl - << "coordinates" << nl - << setw(10) << points_.size() - << endl; - - for (direction d=0; d<vector::nComponents; d++) - { - writePoints(points_.component(d)(), ensightGeometryFile); - } - - writeBoxes - ( - ensightGeometryFile - ); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/octreeToEnsight/octreeMesh.H b/meshLibrary/utilities/dataConversion/octreeToEnsight/octreeMesh.H deleted file mode 100644 index f9ce6a9d982d13b268ea1bf66054d51e59e745cb..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToEnsight/octreeMesh.H +++ /dev/null @@ -1,126 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - octreeMesh - -Description - -SourceFiles - octreeMesh.C - -\*---------------------------------------------------------------------------*/ - -#ifndef octreeMesh_H -#define octreeMesh_H - -#include "meshOctree.H" -#include "polyMeshGen.H" -#include "cellShapeList.H" -#include "OFstream.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -/*---------------------------------------------------------------------------*\ - Class octreeMesh Declaration -\*---------------------------------------------------------------------------*/ - -class octreeMesh -{ - // Private data - //- points - pointField points_; - - cellShapeList boxes_; - - boolList useBox_; - - // Private Member Functions - - //- Disallow default bitwise copy construct - octreeMesh(const octreeMesh&); - - //- Disallow default bitwise assignment - void operator=(const octreeMesh&); - - void writePoints - ( - const scalarField& pointsComponent, - OFstream& ensightGeometryFile - ) const; - - void writeBoxes - ( - OFstream& ensightGeometryFile - ) const; - - void createPointsAndCells(); -public: - - // Public data - - const meshOctree& octree_; - - // Constructors - - //- Construct from meshOctree - octreeMesh(const meshOctree& octree); - - //- Construct from meshOctree and cube type - octreeMesh(const meshOctree& octree, const direction cubeType); - - // Destructor - - ~octreeMesh(); - - - // Member Functions - - // Access - - // Check - - // Edit - - // Write - - void write - ( - OFstream& ensightGeometryFile - ) const; -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/octreeToEnsight/writeOctreeEnsight.C b/meshLibrary/utilities/dataConversion/octreeToEnsight/writeOctreeEnsight.C deleted file mode 100644 index 54055f4a891f8b83fe5221932b5a065195564345..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToEnsight/writeOctreeEnsight.C +++ /dev/null @@ -1,203 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Description - Translates octree to EnSight format - -\*---------------------------------------------------------------------------*/ - -#include "objectRegistry.H" -#include "meshOctree.H" -#include "OFstream.H" -#include "IOmanip.H" -#include "fileName.H" - -#include "octreeMesh.H" -#include "writeOctreeEnsight.H" - -#include <sstream> - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void writeOctreeEnsight(const meshOctree& octree, const word& fName) -{ - const word postProcDir = "EnSight"+fName; - const word prepend = fName + '.'; - Serr << "Writting mesh into " << postProcDir << endl; - - fileName postProcPath; - if( Pstream::parRun() ) - { - std::ostringstream ss; - ss << Pstream::myProcNo(); - postProcPath = "processor"+ss.str()/postProcDir; - } - else - { - postProcPath = postProcDir; - } - - if( Foam::isDir(postProcPath) ) - { - rmDir(postProcPath); - } - - mkDir(postProcPath); - - // Open the Case file - fileName ensightCaseFileName = prepend + "case"; - -/* OFstream ensightCaseFile - ( - postProcPath/ensightCaseFileName, - IOstream::ASCII, - IOstream::currentVersion, - IOstream::UNCOMPRESSED - ); -*/ - OFstream ensightCaseFile(postProcPath/ensightCaseFileName); - - Serr<< nl << "Case file is " << ensightCaseFileName << endl; - -/* OFstream ensightGeometryFile - ( - postProcPath/prepend+"000.mesh", - IOstream::ASCII, - IOstream::currentVersion, - IOstream::UNCOMPRESSED - ); -*/ - OFstream ensightGeometryFile(postProcPath/prepend+"000.mesh"); - - // Construct the EnSight mesh - octreeMesh eMesh(octree); - eMesh.write(ensightGeometryFile); - - //- write the case file - ensightCaseFile << "FORMAT" << nl; - ensightCaseFile << "type: ensight gold" << nl << nl; - - word geomCaseFileName = prepend + "000"; - - // test pre check variable if there is a moving mesh - ensightCaseFile - << "GEOMETRY" << nl - << "model: 1 " - << (geomCaseFileName + ".mesh").c_str() << nl; - - ensightCaseFile << nl << "TIME" << nl - << "time set: " << 1 << nl - << "number of steps: " << 1 << nl - << "filename start number: " << 0 << nl - << "filename increment: " << 1 << nl; - - ensightCaseFile << "time values: 0" << nl; - - ensightCaseFile.setf(ios_base::scientific, ios_base::floatfield); - ensightCaseFile.precision(5); -} - -void writeOctreeEnsight -( - const meshOctree& octree, - const word& fName, - const direction cubeType -) -{ - //const Time& time = mesh.returnRegistry().time(); - - const word postProcDir = "EnSight"+fName; - const word prepend = fName + '.'; - Info << "Writting mesh into " << postProcDir << endl; - - fileName postProcPath = postProcDir; - - if( Foam::isDir(postProcPath)) - { - rmDir(postProcPath); - } - - mkDir(postProcPath); - - // Open the Case file - fileName ensightCaseFileName = prepend + "case"; - -/* OFstream ensightCaseFile - ( - postProcPath/ensightCaseFileName, - IOstream::ASCII, - IOstream::currentVersion, - IOstream::UNCOMPRESSED - ); -*/ - OFstream ensightCaseFile(postProcPath/ensightCaseFileName); - - Info<< nl << "Case file is " << ensightCaseFileName << endl; - -/* OFstream ensightGeometryFile - ( - postProcPath/prepend+"000.mesh", - IOstream::ASCII, - IOstream::currentVersion, - IOstream::UNCOMPRESSED - ); -*/ - OFstream ensightGeometryFile(postProcPath/prepend+"000.mesh"); - - // Construct the EnSight mesh - octreeMesh eMesh(octree, cubeType); - eMesh.write(ensightGeometryFile); - - //- write the case file - ensightCaseFile << "FORMAT" << nl; - ensightCaseFile << "type: ensight gold" << nl << nl; - - word geomCaseFileName = prepend + "000"; - if (Pstream::master()) - { - // test pre check variable if there is a moving mesh - ensightCaseFile - << "GEOMETRY" << nl - << "model: 1 " - << (geomCaseFileName + ".mesh").c_str() << nl; - } - - ensightCaseFile << nl << "TIME" << nl - << "time set: " << 1 << nl - << "number of steps: " << 1 << nl - << "filename start number: " << 0 << nl - << "filename increment: " << 1 << nl; - - ensightCaseFile << "time values:" << nl; - - ensightCaseFile.setf(ios_base::scientific, ios_base::floatfield); - ensightCaseFile.precision(5); -} - -} - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/octreeToEnsight/writeOctreeEnsight.H b/meshLibrary/utilities/dataConversion/octreeToEnsight/writeOctreeEnsight.H deleted file mode 100644 index 432e3b21808960d86839e7c5af9f839cb675a3f8..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToEnsight/writeOctreeEnsight.H +++ /dev/null @@ -1,69 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - writeOctreeMesh - -Description - -SourceFiles - writeOctreeEnsight.C - -\*---------------------------------------------------------------------------*/ - -#ifndef writeOctreeMesh_H -#define writeOctreeMesh_H - -#include "OFstream.H" -#include "word.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -class meshOctree; - -void writeOctreeEnsight -( - const meshOctree& octree, - const word& fName -); - -void writeOctreeEnsight -( - const meshOctree& octree, - const word& fName, - const direction cubeType -); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/octreeToFPMA/octreeMeshFPMA.C b/meshLibrary/utilities/dataConversion/octreeToFPMA/octreeMeshFPMA.C deleted file mode 100644 index 19c9efdedcc8a0d1acfa8a532a8c729d779250d2..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToFPMA/octreeMeshFPMA.C +++ /dev/null @@ -1,192 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -\*---------------------------------------------------------------------------*/ - -#include "octreeMeshFPMA.H" -#include "IOmanip.H" - -namespace Foam -{ - -// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from meshOctree -Foam::octreeMeshFPMA::octreeMeshFPMA -( - const meshOctree& octree, - const dictionary& dict -) -: - addressing_(octree, dict, false) -{ - addressing_.boxType(); - for(label leafI=0;leafI<octree.numberOfLeaves();++leafI) - addressing_.setBoxType(leafI, meshOctreeAddressing::MESHCELL); -} - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -Foam::octreeMeshFPMA::~octreeMeshFPMA() -{} - - -// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // - -void Foam::octreeMeshFPMA::writePoints -( - Foam::OFstream& fpmaGeometryFile -) const -{ - const pointField& points = addressing_.octreePoints(); - fpmaGeometryFile << points.size() << nl; - - forAll(points, pointI) - { - const point& p = points[pointI]; - fpmaGeometryFile << p.x() << ' ' << p.y() << ' ' << p.z() << ' '; - } - - fpmaGeometryFile << nl; -} - -void octreeMeshFPMA::writeCells -( - OFstream& fpmaGeometryFile -) const -{ - const VRWGraph& cells = addressing_.leafFaces(); - - fpmaGeometryFile << cells.size() << nl; - forAll(cells, cellI) - { - fpmaGeometryFile << cells.sizeOfRow(cellI); - forAllRow(cells, cellI, fI) - fpmaGeometryFile << ' ' << cells(cellI, fI); - fpmaGeometryFile << nl; - } -} - -void Foam::octreeMeshFPMA::writeFaces -( - OFstream& fpmaGeometryFile -) const -{ - const VRWGraph& faces = addressing_.octreeFaces(); - fpmaGeometryFile << faces.size() << nl; - forAll(faces, faceI) - { - const constRow f = faces[faceI]; - - fpmaGeometryFile << f.size(); - forAllReverse(f, pI) - fpmaGeometryFile << ' ' << f[pI]; - fpmaGeometryFile << nl; - } -} - -void Foam::octreeMeshFPMA::writeSelections -( - Foam::OFstream& fpmaGeometryFile -) const -{ - fpmaGeometryFile << 4 << nl; - //- create outside selection - fpmaGeometryFile << "Outside" << nl << 2 << nl; - labelListPMG selBoxes; - const meshOctree& octree = addressing_.octree(); - for(label i=0;i<octree.numberOfLeaves();++i) - { - if( octree.returnLeaf(i).cubeType() & meshOctreeCube::OUTSIDE ) - selBoxes.append(i); - } - fpmaGeometryFile << selBoxes.size() << nl; - forAll(selBoxes, boxI) - fpmaGeometryFile << selBoxes[boxI] << ' '; - fpmaGeometryFile << nl; - - //- create inside selection - fpmaGeometryFile << "Inside" << nl << 2 << nl; - selBoxes.clear(); - for(label i=0;i<octree.numberOfLeaves();++i) - { - if( octree.hasContainedTriangles(i) ) - continue; - if( octree.returnLeaf(i).cubeType() & meshOctreeCube::INSIDE ) - selBoxes.append(i); - } - fpmaGeometryFile << selBoxes.size() << nl; - forAll(selBoxes, boxI) - fpmaGeometryFile << selBoxes[boxI] << ' '; - fpmaGeometryFile << nl; - - //- create unknown selection - fpmaGeometryFile << "Unknown" << nl << 2 << nl; - selBoxes.clear(); - for(label i=0;i<octree.numberOfLeaves();++i) - { - if( octree.returnLeaf(i).cubeType() & meshOctreeCube::UNKNOWN ) - selBoxes.append(i); - } - fpmaGeometryFile << selBoxes.size() << nl; - forAll(selBoxes, boxI) - fpmaGeometryFile << selBoxes[boxI] << ' '; - fpmaGeometryFile << nl; - - //- create DATA selection - fpmaGeometryFile << "Data" << nl << 2 << nl; - selBoxes.clear(); - for(label i=0;i<octree.numberOfLeaves();++i) - { - if( octree.hasContainedTriangles(i) ) - selBoxes.append(i); - } - fpmaGeometryFile << selBoxes.size() << nl; - forAll(selBoxes, boxI) - fpmaGeometryFile << selBoxes[boxI] << ' '; - fpmaGeometryFile << nl; -} - - -void octreeMeshFPMA::write -( - OFstream& fpmaGeometryFile -) const -{ - writePoints(fpmaGeometryFile); - - writeFaces(fpmaGeometryFile); - - writeCells(fpmaGeometryFile); - - writeSelections(fpmaGeometryFile); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/octreeToFPMA/octreeMeshFPMA.H b/meshLibrary/utilities/dataConversion/octreeToFPMA/octreeMeshFPMA.H deleted file mode 100644 index 93b22b714444b272e45d1f340b5e2de659c1dec3..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToFPMA/octreeMeshFPMA.H +++ /dev/null @@ -1,123 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - octreeMesh - -Description - -SourceFiles - octreeMesh.C - -\*---------------------------------------------------------------------------*/ - -#ifndef octreeMeshFPMA_H -#define octreeMeshFPMA_H - -#include "meshOctree.H" -#include "meshOctreeAddressing.H" -#include "polyMeshGen.H" -#include "OFstream.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -/*---------------------------------------------------------------------------*\ - Class octreeMeshFPMA Declaration -\*---------------------------------------------------------------------------*/ - -class octreeMeshFPMA -{ - // Private data - //- octree addressing - meshOctreeAddressing addressing_; - - // Private Member Functions - - //- Disallow default bitwise copy construct - octreeMeshFPMA(const octreeMeshFPMA&); - - //- Disallow default bitwise assignment - void operator=(const octreeMeshFPMA&); - - void writePoints - ( - OFstream& fpmaGeometryFile - ) const; - - void writeFaces - ( - OFstream& fpmaGeometryFile - ) const; - - void writeCells - ( - OFstream& fpmaGeometryFile - ) const; - - void writeSelections - ( - OFstream& fpmaGeometryFile - ) const; - -public: - - // Constructors - - //- Construct from meshOctree - octreeMeshFPMA(const meshOctree& octree, const dictionary& dict); - - // Destructor - - ~octreeMeshFPMA(); - - - // Member Functions - - // Access - - // Check - - // Edit - - // Write - - void write - ( - OFstream& fpmaGeometryFile - ) const; -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/octreeToFPMA/writeOctreeFPMA.C b/meshLibrary/utilities/dataConversion/octreeToFPMA/writeOctreeFPMA.C deleted file mode 100644 index 154200fd460304cfada703fc6e6d588430bfa2c5..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToFPMA/writeOctreeFPMA.C +++ /dev/null @@ -1,85 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Description - Translates octree to EnSight format - -\*---------------------------------------------------------------------------*/ - -#include "objectRegistry.H" -#include "meshOctree.H" -#include "OFstream.H" -#include "IOmanip.H" -#include "fileName.H" - -#include "octreeMeshFPMA.H" -#include "writeOctreeFPMA.H" - -#include <sstream> - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -void writeOctreeFPMA(const meshOctree& octree, const word& fName) -{ - const word postProcDir = "FPMA"; - - const word prepend = fName + '.'; - Serr << "Writting mesh into " << postProcDir << endl; - - fileName postProcPath; - if( Pstream::parRun() ) - { - std::ostringstream ss; - ss << Pstream::myProcNo(); - postProcPath = "processor"+ss.str()/postProcDir; - } - else - { - postProcPath = postProcDir; - } - - if( !Foam::isDir(postProcPath) ) - { - mkDir(postProcPath); - } - - // Open the Case file - const fileName fpmaFileName = fName + ".fpma"; - - Info << "Writting octree into " << fpmaFileName << endl; - - OFstream fpmaGeometryFile(postProcPath/fpmaFileName); - - // Construct the octree mesh - dictionary dict; - octreeMeshFPMA Mesh(octree, dict); - Mesh.write(fpmaGeometryFile); -} - -} - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/octreeToFPMA/writeOctreeFPMA.H b/meshLibrary/utilities/dataConversion/octreeToFPMA/writeOctreeFPMA.H deleted file mode 100644 index 1f42f828bef770221e6e75cb0d68fc609cd6f8e2..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/octreeToFPMA/writeOctreeFPMA.H +++ /dev/null @@ -1,62 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - writeOctreeFPMA - -Description - -SourceFiles - writeOctreeFPMA.C - -\*---------------------------------------------------------------------------*/ - -#ifndef writeOctreeFPMA_H -#define writeOctreeFPMA_H - -#include "OFstream.H" -#include "word.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -class meshOctree; - -void writeOctreeFPMA -( - const meshOctree& octree, - const word& fName -); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/simplexToFLMA/simplexMesh.C b/meshLibrary/utilities/dataConversion/simplexToFLMA/simplexMesh.C deleted file mode 100644 index 81f2af94d82cf7d00f2139c2196e68e55d749792..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/simplexToFLMA/simplexMesh.C +++ /dev/null @@ -1,113 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -\*---------------------------------------------------------------------------*/ - -#include "simplexMesh.H" -#include "IOmanip.H" - -namespace Foam -{ - -// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // - -void Foam::simplexMesh::writePoints(Foam::OFstream& flmaGeometryFile) const -{ - flmaGeometryFile << mesh_.pts().size() << nl; - const DynList<point, 128>& points = mesh_.pts(); - forAll(points, pointI) - { - const point& p = points[pointI]; - flmaGeometryFile << p.x() << ' ' << p.y() << ' ' << p.z() << ' '; - } - - flmaGeometryFile << nl; -} - -void simplexMesh::writeCells(OFstream& flmaGeometryFile) const -{ - const DynList<partTet, 128>& tets = mesh_.tets(); - - flmaGeometryFile << tets.size() << nl; - - forAll(tets, tetI) - { - const partTet& tet = tets[tetI]; - flmaGeometryFile << 4; - for(label i=0;i<4;++i) - flmaGeometryFile << ' ' << tet[i]; - flmaGeometryFile << nl; - } -} - -void Foam::simplexMesh::writeCellTypes(OFstream& flmaGeometryFile) const -{ - const DynList<partTet, 128>& tets = mesh_.tets(); - flmaGeometryFile << nl << tets.size() << nl; - forAll(tets, tetI) - flmaGeometryFile << 4 << nl; - flmaGeometryFile << nl; -} - -void Foam::simplexMesh::writeSelections(Foam::OFstream& flmaGeometryFile) const -{ - flmaGeometryFile << 0; -} - -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from partTetMeshSimplex -Foam::simplexMesh::simplexMesh(const partTetMeshSimplex& mesh) -: - mesh_(mesh) -{} - - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -Foam::simplexMesh::~simplexMesh() -{} - - -// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // - -void simplexMesh::write -( - OFstream& flmaGeometryFile -) const -{ - writePoints(flmaGeometryFile); - - writeCells(flmaGeometryFile); - - writeCellTypes(flmaGeometryFile); - - writeSelections(flmaGeometryFile); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/simplexToFLMA/simplexMesh.H b/meshLibrary/utilities/dataConversion/simplexToFLMA/simplexMesh.H deleted file mode 100644 index 4341a75df45cddf77f343c27865de71d6fbc673a..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/simplexToFLMA/simplexMesh.H +++ /dev/null @@ -1,121 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - simplexMesh - -Description - -SourceFiles - simplexMesh.C - -\*---------------------------------------------------------------------------*/ - -#ifndef simplexMesh_H -#define simplexMesh_H - -#include "partTetMeshSimplex.H" -#include "OFstream.H" -#include "Map.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -/*---------------------------------------------------------------------------*\ - Class simplexMesh Declaration -\*---------------------------------------------------------------------------*/ - -class simplexMesh -{ - // Private data - - //- Reference to the simplex - const partTetMeshSimplex& mesh_; - - // Private Member Functions - - //- Disallow default bitwise copy construct - simplexMesh(const simplexMesh&); - - //- Disallow default bitwise assignment - void operator=(const simplexMesh&); - - void writePoints - ( - OFstream& flmaGeometryFile - ) const; - - void writeCellTypes - ( - OFstream& flmaGeometryFile - ) const; - - void writeCells - ( - OFstream& flmaGeometryFile - ) const; - - void writeSelections - ( - OFstream& flmaGeometryFile - ) const; - -public: - - // Constructors - - //- Construct from partTetMeshSimplex - simplexMesh(const partTetMeshSimplex& mesh); - - - // Destructor - - ~simplexMesh(); - - - // Member Functions - - // Access - - // Check - - // Edit - - // Write - - void write(OFstream& flmaGeometryFile) const; -}; - - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/dataConversion/simplexToFLMA/writeSimplexFLMA.H b/meshLibrary/utilities/dataConversion/simplexToFLMA/writeSimplexFLMA.H deleted file mode 100644 index 2413ad473892206a0272e9d7b6622adf3b907aea..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/dataConversion/simplexToFLMA/writeSimplexFLMA.H +++ /dev/null @@ -1,59 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - writeSimplexFLMA - -Description - Write a partTetMeshSimplex into flma format - -SourceFiles - writeSimplexFLMA.C - -\*---------------------------------------------------------------------------*/ - -#ifndef writeSimplexFLMA_H -#define writeSimplexFLMA_H - -#include "OFstream.H" -#include "word.H" - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -namespace Foam -{ - -class partTetMeshSimplex; - -void writeSimplexFLMA(const partTetMeshSimplex& simplex, const word& fName); - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/decomposeCells/decomposeCells.C b/meshLibrary/utilities/decomposeCells/decomposeCells.C index 9bb35507d476ef7728279fcce912776bee3431c0..108f6f768943fc21c3bdf668580048f6d7a59af2 100644 --- a/meshLibrary/utilities/decomposeCells/decomposeCells.C +++ b/meshLibrary/utilities/decomposeCells/decomposeCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,7 +40,7 @@ decomposeCells::decomposeCells(polyMeshGen& mesh) newBoundaryPatches_(), facesOfNewCells_() { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) patchNames_[patchI] = boundaries[patchI].patchName(); } diff --git a/meshLibrary/utilities/decomposeCells/decomposeCells.H b/meshLibrary/utilities/decomposeCells/decomposeCells.H index d63d1a4615adddcb83bca05d924d6e937ab8aed1..6ba1d705dd324b5abd16a0f9018151f13c6ceabc 100644 --- a/meshLibrary/utilities/decomposeCells/decomposeCells.H +++ b/meshLibrary/utilities/decomposeCells/decomposeCells.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class decomposeCells @@ -50,17 +49,17 @@ namespace Foam class decomposeCells { // private data - //- reference to the mesh - polyMeshGen& mesh_; - - //- new boundary faces - wordList patchNames_; - VRWGraph newBoundaryFaces_; - labelListPMG newBoundaryPatches_; - - VRWGraphList facesOfNewCells_; - - // Private member functions + //- reference to the mesh + polyMeshGen& mesh_; + + //- new boundary faces + wordList patchNames_; + VRWGraph newBoundaryFaces_; + labelLongList newBoundaryPatches_; + + VRWGraphList facesOfNewCells_; + + // Private member functions //- check if the valid pyramids are generated from the split cells //- this check splits faces which could @@ -68,33 +67,33 @@ class decomposeCells void checkFaceConnections(const boolList& decomposeCell); //- create addressing needed to decompose the cell - void findAddressingForCell - ( - const label cellI, - DynList<label, 32>& vrt, - DynList<edge, 64>& edges, - DynList<DynList<label, 8> >& faceEdges, - DynList<DynList<label, 2>, 64>& edgeFaces - ) const; - + void findAddressingForCell + ( + const label cellI, + DynList<label, 32>& vrt, + DynList<edge, 64>& edges, + DynList<DynList<label, 8> >& faceEdges, + DynList<DynList<label, 2>, 64>& edgeFaces + ) const; + //- find the apex of the pyramids - label findTopVertex - ( - const label cellI, - const DynList<label, 32>& vrt, - const DynList<edge, 64>& edges, - const DynList<DynList<label, 2>, 64>& edgeFaces - ); - - void decomposeCellIntoPyramids(const label cellI); - - void createPointsAndCellFaces(const boolList& decomposeCell); - - void storeBoundaryFaces(const boolList& decomposeCell); - - void removeDecomposedCells(const boolList& decomposeCell); - - void addNewCells(); + label findTopVertex + ( + const label cellI, + const DynList<label, 32>& vrt, + const DynList<edge, 64>& edges, + const DynList<DynList<label, 2>, 64>& edgeFaces + ); + + void decomposeCellIntoPyramids(const label cellI); + + void createPointsAndCellFaces(const boolList& decomposeCell); + + void storeBoundaryFaces(const boolList& decomposeCell); + + void removeDecomposedCells(const boolList& decomposeCell); + + void addNewCells(); //- disallows bitwise construct void operator=(const decomposeCells&); @@ -105,17 +104,17 @@ class decomposeCells public: // Constructors - //- construct from polyMeshGen and a list containing patches - //- for each point - decomposeCells(polyMeshGen& mesh); + //- construct from polyMeshGen and a list containing patches + //- for each point + decomposeCells(polyMeshGen& mesh); //- Destructor ~decomposeCells(); // Member functions - //- perform decomposition of selected cell into pyramids - void decomposeMesh(const boolList&); + //- perform decomposition of selected cell into pyramids + void decomposeMesh(const boolList&); }; diff --git a/meshLibrary/utilities/decomposeCells/decomposeCellsDecomposition.C b/meshLibrary/utilities/decomposeCells/decomposeCellsDecomposition.C index 45cd9281a51d3c37a46c8c64c8d87607b69fd791..c04ef94919c7ee1022ac0e37811baebf46c99497 100644 --- a/meshLibrary/utilities/decomposeCells/decomposeCellsDecomposition.C +++ b/meshLibrary/utilities/decomposeCells/decomposeCellsDecomposition.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,14 +30,10 @@ Description #include "polyMeshGenAddressing.H" #include "meshSurfaceEngine.H" #include "decomposeFaces.H" -#include "labelListPMG.H" +#include "labelLongList.H" //#define DEBUGDecompose -# ifdef DEBUGDecompose -#include "writeMeshEnsight.H" -# endif - // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam @@ -58,7 +53,6 @@ void decomposeCells::decomposeMesh(const boolList& decomposeCell) # ifdef DEBUGDecompose mesh_.addressingData().checkMesh(); - writeMeshEnsight(mesh_, "decomposedMesh"); # endif } @@ -75,7 +69,6 @@ void decomposeCells::checkFaceConnections(const boolList& decomposeCell) DynList<label, 32> vrt; DynList<edge, 64> edges; DynList<DynList<label, 8> > faceEdges; - faceEdges.setSize(cells[cellI].size()); DynList<DynList<label, 2>, 64> edgeFaces; findAddressingForCell(cellI, vrt, edges, faceEdges, edgeFaces); @@ -106,7 +99,7 @@ void decomposeCells::checkFaceConnections(const boolList& decomposeCell) if( Pstream::parRun() ) { - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); //- send information to the neighbour processor @@ -209,7 +202,7 @@ void decomposeCells::addNewCells() const labelList& owner = mesh_.owner(); const VRWGraph& pointFaces = mesh_.addressingData().pointFaces(); - labelListPMG newBoundaryOwners; + labelLongList newBoundaryOwners; forAll(newBoundaryFaces_, faceI) { @@ -254,7 +247,8 @@ void decomposeCells::addNewCells() newBoundaryPatches_ ); - polyMeshGenModifier(mesh_).removeUnusedVertices(); + polyMeshGenModifier(mesh_).removeUnusedVertices(); + polyMeshGenModifier(mesh_).clearAll(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/decomposeCells/decomposeCellsPyramids.C b/meshLibrary/utilities/decomposeCells/decomposeCellsPyramids.C index 12dffedfa29045dcd8a087a0c9468fe48a6f8862..669e4d7374f62c8ed4dacbb2f5e1b64b7b411d7b 100644 --- a/meshLibrary/utilities/decomposeCells/decomposeCellsPyramids.C +++ b/meshLibrary/utilities/decomposeCells/decomposeCellsPyramids.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,18 +35,24 @@ Description namespace Foam { - + void decomposeCells::findAddressingForCell ( - const label cellI, - DynList<label, 32>& vrt, - DynList<edge, 64>& edges, - DynList<DynList<label, 8> >& faceEdges, - DynList<DynList<label, 2>, 64>& edgeFaces + const label cellI, + DynList<label, 32>& vrt, + DynList<edge, 64>& edges, + DynList<DynList<label, 8> >& faceEdges, + DynList<DynList<label, 2>, 64>& edgeFaces ) const { - const cell& c = mesh_.cells()[cellI]; - const faceListPMG& faces = mesh_.faces(); + const cell& c = mesh_.cells()[cellI]; + + vrt.clear(); + edges.clear(); + edgeFaces.clear(); + faceEdges.setSize(c.size()); + + const faceListPMG& faces = mesh_.faces(); forAll(faceEdges, feI) { faceEdges[feI].setSize(faces[c[feI]].size()); @@ -56,11 +61,12 @@ void decomposeCells::findAddressingForCell forAll(c, fI) { - const face& f = faces[c[fI]]; - const edgeList edg = faces[c[fI]].edges(); + const face& f = faces[c[fI]]; - forAll(edg, eI) + forAll(f, eI) { + const edge e = f.faceEdge(eI); + bool store(true); forAll(vrt, vI) if( vrt[vI] == f[eI] ) @@ -72,13 +78,12 @@ void decomposeCells::findAddressingForCell { vrt.append(f[eI]); } - else - { - store = true; - } + + //- check if the edge alreready exists + store = true; forAll(edges, eJ) - if( edg[eI] == edges[eJ] ) + if( e == edges[eJ] ) { store = false; faceEdges[fI][eI] = eJ; @@ -92,7 +97,7 @@ void decomposeCells::findAddressingForCell DynList<label, 2> ef; ef.append(fI); edgeFaces.append(ef); - edges.append(edg[eI]); + edges.append(e); } } } @@ -101,41 +106,47 @@ void decomposeCells::findAddressingForCell forAll(edgeFaces, efI) if( edgeFaces[efI].size() != 2 ) { + forAll(c, fI) + Info << "Face " << c[fI] << " is " << faces[c[fI]] << endl; + Info << "Edges " << edges << endl; Info << "faceEdges " << faceEdges << endl; Info << "edgeFaces " << edgeFaces << endl; - mesh_.write(); + mesh_.write(); FatalErrorIn ( - "faceListList pMesh::decomposeCellIntoPyramids()" + "void decomposeCells::findAddressingForCell" + "(const label, DynList<label, 32>&, DynList<edge, 64>&" + ", DynList<DynList<label, 8> >&" + ", DynList<DynList<label, 2>, 64>&) const" ) << "Cell " << cellI << " is not topologically closed!" << abort(FatalError); - } + } } label decomposeCells::findTopVertex ( - const label cellI, - const DynList<label, 32>& vrt, - const DynList<edge, 64>& edges, - const DynList<DynList<label, 2>, 64>& edgeFaces + const label cellI, + const DynList<label, 32>& vrt, + const DynList<edge, 64>& edges, + const DynList<DynList<label, 2>, 64>& edgeFaces ) { - const cell& c = mesh_.cells()[cellI]; - const faceListPMG& faces = mesh_.faces(); - - pointFieldPMG& pointsAccess = mesh_.points(); - - //- there is no vertex in 3 or more patches - //- find boundary faces - label topVertex(-1); - + const cell& c = mesh_.cells()[cellI]; + const faceListPMG& faces = mesh_.faces(); + + pointFieldPMG& pointsAccess = mesh_.points(); + + //- there is no vertex in 3 or more patches + //- find boundary faces + label topVertex(-1); + const labelList cp = c.labels(faces); point p(vector::zero); forAll(cp, cpI) p += pointsAccess[cp[cpI]]; p /= cp.size(); - + topVertex = pointsAccess.size(); pointsAccess.append(p); @@ -143,39 +154,39 @@ label decomposeCells::findTopVertex Info << "Top vertex is " << topVertex << endl; # endif - return topVertex; + return topVertex; } void decomposeCells::decomposeCellIntoPyramids(const label cellI) { - const cellListPMG& cells = mesh_.cells(); - const faceListPMG& faces = mesh_.faces(); - const labelList& owner = mesh_.owner(); + const cellListPMG& cells = mesh_.cells(); + const faceListPMG& faces = mesh_.faces(); + const labelList& owner = mesh_.owner(); + + const cell& c = cells[cellI]; - const cell& c = cells[cellI]; - # ifdef DEBUGDecompose Info << "Starting decomposing cell " << cellI << endl; Info << "Cell consists of faces " << c << endl; - forAll(c, fI) - Info << "Face " << c[fI] << " is " << faces[c[fI]] << endl; + forAll(c, fI) + Info << "Face " << c[fI] << " is " << faces[c[fI]] << endl; # endif //- calculate edges, faceEdges and edgeFaces addressing - DynList<label, 32> vrt; + DynList<label, 32> vrt; DynList<edge, 64> edges; DynList<DynList<label, 8> > faceEdges; faceEdges.setSize(c.size()); DynList<DynList<label, 2>, 64> edgeFaces; - findAddressingForCell(cellI, vrt, edges, faceEdges, edgeFaces); + findAddressingForCell(cellI, vrt, edges, faceEdges, edgeFaces); // find a vertex which will be the top of the pyramids //- if there exist a corner vertex which is in 3 or more patches then //- it is selected as the top vertex label topVertex = findTopVertex(cellI, vrt, edges, edgeFaces); - + //- start generating pyramids - forAll(c, fI) + forAll(c, fI) { # ifdef DEBUGDecompose Info << "Face " << faces[c[fI]] << " is a base face" << endl; @@ -183,7 +194,7 @@ void decomposeCells::decomposeCellIntoPyramids(const label cellI) const face& f = faces[c[fI]]; DynList<DynList<label, 8> > cellFaces; cellFaces.setSize(f.size() + 1); - + DynList<triFace> triFaces; triFaces.setSize(f.size()); forAll(triFaces, pI) @@ -192,12 +203,12 @@ void decomposeCells::decomposeCellIntoPyramids(const label cellI) triFaces[pI][1] = f[pI]; triFaces[pI][2] = topVertex; } - + label cfI(0); if( owner[c[fI]] == cellI ) { cellFaces[cfI++] = faces[c[fI]]; - + forAll(triFaces, tfI) { cellFaces[cfI++] = triFaces[tfI]; @@ -214,12 +225,12 @@ void decomposeCells::decomposeCellIntoPyramids(const label cellI) rf[1] = triFaces[tfI][2]; rf[2] = triFaces[tfI][1]; cellFaces[cfI++] = rf; - } + } } - + # ifdef DEBUGDecompose Info << "Cell for face is " << cellFaces << endl; - + DynList<edge, 64> cEdges; DynList<DynList<label, 2>, 64> eFaces; forAll(cellFaces, fI) @@ -228,9 +239,9 @@ void decomposeCells::decomposeCellIntoPyramids(const label cellI) forAll(f, eI) { const edge e(f[eI], f[(eI+1)%f.size()]); - + const label pos = cEdges.contains(e); - + if( pos < 0 ) { cEdges.append(e); @@ -244,12 +255,12 @@ void decomposeCells::decomposeCellIntoPyramids(const label cellI) } } } - + forAll(eFaces, eI) if( eFaces[eI].size() != 2 ) Pout << "This pyrmid is not topologically closed" << endl; # endif - + facesOfNewCells_.appendGraph(cellFaces); } } diff --git a/meshLibrary/utilities/faceDecomposition/decomposeFaces.C b/meshLibrary/utilities/faceDecomposition/decomposeFaces.C index e58693aebffd54e4da13edb6332ee86ad0c0325e..6a627b7401e57693cdeda0d7ead293ea6b3d3635 100644 --- a/meshLibrary/utilities/faceDecomposition/decomposeFaces.C +++ b/meshLibrary/utilities/faceDecomposition/decomposeFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,7 +29,9 @@ Description #include "decomposeFaces.H" #include "boolList.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGDec @@ -49,13 +50,11 @@ decomposeFaces::decomposeFaces(polyMeshGen& mesh) : mesh_(mesh), newFacesForFace_(mesh_.faces().size()) -{ -} +{} //- Destructor decomposeFaces::~decomposeFaces() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -130,7 +129,7 @@ void decomposeFaces::decomposeMeshFaces(const boolList& decomposeFace) } //- decompose boundary faces - PtrList<writePatch>& boundaries = meshModifier.boundariesAccess(); + PtrList<boundaryPatch>& boundaries = meshModifier.boundariesAccess(); forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); @@ -187,7 +186,7 @@ void decomposeFaces::decomposeMeshFaces(const boolList& decomposeFace) //- decompose processor faces if( Pstream::parRun() ) { - PtrList<writeProcessorPatch>& procBoundaries = + PtrList<processorBoundaryPatch>& procBoundaries = meshModifier.procBoundariesAccess(); forAll(procBoundaries, patchI) @@ -287,7 +286,9 @@ void decomposeFaces::decomposeMeshFaces(const boolList& decomposeFace) //- change the mesh cellListPMG& cells = meshModifier.cellsAccess(); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(cells, cellI) { cell& c = cells[cellI]; @@ -309,7 +310,7 @@ void decomposeFaces::decomposeMeshFaces(const boolList& decomposeFace) c.setSize(newC.size()); forAll(newC, fJ) c[fJ] = newC[fJ]; - } + } meshModifier.clearAll(); @@ -428,7 +429,7 @@ void decomposeFaces::decomposeConcaveInternalFaces } } - PtrList<writePatch>& boundaries = meshModifier.boundariesAccess(); + PtrList<boundaryPatch>& boundaries = meshModifier.boundariesAccess(); forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); @@ -460,7 +461,9 @@ void decomposeFaces::decomposeConcaveInternalFaces //- update cells cellListPMG& cells = meshModifier.cellsAccess(); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(cells, cellI) { cell& c = cells[cellI]; diff --git a/meshLibrary/utilities/faceDecomposition/decomposeFaces.H b/meshLibrary/utilities/faceDecomposition/decomposeFaces.H index cac7194d2e2b7fe7eef50626138ff0633aa273ef..ea4aeb4dbb4c8f22ae57ca09c2e1772f6a26dd1c 100644 --- a/meshLibrary/utilities/faceDecomposition/decomposeFaces.H +++ b/meshLibrary/utilities/faceDecomposition/decomposeFaces.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class decomposeFaces @@ -49,11 +48,11 @@ namespace Foam class decomposeFaces { // private data - //- reference to the mesh - polyMeshGen& mesh_; - - //- number of points - VRWGraph newFacesForFace_; + //- reference to the mesh + polyMeshGen& mesh_; + + //- number of points + VRWGraph newFacesForFace_; //- disallows bitwise construct void operator=(const decomposeFaces&); @@ -72,11 +71,11 @@ public: ~decomposeFaces(); // Member functions - //- decompose selected faces into triangles using midnode subdivision - void decomposeMeshFaces(const boolList& decomposeFace); + //- decompose selected faces into triangles using midnode subdivision + void decomposeMeshFaces(const boolList& decomposeFace); - //- decompose internal faces containing concave nodes - void decomposeConcaveInternalFaces(const boolList& concaveVertex); + //- decompose internal faces containing concave nodes + void decomposeConcaveInternalFaces(const boolList& concaveVertex); }; diff --git a/meshLibrary/utilities/faceDecomposition/faceDecomposition.C b/meshLibrary/utilities/faceDecomposition/faceDecomposition.C index 83e4928a969ea6c06faf94cab833a19e8785887c..ace0b537b5952cf86eb5d6d2827d76ccc7252539 100644 --- a/meshLibrary/utilities/faceDecomposition/faceDecomposition.C +++ b/meshLibrary/utilities/faceDecomposition/faceDecomposition.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -70,13 +69,13 @@ label faceDecomposition::concaveVertex() const } label vrtIndex = edges[eI].commonVertex(edges[next]); - /* + /* if( pointTriIndex_[vrtIndex] && pointTriIndex_[vrtIndex]->size() > 1 ) - */ - concaveVrt = vrtIndex; + */ + concaveVrt = vrtIndex; } } @@ -87,12 +86,12 @@ label faceDecomposition::concaveVertex() const //- Constructor faceDecomposition::faceDecomposition ( - const face& f, - const pointField& pts + const face& f, + const pointField& pts ) : - f_(f), - points_(pts) + f_(f), + points_(pts) { } @@ -113,7 +112,7 @@ bool faceDecomposition::isFaceConvex() const bool faceDecomposition::isFacePlanar(const scalar tol) const { - vector nref = f_.normal(points_); + vector nref = f_.normal(points_); nref /= mag(nref); forAll(f_, pI) @@ -138,7 +137,7 @@ bool faceDecomposition::isFacePlanar() const tol *= 0.05; - return isFacePlanar(tol); + return isFacePlanar(tol); } faceList faceDecomposition::decomposeFace() const @@ -267,13 +266,13 @@ faceList faceDecomposition::decomposeFaceIntoTriangles(const label cv) const Info << "face " << faceNo << " " << f_ << " is decomposed into " << fcs << endl; # endif - - return fcs; + + return fcs; } - - faceList fcs(1, f_); - - return fcs; + + faceList fcs(1, f_); + + return fcs; } faceList faceDecomposition::decomposeFaceIntoTriangles() const diff --git a/meshLibrary/utilities/faceDecomposition/faceDecomposition.H b/meshLibrary/utilities/faceDecomposition/faceDecomposition.H index ff8db7b167809be54f628d8e3e02591ca73f04e2..7178b68f54559cf4e73ca31e5c567f11201c647d 100644 --- a/meshLibrary/utilities/faceDecomposition/faceDecomposition.H +++ b/meshLibrary/utilities/faceDecomposition/faceDecomposition.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class faceDecomposition @@ -49,18 +48,18 @@ namespace Foam class faceDecomposition { // private data - const face& f_; - - const pointField& points_; + const face& f_; + + const pointField& points_; // private member functions - //- find concave vertex and return its position - //- in the face - label concaveVertex() const; - - //- decomposes the face into triangle starting from - //- the given vertex - faceList decomposeFaceIntoTriangles(const label cv) const; + //- find concave vertex and return its position + //- in the face + label concaveVertex() const; + + //- decomposes the face into triangle starting from + //- the given vertex + faceList decomposeFaceIntoTriangles(const label cv) const; //- disallows bitwise construct void operator=(const faceDecomposition&); @@ -75,27 +74,27 @@ public: //- construct components faceDecomposition ( - const face&, - const pointField& + const face&, + const pointField& ); //- Destructor ~faceDecomposition(); // Member functions - //- check if the face is convex - bool isFaceConvex() const; - - //- check if the face is planar - bool isFacePlanar() const; - bool isFacePlanar(const scalar tol) const; - - //- decompose face into triangles - faceList decomposeFaceIntoTriangles() const; - - //- decompose face into the minimal number - //- of convex faces - faceList decomposeFace() const; + //- check if the face is convex + bool isFaceConvex() const; + + //- check if the face is planar + bool isFacePlanar() const; + bool isFacePlanar(const scalar tol) const; + + //- decompose face into triangles + faceList decomposeFaceIntoTriangles() const; + + //- decompose face into the minimal number + //- of convex faces + faceList decomposeFace() const; }; diff --git a/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.C b/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.C index e8dbe61c339c9379a88671bc18a1249c7299d2bb..725d722596cb845ac2e7368be045c86c144fe2fa 100644 --- a/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.C +++ b/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,193 +41,193 @@ namespace Foam void createFacesFromChain::findPointsBelongingToTheFace ( - const label currPos, - boolList& includePoints, - boolList& endPoints + const label currPos, + boolList& includePoints, + boolList& endPoints ) const { - includePoints.setSize(chainPoints_.size()); - endPoints.setSize(chainPoints_.size()); - endPoints = false; - includePoints = false; - - const label currRegion = regionsForPointAtPosition_[currPos][0]; - if( regionsForPointAtPosition_[currPos].size() != 1 ) - { - FatalErrorIn - ( - "void createFacesFromChain::createFacesFromChain::" - "findVerticesBelongingToTheFace" - ) << "Trying to create a face from an invalid point!" - << abort(FatalError); - } - - # ifdef DEBUGCutter - Info << "Finding vertices belonging to the face from chain " - << chainPoints_ << endl; - # endif - - forAll(chainPoints_, pI) - { - const label pos = (pI+currPos) % chainPoints_.size(); - - if( regionsForPointAtPosition_[pos].contains(currRegion) ) - includePoints[pos] = true; - - if( regionsForPointAtPosition_[pos].size() > 1 ) - { - endPoints[pos] = true; - break; - } - else if( !includePoints[pos] ) - { - FatalErrorIn - ( - "void createFacesFromChain::findVerticesBelongingToTheFace()" - ) << "Cannot create boundary face" - << abort(FatalError); - } - } - - forAllReverse(chainPoints_, pI) - { - const label pos = (pI+currPos) % chainPoints_.size(); - if( includePoints[pos] ) break; - - if( regionsForPointAtPosition_[pos].contains(currRegion) ) - includePoints[pos] = true; - - if( regionsForPointAtPosition_[pos].size() > 1 ) - { - endPoints[pos] = true; - break; - } - else if( !includePoints[pos] ) - { - FatalErrorIn - ( - "void createFacesFromChain::createFacesFromChain::" - "findVerticesBelongingToTheFace" - ) << "Cannot create boundary face" - << abort(FatalError); - } - } - - # ifdef DEBUGCutter - Info << "Include points " << includePoints << endl; - Info << "End points " << endPoints << endl; - # endif + includePoints.setSize(chainPoints_.size()); + endPoints.setSize(chainPoints_.size()); + endPoints = false; + includePoints = false; + + const label currRegion = regionsForPointAtPosition_[currPos][0]; + if( regionsForPointAtPosition_[currPos].size() != 1 ) + { + FatalErrorIn + ( + "void createFacesFromChain::createFacesFromChain::" + "findVerticesBelongingToTheFace" + ) << "Trying to create a face from an invalid point!" + << abort(FatalError); + } + + # ifdef DEBUGCutter + Info << "Finding vertices belonging to the face from chain " + << chainPoints_ << endl; + # endif + + forAll(chainPoints_, pI) + { + const label pos = (pI+currPos) % chainPoints_.size(); + + if( regionsForPointAtPosition_[pos].contains(currRegion) ) + includePoints[pos] = true; + + if( regionsForPointAtPosition_[pos].size() > 1 ) + { + endPoints[pos] = true; + break; + } + else if( !includePoints[pos] ) + { + FatalErrorIn + ( + "void createFacesFromChain::findVerticesBelongingToTheFace()" + ) << "Cannot create boundary face" + << abort(FatalError); + } + } + + forAllReverse(chainPoints_, pI) + { + const label pos = (pI+currPos) % chainPoints_.size(); + if( includePoints[pos] ) break; + + if( regionsForPointAtPosition_[pos].contains(currRegion) ) + includePoints[pos] = true; + + if( regionsForPointAtPosition_[pos].size() > 1 ) + { + endPoints[pos] = true; + break; + } + else if( !includePoints[pos] ) + { + FatalErrorIn + ( + "void createFacesFromChain::createFacesFromChain::" + "findVerticesBelongingToTheFace" + ) << "Cannot create boundary face" + << abort(FatalError); + } + } + + # ifdef DEBUGCutter + Info << "Include points " << includePoints << endl; + Info << "End points " << endPoints << endl; + # endif } void createFacesFromChain::shrinkTheChain ( - const label currPos, - const boolList& includePoints, - const boolList& endPoints + const label currPos, + const boolList& includePoints, + const boolList& endPoints ) { - const label currRegion = regionsForPointAtPosition_[currPos][0]; - if( regionsForPointAtPosition_[currPos].size() != 1 ) - { - FatalErrorIn - ( - "void createFacesFromChain::createFacesFromChain::" - "findVerticesBelongingToTheFace" - ) << "Trying to create a face from an invalid point!" - << abort(FatalError); - } - - # ifdef DEBUGCutter - Info << "Shrinking chain " << chainPoints_ << endl; - # endif - - labelList shrinkedChain(chainPoints_.size()); - List<DynList<label> > shrinkedRegions(chainPoints_.size()); - - direction pI(0); - - forAll(chainPoints_, vI) - if( !includePoints[vI] ) - { - shrinkedChain[pI] = chainPoints_[vI]; - shrinkedRegions[pI] = regionsForPointAtPosition_[vI]; - ++pI; - } - else if( endPoints[vI] ) - { - shrinkedChain[pI] = chainPoints_[vI]; - forAll(regionsForPointAtPosition_[vI], regI) - if( regionsForPointAtPosition_[vI][regI] != currRegion ) - shrinkedRegions[pI].append - ( - regionsForPointAtPosition_[vI][regI] - ); - ++pI; - } - - //- set sizes - shrinkedChain.setSize(pI); - shrinkedRegions.setSize(pI); - - //- store the shrinked lists - chainPoints_ = shrinkedChain; - regionsForPointAtPosition_ = shrinkedRegions; - - # ifdef DEBUGCutter - Info << "Shrinked chain " << chainPoints_ << endl; - Info << "Shrinked regions " << regionsForPointAtPosition_ << endl; - # endif + const label currRegion = regionsForPointAtPosition_[currPos][0]; + if( regionsForPointAtPosition_[currPos].size() != 1 ) + { + FatalErrorIn + ( + "void createFacesFromChain::createFacesFromChain::" + "findVerticesBelongingToTheFace" + ) << "Trying to create a face from an invalid point!" + << abort(FatalError); + } + + # ifdef DEBUGCutter + Info << "Shrinking chain " << chainPoints_ << endl; + # endif + + labelList shrinkedChain(chainPoints_.size()); + List<DynList<label> > shrinkedRegions(chainPoints_.size()); + + direction pI(0); + + forAll(chainPoints_, vI) + if( !includePoints[vI] ) + { + shrinkedChain[pI] = chainPoints_[vI]; + shrinkedRegions[pI] = regionsForPointAtPosition_[vI]; + ++pI; + } + else if( endPoints[vI] ) + { + shrinkedChain[pI] = chainPoints_[vI]; + forAll(regionsForPointAtPosition_[vI], regI) + if( regionsForPointAtPosition_[vI][regI] != currRegion ) + shrinkedRegions[pI].append + ( + regionsForPointAtPosition_[vI][regI] + ); + ++pI; + } + + //- set sizes + shrinkedChain.setSize(pI); + shrinkedRegions.setSize(pI); + + //- store the shrinked lists + chainPoints_ = shrinkedChain; + regionsForPointAtPosition_ = shrinkedRegions; + + # ifdef DEBUGCutter + Info << "Shrinked chain " << chainPoints_ << endl; + Info << "Shrinked regions " << regionsForPointAtPosition_ << endl; + # endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// createFacesFromChain::createFacesFromChain ( - const labelList& chVertices, - const VRWGraph& pointRegions + const labelList& chVertices, + const VRWGraph& pointRegions ) : - chainPoints_(chVertices), - regionsForPointAtPosition_(chVertices.size()), - createdFaces_(), - faceRegions_() + chainPoints_(chVertices), + regionsForPointAtPosition_(chVertices.size()), + createdFaces_(), + faceRegions_() { - forAll(chVertices, vI) - { - const constRow row = pointRegions[chVertices[vI]]; - regionsForPointAtPosition_[vI].clear(); - forAll(row, rI) - regionsForPointAtPosition_[vI].append(row[rI]); - } - - # ifdef DEBUGCutter - Info << "Making boundary faces for chain " << chainPoints_ << endl; - Info << "Regions for chain points " << regionsForPointAtPosition_ << endl; - # endif + forAll(chVertices, vI) + { + const constRow row = pointRegions[chVertices[vI]]; + regionsForPointAtPosition_[vI].clear(); + forAll(row, rI) + regionsForPointAtPosition_[vI].append(row[rI]); + } + + # ifdef DEBUGCutter + Info << "Making boundary faces for chain " << chainPoints_ << endl; + Info << "Regions for chain points " << regionsForPointAtPosition_ << endl; + # endif } createFacesFromChain::createFacesFromChain ( - const labelList& chVertices, - const List<DynList<label> >& pointRegions + const labelList& chVertices, + const List<DynList<label> >& pointRegions ) : - chainPoints_(chVertices), - regionsForPointAtPosition_(chVertices.size()), - createdFaces_(), - faceRegions_() + chainPoints_(chVertices), + regionsForPointAtPosition_(chVertices.size()), + createdFaces_(), + faceRegions_() { - forAll(chVertices, vI) - { - regionsForPointAtPosition_[vI] = pointRegions[chVertices[vI]]; - } - - # ifdef DEBUGCutter - Info << "Making boundary faces for chain " << chainPoints_ << endl; - Info << "Regions for chain points " << regionsForPointAtPosition_ << endl; - # endif + forAll(chVertices, vI) + { + regionsForPointAtPosition_[vI] = pointRegions[chVertices[vI]]; + } + + # ifdef DEBUGCutter + Info << "Making boundary faces for chain " << chainPoints_ << endl; + Info << "Regions for chain points " << regionsForPointAtPosition_ << endl; + # endif } - + createFacesFromChain::~createFacesFromChain() { } @@ -238,205 +237,202 @@ createFacesFromChain::~createFacesFromChain() void createFacesFromChain::createFacesWithoutACorner() { - bool found; - do - { - found = false; - - boolList includePoints, endPoints; - - //- this function removes nodes from the chainPoints_ and creates - //- new faces. In order to create a valid face, it is important that - //- that a chain of vertices belonging to a given patch is singly - //- connected. Non-singly connected chains are not treated until they - //- become singly connected after elimination of other chains - - /* - boolList usedPoint(chainPoints_.size(), false); - Map<label> numOfChains; - forAll(chainPoints_, pI) - if( !usedPoint[pI] && (regionsForPointAtPosition_[pI].size() == 1) ) - { - findPointsBelongingToTheFace(pI, includePoints, endPoints); - - forAll(includePoints, ipI) - if( includePoints[ipI] ) - usedPoint[ipI] = true; - - if( !numOfChains.found(regionsForPointAtPosition_[pI][0]) ) - { - numOfChains.insert - ( - regionsForPointAtPosition_[pI][0], - 1 - ); - } - else - { - numOfChains[regionsForPointAtPosition_[pI][0]]++; - } - } - */ - - //- start creating faces and eliminating nodes from the chain for - //- singly connected topologies - forAll(chainPoints_, pI) - if( - (regionsForPointAtPosition_[pI].size() == 1) - //&& (numOfChains[regionsForPointAtPosition_[pI][0]] == 1) - ) - { - findPointsBelongingToTheFace(pI, includePoints, endPoints); - - //- create a new face - face f(chainPoints_.size()); - direction vrtI(0); - - forAll(includePoints, incI) - if( includePoints[incI] ) - f[vrtI++] = chainPoints_[incI]; - - DynList<label> facePatches(3); - forAll(endPoints, epI) - if( endPoints[epI] ) - { - const DynList<label>& pr = - regionsForPointAtPosition_[epI]; - - forAll(pr, i) - facePatches.appendIfNotIn(pr[i]); - } - - //- face must contain an additional corner point if the number - //- of associated patches is greater than 2. Skip creating the - //- face is this is the case - if( facePatches.size() > 2 ) - continue; - - found = true; - - if( vrtI > 2 ) - { - f.setSize(vrtI); - createdFaces_.append(f); - faceRegions_.append(regionsForPointAtPosition_[pI][0]); - - # ifdef DEBUGCutter - Info << "Created face " << f << endl; - # endif - } - - //- shrink the chainPoints_ - shrinkTheChain(pI, includePoints, endPoints); - - break; - } - } while( found ); + bool found; + do + { + found = false; + + boolList includePoints, endPoints; + + //- this function removes nodes from the chainPoints_ and creates + //- new faces. In order to create a valid face, it is important that + //- that a chain of vertices belonging to a given patch is singly + //- connected. Non-singly connected chains are not treated until they + //- become singly connected after elimination of other chains + + /* + boolList usedPoint(chainPoints_.size(), false); + Map<label> numOfChains; + forAll(chainPoints_, pI) + if( !usedPoint[pI] && (regionsForPointAtPosition_[pI].size() == 1) ) + { + findPointsBelongingToTheFace(pI, includePoints, endPoints); + + forAll(includePoints, ipI) + if( includePoints[ipI] ) + usedPoint[ipI] = true; + + if( !numOfChains.found(regionsForPointAtPosition_[pI][0]) ) + { + numOfChains.insert + ( + regionsForPointAtPosition_[pI][0], + 1 + ); + } + else + { + numOfChains[regionsForPointAtPosition_[pI][0]]++; + } + } + */ + + //- start creating faces and eliminating nodes from the chain for + //- singly connected topologies + forAll(chainPoints_, pI) + if( + (regionsForPointAtPosition_[pI].size() == 1) + //&& (numOfChains[regionsForPointAtPosition_[pI][0]] == 1) + ) + { + findPointsBelongingToTheFace(pI, includePoints, endPoints); + + //- create a new face + face f(chainPoints_.size()); + direction vrtI(0); + + forAll(includePoints, incI) + if( includePoints[incI] ) + f[vrtI++] = chainPoints_[incI]; + + DynList<label> facePatches; + forAll(endPoints, epI) + if( endPoints[epI] ) + { + const DynList<label>& pr = + regionsForPointAtPosition_[epI]; + + forAll(pr, i) + facePatches.appendIfNotIn(pr[i]); + } + + //- face must contain an additional corner point if the number + //- of associated patches is greater than 2. Skip creating the + //- face is this is the case + if( facePatches.size() > 2 ) + continue; + + found = true; + + if( vrtI > 2 ) + { + f.setSize(vrtI); + createdFaces_.append(f); + faceRegions_.append(regionsForPointAtPosition_[pI][0]); + + # ifdef DEBUGCutter + Info << "Created face " << f << endl; + # endif + } + + //- shrink the chainPoints_ + shrinkTheChain(pI, includePoints, endPoints); + + break; + } + } while( found ); } - -void createFacesFromChain::createFacesWithACorner -( - const label cornerLabel -) + +void createFacesFromChain::createFacesWithACorner(const label cornerLabel) { - label start(-1), facePatch(-1); - forAll(chainPoints_, cpI) - if( regionsForPointAtPosition_[cpI].size() == 2 ) - { - start = cpI; - - DynList<label> commonPatches(2); - const DynList<label>& np = - regionsForPointAtPosition_[chainPoints_.fcIndex(cpI)]; - - forAll(np, npI) - if( regionsForPointAtPosition_[cpI].contains(np[npI]) ) - commonPatches.append(np[npI]); - - if( commonPatches.size() == 1 ) - { - facePatch = commonPatches[0]; - } - else - { - FatalErrorIn - ( - "void createFacesFromChain::createFacesFromChain::" - "createFacesWithACorner(const label cornerLabel)" - ) << "Cannot determine face patch" << abort(FatalError); - } - - break; - } - - //- start creating faces with a corner - face f(5); - direction vI(0); - f[vI++] = chainPoints_[start]; - - for(label cpI=1;cpI<chainPoints_.size();++cpI) - { - const label pos = (cpI + start) % chainPoints_.size(); - - if( regionsForPointAtPosition_[pos].size() == 1 ) - { - f.newElmt(vI++) = chainPoints_[pos]; - } - else if( regionsForPointAtPosition_[pos].size() == 2 ) - { - //- store old face - f.newElmt(vI++) = chainPoints_[pos]; - f.newElmt(vI++) = cornerLabel; - f.setSize(vI); - vI = 0; - createdFaces_.append(f); - faceRegions_.append(facePatch); - - //- start creting new face - f[vI++] = chainPoints_[pos]; - const label ppos = - regionsForPointAtPosition_[pos].containsAtPosition(facePatch); - if( ppos == 0 ) - { - facePatch = regionsForPointAtPosition_[pos][1]; - } - else - { - facePatch = regionsForPointAtPosition_[pos][0]; - } - } - else - { - FatalErrorIn - ( - "void createFacesFromChain::createFacesFromChain::" - "createFacesWithACorner(const label cornerLabel)" - ) << "Found chain vertex in more than 2 patches!!" - << abort(FatalError); - } - } - - //- add the start position into the last face - f.newElmt(vI++) = chainPoints_[start]; - f.newElmt(vI++) = cornerLabel; - f.setSize(vI); - createdFaces_.append(f); - faceRegions_.append(facePatch); + label start(-1), facePatch(-1); + forAll(chainPoints_, cpI) + if( regionsForPointAtPosition_[cpI].size() == 2 ) + { + start = cpI; + + DynList<label> commonPatches; + const DynList<label>& np = + regionsForPointAtPosition_[chainPoints_.fcIndex(cpI)]; + + forAll(np, npI) + if( regionsForPointAtPosition_[cpI].contains(np[npI]) ) + commonPatches.append(np[npI]); + + if( commonPatches.size() == 1 ) + { + facePatch = commonPatches[0]; + } + else + { + FatalErrorIn + ( + "void createFacesFromChain::createFacesFromChain::" + "createFacesWithACorner(const label cornerLabel)" + ) << "Cannot determine face patch" << abort(FatalError); + } + + break; + } + + //- start creating faces with a corner + face f(5); + direction vI(0); + f[vI++] = chainPoints_[start]; + + for(label cpI=1;cpI<chainPoints_.size();++cpI) + { + const label pos = (cpI + start) % chainPoints_.size(); + + if( regionsForPointAtPosition_[pos].size() == 1 ) + { + f.newElmt(vI++) = chainPoints_[pos]; + } + else if( regionsForPointAtPosition_[pos].size() == 2 ) + { + //- store old face + f.newElmt(vI++) = chainPoints_[pos]; + f.newElmt(vI++) = cornerLabel; + f.setSize(vI); + vI = 0; + createdFaces_.append(f); + faceRegions_.append(facePatch); + + //- start creting new face + f[vI++] = chainPoints_[pos]; + const label ppos = + regionsForPointAtPosition_[pos].containsAtPosition(facePatch); + if( ppos == 0 ) + { + facePatch = regionsForPointAtPosition_[pos][1]; + } + else + { + facePatch = regionsForPointAtPosition_[pos][0]; + } + } + else + { + FatalErrorIn + ( + "void createFacesFromChain::createFacesFromChain::" + "createFacesWithACorner(const label cornerLabel)" + ) << "Found chain vertex in more than 2 patches!!" + << abort(FatalError); + } + } + + //- add the start position into the last face + f.newElmt(vI++) = chainPoints_[start]; + f.newElmt(vI++) = cornerLabel; + f.setSize(vI); + createdFaces_.append(f); + faceRegions_.append(facePatch); } const DynList<face>& createFacesFromChain::createdFaces() const { - return createdFaces_; + return createdFaces_; } const DynList<label>& createFacesFromChain::faceRegion()const { - return faceRegions_; + return faceRegions_; } const labelList& createFacesFromChain::unresolvedPoints() const { - return chainPoints_; + return chainPoints_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.H b/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.H index 4390acf7eaefcb6587204543997da30ef03d2245..b48dcdee66a675e9e27a573ae0a4a8f48965ebdd 100644 --- a/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.H +++ b/meshLibrary/utilities/helperClasses/createFacesFromChain/createFacesFromChain.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class createFacesFromChain @@ -43,67 +42,74 @@ SourceFiles namespace Foam { - + class VRWGraph; /*---------------------------------------------------------------------------*\ - Class createFacesFromChain Declaration + Class createFacesFromChain Declaration \*---------------------------------------------------------------------------*/ class createFacesFromChain { - // Members - labelList chainPoints_; - - List<DynList<label> > regionsForPointAtPosition_; - - DynList<face> createdFaces_; - DynList<label> faceRegions_; - - // Private member functions - void findPointsBelongingToTheFace - ( - const label currPos, - boolList& includePoints, - boolList& endPoints - ) const; - - void shrinkTheChain - ( - const label currPos, - const boolList& includePoints, - const boolList& endPoints - ); - - public: - - createFacesFromChain - ( - const labelList& chPoints, - const VRWGraph& pointRegions - ); - - createFacesFromChain - ( - const labelList& chPoints, - const List<DynList<label> >& pointRegions - ); - - ~createFacesFromChain(); - - // Member functions - //- create faces which do not require an additional corner - void createFacesWithoutACorner(); - - //- create faces with a corner - void createFacesWithACorner(const label); - - //- return created faces and the corresponding patches - const DynList<face>& createdFaces() const; - const DynList<label>& faceRegion() const; - - //- a list of points which have not yet been resolved - const labelList& unresolvedPoints() const; + // Members + labelList chainPoints_; + + List<DynList<label> > regionsForPointAtPosition_; + + DynList<face> createdFaces_; + DynList<label> faceRegions_; + + // Private member functions + void findPointsBelongingToTheFace + ( + const label currPos, + boolList& includePoints, + boolList& endPoints + ) const; + + void shrinkTheChain + ( + const label currPos, + const boolList& includePoints, + const boolList& endPoints + ); + + public: + + // Constructors + //- construct from chain points and a graph of regions + //- to which each point belongs to + createFacesFromChain + ( + const labelList& chPoints, + const VRWGraph& pointRegions + ); + + //- construct from chain points and regions + //- to which each point belongs to + createFacesFromChain + ( + const labelList& chPoints, + const List<DynList<label> >& pointRegions + ); + + // Destructor + + ~createFacesFromChain(); + + // Member functions + //- create faces which do not require an additional corner + void createFacesWithoutACorner(); + + //- create faces with a corner + void createFacesWithACorner(const label); + + //- return created faces and the corresponding patches + const DynList<face>& createdFaces() const; + const DynList<label>& faceRegion() const; + + //- a list of points which have not yet been resolved + const labelList& unresolvedPoints() const; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFitting.H b/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFitting.H index af916e71790aa130164fbe8664194f7879d0bced..c2381a3353f5d7e02b6b3e170484cb9043aa10f9 100644 --- a/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFitting.H +++ b/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFitting.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class quadricFitting diff --git a/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFittingI.H b/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFittingI.H index 72e5fec672f7453f51f461a28e578b53d7a1ec92..58d0d8d724799388d7f67f2d0df7ef1931adba52 100644 --- a/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFittingI.H +++ b/meshLibrary/utilities/helperClasses/geometry/quadricFitting/quadricFittingI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -74,7 +73,6 @@ void quadricFitting::calculateCoordinateSystem() label pI(0); while( !valid ) { - vector v = otherPoints_[pI] - origin_; const point vp = pl.nearestPoint(otherPoints_[pI]); vecX_ = vp - origin_; diff --git a/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.C b/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.C index c0ef4d1365c7cbf9f5697562a2d6fabf07a23f0c..fce462c54fa9547589055f0c64581d992b378e1e 100644 --- a/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.C +++ b/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.H b/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.H index 6c2cdd4221cef0ba02f18d0b9db492972b8f68e8..6ac111c3ef39f5d2f947a4a20ecf5e1e51576b85 100644 --- a/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.H +++ b/meshLibrary/utilities/helperClasses/inSphereTest/inSphereTest.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class inSphereTest Description Calculates if a point is inside a tetrahedron sphere or not. Uses adaptive- - precision arithmetic by J. R. Schewchuk + precision arithmetic by J. R. Schewchuk SourceFiles inSphereTest.C diff --git a/meshLibrary/utilities/helperClasses/matrices/matrix2D.H b/meshLibrary/utilities/helperClasses/matrices/matrix2D.H index c37b39b444c317b0ec3a57b640a9a11dd60489b6..d13c0482969852a152ac9cb6db83bc87d35906aa 100644 --- a/meshLibrary/utilities/helperClasses/matrices/matrix2D.H +++ b/meshLibrary/utilities/helperClasses/matrices/matrix2D.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class matrix2D @@ -42,7 +41,7 @@ SourceFiles namespace Foam { - + /*---------------------------------------------------------------------------*\ Class matrix2D Declaration \*---------------------------------------------------------------------------*/ @@ -51,43 +50,43 @@ class matrix2D : public FixedList<FixedList<scalar, 2>, 2> { // Private members - mutable scalar det_; - mutable bool calculatedDet_; - + scalar det_; + bool calculatedDet_; + // Private member functions - //- calculate matrix determinant - inline void calculateDeterminant() const; - + //- calculate matrix determinant + inline void calculateDeterminant(); + public: - // Constructors - //- Null constructor - explicit inline matrix2D(); + // Constructors + //- Null constructor + explicit inline matrix2D(); + + //- Copy constructor + inline matrix2D(const matrix2D&); - //- Copy constructor - inline matrix2D(const matrix2D&); + // Destructor + inline ~matrix2D(); - // Destructor - inline ~matrix2D(); + // Member functions + //- return matrix determinant + inline scalar determinant(); - // Member functions - //- return matrix determinant - inline scalar determinant() const; + //- return inverse matrix + inline matrix2D inverse(); - //- return inverse matrix - inline matrix2D inverse() const; + //- find the solution of the system with the given rhs + inline FixedList<scalar, 2> solve + ( + const FixedList<scalar, 2>& source + ); - //- find the solution of the system with the given rhs - inline FixedList<scalar, 2> solve - ( - const FixedList<scalar, 2>& source - ) const; + //- return the first component of the solution vector + inline scalar solveFirst(const FixedList<scalar, 2>& source); - //- return the first component of the solution vector - inline scalar solveFirst(const FixedList<scalar, 2>& source) const; - - //- return the second component of the solution vector - inline scalar solveSecond(const FixedList<scalar, 2>& source) const; + //- return the second component of the solution vector + inline scalar solveSecond(const FixedList<scalar, 2>& source); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperClasses/matrices/matrix2DI.H b/meshLibrary/utilities/helperClasses/matrices/matrix2DI.H index 29bfb1fa40119ad478b376fd3dde54a509804959..408acf1f06b7925c0dce6da33482d44b9c9454c2 100644 --- a/meshLibrary/utilities/helperClasses/matrices/matrix2DI.H +++ b/meshLibrary/utilities/helperClasses/matrices/matrix2DI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class matrix2D @@ -35,98 +34,98 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -inline void matrix2D::calculateDeterminant() const + +inline void matrix2D::calculateDeterminant() { - if( calculatedDet_ ) - return; - - const FixedList<FixedList<scalar, 2>, 2>& mat = *this; - det_ = mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0]; - - calculatedDet_ = true; + if( calculatedDet_ ) + return; + + const FixedList<FixedList<scalar, 2>, 2>& mat = *this; + det_ = mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0]; + + calculatedDet_ = true; } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + inline matrix2D::matrix2D() : - det_(), - calculatedDet_(false) -{ -} + det_(), + calculatedDet_(false) +{} inline matrix2D::matrix2D(const matrix2D& m) : - FixedList<FixedList<scalar, 2>, 2>(m), - det_(), - calculatedDet_(false) -{ -} + FixedList<FixedList<scalar, 2>, 2>(m), + det_(m.det_), + calculatedDet_(m.calculatedDet_) +{} inline matrix2D::~matrix2D() {} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -inline scalar matrix2D::determinant() const +inline scalar matrix2D::determinant() { - calculateDeterminant(); - - return det_; + calculateDeterminant(); + + return det_; } -inline matrix2D matrix2D::inverse() const +inline matrix2D matrix2D::inverse() { - calculateDeterminant(); - const FixedList<FixedList<scalar, 2>, 2>& mat = *this; - matrix2D imat; - imat[0][0] = mat[1][1] / det_; - imat[0][1] = -1.0 * mat[0][1] / det_; - imat[1][0] = -1.0 * mat[1][0] / det_; - imat[1][1] = mat[0][0] / det_; - - return matrix2D(imat); + calculateDeterminant(); + + const FixedList<FixedList<scalar, 2>, 2>& mat = *this; + + matrix2D imat; + imat[0][0] = mat[1][1] / det_; + imat[0][1] = -1.0 * mat[0][1] / det_; + imat[1][0] = -1.0 * mat[1][0] / det_; + imat[1][1] = mat[0][0] / det_; + + return matrix2D(imat); } inline FixedList<scalar, 2> matrix2D::solve ( - const FixedList<scalar, 2>& source -) const + const FixedList<scalar, 2>& source +) { - FixedList<scalar, 2> result; - result[0] = solveFirst(source); - result[1] = solveSecond(source); - - return result; + FixedList<scalar, 2> result; + result[0] = solveFirst(source); + result[1] = solveSecond(source); + + return result; } -inline scalar matrix2D::solveFirst(const FixedList<scalar, 2>& source) const +inline scalar matrix2D::solveFirst(const FixedList<scalar, 2>& source) { - calculateDeterminant(); - - const FixedList<FixedList<scalar, 2>, 2>& mat = *this; - - return - ( - mat[1][1] * source[0] - - mat[0][1] * source[1] - ) / det_; + calculateDeterminant(); + + const FixedList<FixedList<scalar, 2>, 2>& mat = *this; + + return + ( + mat[1][1] * source[0] - + mat[0][1] * source[1] + ) / det_; } - -inline scalar matrix2D::solveSecond(const FixedList<scalar, 2>& source) const + +inline scalar matrix2D::solveSecond(const FixedList<scalar, 2>& source) { - calculateDeterminant(); - - const FixedList<FixedList<scalar, 2>, 2>& mat = *this; - - return - ( - -1.0 * mat[1][0] * source[0] + - mat[0][0] * source[1] - ) / det_; + calculateDeterminant(); + + const FixedList<FixedList<scalar, 2>, 2>& mat = *this; + + return + ( + -1.0 * mat[1][0] * source[0] + + mat[0][0] * source[1] + ) / det_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperClasses/matrices/matrix3D.H b/meshLibrary/utilities/helperClasses/matrices/matrix3D.H index 6e4e1b89cad941f465dc9aac376c293b141b315b..1b97ddf13ecc91477c66b96082bdd0b60a2831f0 100644 --- a/meshLibrary/utilities/helperClasses/matrices/matrix3D.H +++ b/meshLibrary/utilities/helperClasses/matrices/matrix3D.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class matrix3D @@ -43,7 +42,7 @@ SourceFiles namespace Foam { - + /*---------------------------------------------------------------------------*\ Class matrix3D Declaration \*---------------------------------------------------------------------------*/ @@ -52,46 +51,46 @@ class matrix3D : public FixedList<FixedList<scalar, 3>, 3> { // Private members - mutable scalar det_; - mutable bool calculatedDet_; - + scalar det_; + bool calculatedDet_; + // Private member functions - //- calculate matrix determinant - inline void calculateDeterminant() const; + //- calculate matrix determinant + inline void calculateDeterminant(); public: - // Constructors - //- Null constructor - explicit inline matrix3D(); - - //- Copy constructor - inline matrix3D(const matrix3D&); - - // Destructor - inline ~matrix3D(); - - // Member functions - //- return matrix determinant - inline scalar determinant() const; - - //- return inverse matrix - inline matrix3D inverse() const; - - //- find the solution of the system with the given rhs - inline FixedList<scalar, 3> solve - ( - const FixedList<scalar, 3>& source - ) const; - - //- return the first component of the solution vector - inline scalar solveFirst(const FixedList<scalar, 3>& source) const; - - //- return the second component of the solution vector - inline scalar solveSecond(const FixedList<scalar, 3>& source) const; - - //- return the third component of the solution vector - inline scalar solveThird(const FixedList<scalar, 3>& source) const; + // Constructors + //- Null constructor + explicit inline matrix3D(); + + //- Copy constructor + inline matrix3D(const matrix3D&); + + // Destructor + inline ~matrix3D(); + + // Member functions + //- return matrix determinant + inline scalar determinant(); + + //- return inverse matrix + inline matrix3D inverse(); + + //- find the solution of the system with the given rhs + inline FixedList<scalar, 3> solve + ( + const FixedList<scalar, 3>& source + ); + + //- return the first component of the solution vector + inline scalar solveFirst(const FixedList<scalar, 3>& source); + + //- return the second component of the solution vector + inline scalar solveSecond(const FixedList<scalar, 3>& source); + + //- return the third component of the solution vector + inline scalar solveThird(const FixedList<scalar, 3>& source); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperClasses/matrices/matrix3DI.H b/meshLibrary/utilities/helperClasses/matrices/matrix3DI.H index 9fb39a96ca3bbeee895490c8b06fc5b3308dabd7..88e5f92a262d68411c8690edc1ed39d22161c840 100644 --- a/meshLibrary/utilities/helperClasses/matrices/matrix3DI.H +++ b/meshLibrary/utilities/helperClasses/matrices/matrix3DI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class matrix3D @@ -35,122 +34,124 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -inline void matrix3D::calculateDeterminant() const + +inline void matrix3D::calculateDeterminant() { - if( calculatedDet_ ) - return; - - const FixedList<FixedList<scalar, 3>, 3>& mat = *this; - det_ = - mat[0][0] * (mat[1][1] * mat[2][2] - mat[1][2] * mat[2][1]) - - mat[0][1] * (mat[1][0] * mat[2][2] - mat[1][2] * mat[2][0]) + - mat[0][2] * (mat[1][0] * mat[2][1] - mat[1][1] * mat[2][0]); - calculatedDet_ = true; + if( calculatedDet_ ) + return; + + const FixedList<FixedList<scalar, 3>, 3>& mat = *this; + + det_ = + mat[0][0] * (mat[1][1] * mat[2][2] - mat[1][2] * mat[2][1]) - + mat[0][1] * (mat[1][0] * mat[2][2] - mat[1][2] * mat[2][0]) + + mat[0][2] * (mat[1][0] * mat[2][1] - mat[1][1] * mat[2][0]); + + calculatedDet_ = true; } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + inline matrix3D::matrix3D() : - det_(), - calculatedDet_(false) -{ -} + det_(), + calculatedDet_(false) +{} inline matrix3D::matrix3D(const matrix3D& m) : - FixedList<FixedList<scalar, 3>, 3>(m), - det_(), - calculatedDet_(false) -{ -} + FixedList<FixedList<scalar, 3>, 3>(m), + det_(m.det_), + calculatedDet_(m.calculatedDet_) +{} inline matrix3D::~matrix3D() {} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -inline scalar matrix3D::determinant() const +inline scalar matrix3D::determinant() { - calculateDeterminant(); - - return det_; + calculateDeterminant(); + + return det_; } -inline matrix3D matrix3D::inverse() const +inline matrix3D matrix3D::inverse() { - calculateDeterminant(); - const FixedList<FixedList<scalar, 3>, 3>& mat = *this; - matrix3D imat; - imat[0][0] = (mat[1][1] * mat[2][2] - mat[1][2] * mat[2][1]) / det_; - imat[0][1] = (mat[0][2] * mat[2][1] - mat[0][1] * mat[2][2]) / det_; - imat[0][2] = (mat[0][1] * mat[1][2] - mat[0][2] * mat[1][1]) / det_; - imat[1][0] = (mat[1][2] * mat[2][0] - mat[1][0] * mat[2][2]) / det_; - imat[1][1] = (mat[0][0] * mat[2][2] - mat[0][2] * mat[2][0]) / det_; - imat[1][2] = (mat[0][2] * mat[1][0] - mat[0][0] * mat[1][2]) / det_; - imat[2][0] = (mat[1][0] * mat[2][1] - mat[1][1] * mat[2][0]) / det_; - imat[2][1] = (mat[0][1] * mat[2][0] - mat[0][0] * mat[2][1]) / det_; - imat[2][2] = (mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0]) / det_; - - return imat; + calculateDeterminant(); + + const FixedList<FixedList<scalar, 3>, 3>& mat = *this; + + matrix3D imat; + imat[0][0] = (mat[1][1] * mat[2][2] - mat[1][2] * mat[2][1]) / det_; + imat[0][1] = (mat[0][2] * mat[2][1] - mat[0][1] * mat[2][2]) / det_; + imat[0][2] = (mat[0][1] * mat[1][2] - mat[0][2] * mat[1][1]) / det_; + imat[1][0] = (mat[1][2] * mat[2][0] - mat[1][0] * mat[2][2]) / det_; + imat[1][1] = (mat[0][0] * mat[2][2] - mat[0][2] * mat[2][0]) / det_; + imat[1][2] = (mat[0][2] * mat[1][0] - mat[0][0] * mat[1][2]) / det_; + imat[2][0] = (mat[1][0] * mat[2][1] - mat[1][1] * mat[2][0]) / det_; + imat[2][1] = (mat[0][1] * mat[2][0] - mat[0][0] * mat[2][1]) / det_; + imat[2][2] = (mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0]) / det_; + + return imat; } inline FixedList<scalar, 3> matrix3D::solve ( - const FixedList<scalar, 3>& source -) const + const FixedList<scalar, 3>& source +) { - FixedList<scalar, 3> result; - result[0] = solveFirst(source); - result[1] = solveSecond(source); - result[2] = solveThird(source); - - return result; + FixedList<scalar, 3> result; + result[0] = solveFirst(source); + result[1] = solveSecond(source); + result[2] = solveThird(source); + + return result; } -inline scalar matrix3D::solveFirst(const FixedList<scalar, 3>& source) const +inline scalar matrix3D::solveFirst(const FixedList<scalar, 3>& source) { - calculateDeterminant(); - - const FixedList<FixedList<scalar, 3>, 3>& mat = *this; - - return - ( - (mat[1][1] * mat[2][2] - mat[1][2] * mat[2][1]) * source[0] + - (mat[0][2] * mat[2][1] - mat[0][1] * mat[2][2]) * source[1] + - (mat[0][1] * mat[1][2] - mat[0][2] * mat[1][1]) * source[2] - ) / det_; + calculateDeterminant(); + + const FixedList<FixedList<scalar, 3>, 3>& mat = *this; + + return + ( + (mat[1][1] * mat[2][2] - mat[1][2] * mat[2][1]) * source[0] + + (mat[0][2] * mat[2][1] - mat[0][1] * mat[2][2]) * source[1] + + (mat[0][1] * mat[1][2] - mat[0][2] * mat[1][1]) * source[2] + ) / det_; } - -inline scalar matrix3D::solveSecond(const FixedList<scalar, 3>& source) const + +inline scalar matrix3D::solveSecond(const FixedList<scalar, 3>& source) { - calculateDeterminant(); - - const FixedList<FixedList<scalar, 3>, 3>& mat = *this; - - return - ( - (mat[1][2] * mat[2][0] - mat[1][0] * mat[2][2]) * source[0] + - (mat[0][0] * mat[2][2] - mat[0][2] * mat[2][0]) * source[1] + - (mat[0][2] * mat[1][0] - mat[0][0] * mat[1][2]) * source[2] - ) / det_; + calculateDeterminant(); + + const FixedList<FixedList<scalar, 3>, 3>& mat = *this; + + return + ( + (mat[1][2] * mat[2][0] - mat[1][0] * mat[2][2]) * source[0] + + (mat[0][0] * mat[2][2] - mat[0][2] * mat[2][0]) * source[1] + + (mat[0][2] * mat[1][0] - mat[0][0] * mat[1][2]) * source[2] + ) / det_; } - -inline scalar matrix3D::solveThird(const FixedList<scalar, 3>& source) const + +inline scalar matrix3D::solveThird(const FixedList<scalar, 3>& source) { - calculateDeterminant(); - - const FixedList<FixedList<scalar, 3>, 3>& mat = *this; - - return - ( - (mat[1][0] * mat[2][1] - mat[1][1] * mat[2][0]) * source[0] + - (mat[0][1] * mat[2][0] - mat[0][0] * mat[2][1]) * source[1] + - (mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0]) * source[2] - ) / det_; + calculateDeterminant(); + + const FixedList<FixedList<scalar, 3>, 3>& mat = *this; + + return + ( + (mat[1][0] * mat[2][1] - mat[1][1] * mat[2][0]) * source[0] + + (mat[0][1] * mat[2][0] - mat[0][0] * mat[2][1]) * source[1] + + (mat[0][0] * mat[1][1] - mat[0][1] * mat[1][0]) * source[2] + ) / det_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledMeshOctreeCubeCoordinates/labelledMeshOctreeCubeCoordinates.H b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledMeshOctreeCubeCoordinates/labelledMeshOctreeCubeCoordinates.H index 4cd1fb3e9e48a86c92ae46bbfbd1deabd570188b..1fc78e67aa98948d8fb0474d9d956967baf1318d 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledMeshOctreeCubeCoordinates/labelledMeshOctreeCubeCoordinates.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledMeshOctreeCubeCoordinates/labelledMeshOctreeCubeCoordinates.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class labelledMeshOctreeCubeCoordinates diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPair/labelledPair.H b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPair/labelledPair.H index 09dc894493fd25caeb501aeab53234fc449e2bd2..3bc9f168253a42272267839c0da2c012c3ff927c 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPair/labelledPair.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPair/labelledPair.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class labelledPair @@ -47,18 +46,18 @@ namespace Foam /*---------------------------------------------------------------------------*\ Class labelledPair Declaration \*---------------------------------------------------------------------------*/ - + class labelledPair { // Private data //- label label pLabel_; - + //- pair data labelPair pair_; - + public: - + // Constructors //- Null construct labelledPair() @@ -66,7 +65,7 @@ class labelledPair pLabel_(-1), pair_() {} - + //- Construct from label and pair labelledPair ( @@ -77,32 +76,32 @@ class labelledPair pLabel_(pl), pair_(lp) {} - + // Destructor ~labelledPair() {} - + // Member functions //- return pair label inline label pairLabel() const { return pLabel_; } - + //- return the pair inline const labelPair& pair() const { return pair_; } - + // Member operators - + inline void operator=(const labelledPair& lpp) { pLabel_ = lpp.pLabel_; pair_ = lpp.pair_; } - + inline bool operator== ( const labelledPair& lpp @@ -110,13 +109,17 @@ class labelledPair { if( pLabel_ != lpp.pLabel_ ) return false; - - if( (pair_ != lpp.pair_) && (pair_.reversePair() != lpp.pair_) ) - return false; - - return true; + + const labelPair& op = lpp.pair_; + + if( (pair_.first() == op.first()) && (pair_.second() == op.second()) ) + return true; + if( (pair_.first() == op.second()) && (pair_.second() == op.first()) ) + return true; + + return false; } - + inline bool operator!= ( const labelledPair& lcc @@ -124,33 +127,33 @@ class labelledPair { return !this->operator==(lcc); } - - inline bool operator<(const labelledPair& lpp) const - { - if( pLabel_ < lpp.pLabel_ ) - { - return true; - } - else if( pLabel_ > lpp.pLabel_ ) - { - return false; - } - - if( - (pair_.first() + pair_.second()) < - (lpp.pair().first() + lpp.pair().second()) - ) - return true; - - if( - Foam::min(pair_.first(), pair_.second()) < - Foam::min(lpp.pair().first(), lpp.pair().second()) - ) - return true; - - return false; - } - + + inline bool operator<(const labelledPair& lpp) const + { + if( pLabel_ < lpp.pLabel_ ) + { + return true; + } + else if( pLabel_ > lpp.pLabel_ ) + { + return false; + } + + if( + (pair_.first() + pair_.second()) < + (lpp.pair().first() + lpp.pair().second()) + ) + return true; + + if( + Foam::min(pair_.first(), pair_.second()) < + Foam::min(lpp.pair().first(), lpp.pair().second()) + ) + return true; + + return false; + } + // Friend operators friend Ostream& operator<< ( @@ -170,7 +173,7 @@ class labelledPair return os; } - + friend Istream& operator>> ( Istream& is, @@ -179,16 +182,16 @@ class labelledPair { // Read beginning of labelledPair is.readBegin("labelledPair"); - + is >> lpp.pLabel_; is >> lpp.pair_; - + // Read end of labelledPair is.readEnd("labelledPair"); - + // Check state of Istream is.check("operator>>(Istream&, labelledPair"); - + return is; } }; diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/labelledPoint.H b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/labelledPoint.H index 15610c54b09998d2c8b9c72932617b650f592273..304609dae28a00e8c07d0b61444be646cb846f33 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/labelledPoint.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/labelledPoint.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class labelledPoint @@ -85,22 +84,22 @@ class labelledPoint { return pLabel_; } - - inline label& pointLabel() - { - return pLabel_; - } + + inline label& pointLabel() + { + return pLabel_; + } //- return point coordinates inline const point& coordinates() const { return coords_; } - - inline point& coordinates() - { - return coords_; - } + + inline point& coordinates() + { + return coords_; + } // Member operators diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/refLabelledPoint.H b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/refLabelledPoint.H index 3f706faeb14583b54b21a964eece18f337c99839..5755742f2db421e2d7beb3bc7d81f210781031f8 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/refLabelledPoint.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPoint/refLabelledPoint.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class refLabelledPoint diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPointScalar/labelledPointScalar.H b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPointScalar/labelledPointScalar.H index f051bb9bf0b028681f544fbace3376865d754ad6..227510581859f2937f962d59be1ae63091cf2ec7 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPointScalar/labelledPointScalar.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPointScalar/labelledPointScalar.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class labelledPointScalar @@ -90,22 +89,22 @@ class labelledPointScalar { return pLabel_; } - - inline label& pointLabel() - { - return pLabel_; - } + + inline label& pointLabel() + { + return pLabel_; + } //- return point coordinates inline const point& coordinates() const { return coords_; } - - inline point& coordinates() - { - return coords_; - } + + inline point& coordinates() + { + return coords_; + } //- return scalar value inline const scalar& scalarValue() const diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPointScalar/refLabelledPointScalar.H b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPointScalar/refLabelledPointScalar.H new file mode 100644 index 0000000000000000000000000000000000000000..e6665b4a3e7444c1be0a9130006975d901b090bd --- /dev/null +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledPointScalar/refLabelledPointScalar.H @@ -0,0 +1,156 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + refLabelledPointScalar + +Description + A class containing a label and labelledPointScalar. It is used for + exchanging data over processors + +SourceFiles + +\*---------------------------------------------------------------------------*/ + +#ifndef refLabelledPointScalar_H +#define refLabelledPointScalar_H + +#include "labelledPointScalar.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +/*---------------------------------------------------------------------------*\ + Class refLabelledPointScalar Declaration +\*---------------------------------------------------------------------------*/ + +class refLabelledPointScalar +{ + // Private data + //- point label + label pLabel_; + + //- labelledPointScalar + labelledPointScalar lps_; + + public: + + // Constructors + //- Null construct + refLabelledPointScalar() + : + pLabel_(-1), + lps_() + {} + + //- Construct from label and labelledPointScalar + refLabelledPointScalar(const label pl, const labelledPointScalar& lps) + : + pLabel_(pl), + lps_(lps) + {} + + // Destructor + ~refLabelledPointScalar() + {} + + // Member functions + //- return object label + inline label objectLabel() const + { + return pLabel_; + } + + //- return labelledPointScalar + inline const labelledPointScalar& lps() const + { + return lps_; + } + + // Member operators + + inline void operator=(const refLabelledPointScalar& lps) + { + pLabel_ = lps.pLabel_; + lps_ = lps.lps_; + } + + inline bool operator==(const refLabelledPointScalar& lps) const + { + if( pLabel_ == lps.pLabel_ ) + return true; + + return false; + } + + inline bool operator!=(const refLabelledPointScalar& lps) const + { + return !this->operator==(lps); + } + + // Friend operators + friend Ostream& operator<<(Ostream& os, const refLabelledPointScalar& lps) + { + os << token::BEGIN_LIST; + os << lps.pLabel_ << token::SPACE; + os << lps.lps_ << token::END_LIST; + + // Check state of Ostream + os.check("operator<<(Ostream&, const labelledPointScalarS&"); + + return os; + } + + friend Istream& operator>>(Istream& is, refLabelledPointScalar& lps) + { + // Read beginning of refLabelledPointScalar + is.readBegin("refLabelledPointScalar"); + + is >> lps.pLabel_; + is >> lps.lps_; + + // Read end of refLabelledPointScalar + is.readEnd("refLabelledPointScalar"); + + // Check state of Istream + is.check("operator>>(Istream&, refLabelledPointScalar"); + + return is; + } +}; + +//- Specify data associated with refLabelledPointScalar type is contiguous +template<> +inline bool contiguous<refLabelledPointScalar>() {return true;} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledScalar/labelledScalar.H b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledScalar/labelledScalar.H index 94bbb899133763230ae89a4b02472be3ad876504..5a41da5be716b03e84182a175cf01f87c00f225b 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/labelledScalar/labelledScalar.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/labelledScalar/labelledScalar.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class labelledScalar @@ -48,18 +47,18 @@ namespace Foam /*---------------------------------------------------------------------------*\ Class labelledScalar Declaration \*---------------------------------------------------------------------------*/ - + class labelledScalar { // Private data //- label label sLabel_; - + //- value scalar value_; - + public: - + // Constructors //- Null construct labelledScalar() @@ -67,52 +66,84 @@ class labelledScalar sLabel_(-1), value_(0.0) {} - + //- Construct from label and value labelledScalar(const label sl, const scalar s) : sLabel_(sl), value_(s) {} - + // Destructor ~labelledScalar() {} - + // Member functions //- return scalar label inline label scalarLabel() const { return sLabel_; } - + //- return the value inline const scalar& value() const { return value_; } - + // Member operators - + inline void operator=(const labelledScalar& ls) { sLabel_ = ls.sLabel_; value_ = ls.value_; } - + inline bool operator==(const labelledScalar& ls) const { if( sLabel_ == ls.sLabel_ ) return true; - + return false; } - + + inline bool operator<(const labelledScalar& ls) const + { + if( value_ < ls.value_ ) + return true; + + return false; + } + + inline bool operator<=(const labelledScalar& ls) const + { + if( value_ <= ls.value_ ) + return true; + + return false; + } + + inline bool operator>(const labelledScalar& ls) const + { + if( value_ > ls.value_ ) + return true; + + return false; + } + + inline bool operator>=(const labelledScalar& ls) const + { + if( value_ >= ls.value_ ) + return true; + + return false; + } + inline bool operator!=(const labelledScalar& ls) const { return !this->operator==(ls); } - + // Friend operators friend Ostream& operator<<(Ostream& os, const labelledScalar& ls) { @@ -125,21 +156,21 @@ class labelledScalar return os; } - + friend Istream& operator>>(Istream& is, labelledScalar& ls) { // Read beginning of labelledScalar is.readBegin("labelledScalar"); - + is >> ls.sLabel_; is >> ls.value_; - + // Read end of labelledScalar is.readEnd("labelledScalar"); - + // Check state of Istream is.check("operator>>(Istream&, labelledScalar"); - + return is; } }; diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/parPartTet/parPartTet.H b/meshLibrary/utilities/helperClasses/parallelHelpers/parPartTet/parPartTet.H index 77f53d4cbc1fe8677f09cbdacd309082183a063f..179ca79bcb43dff7574c476c9bfe110b75ce07f1 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/parPartTet/parPartTet.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/parPartTet/parPartTet.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class parPartTet diff --git a/meshLibrary/utilities/helperClasses/parallelHelpers/parTriFace/parTriFace.H b/meshLibrary/utilities/helperClasses/parallelHelpers/parTriFace/parTriFace.H index f1ca677f2f93fabe3d3e17d18c92b1c285885abb..1b0741f9dffcab64b0a83e3f26623a895fe3bb39 100644 --- a/meshLibrary/utilities/helperClasses/parallelHelpers/parTriFace/parTriFace.H +++ b/meshLibrary/utilities/helperClasses/parallelHelpers/parTriFace/parTriFace.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class parTriFace @@ -49,23 +48,23 @@ namespace Foam /*---------------------------------------------------------------------------*\ Class parTriFace Declaration \*---------------------------------------------------------------------------*/ - + class parTriFace { // Private data label globalLabels_[3]; - + triangle<point, point> triPoints_; - + public: - + // Constructors - + inline parTriFace() : triPoints_(vector::zero, vector::zero, vector::zero) {} - + explicit inline parTriFace ( const label globalLabel0, @@ -80,36 +79,36 @@ class parTriFace globalLabels_[1] = globalLabel1; globalLabels_[2] = globalLabel2; } - + // Destructor - + ~parTriFace() {} - + // Member functions - + inline label globalLabelOfPoint(const label i) const { return globalLabels_[i]; } - + inline const triangle<point, point>& trianglePoints() const { return triPoints_; } - + // Member operators - + inline bool operator !=(const parTriFace& ptf) const { - Serr << "Not implemented" << endl; + Serr << "parTriFace::operator!= Not implemented" << endl; ::exit(1); - + return true; } - + // Friend operators - + inline friend Ostream& operator<<(Ostream& os, const parTriFace& ptf) { os << token::BEGIN_LIST; @@ -122,23 +121,23 @@ class parTriFace os.check("operator<<(Ostream&, const parTriFace&"); return os; } - + inline friend Istream& operator>>(Istream& is, parTriFace& ptf) { // Read beginning of parTriFace is.readBegin("parTriFace"); - + is >> ptf.globalLabels_[0]; is >> ptf.globalLabels_[1]; is >> ptf.globalLabels_[2]; is >> ptf.triPoints_; - + // Read end of parHelper is.readEnd("parTriFace"); - + // Check state of Istream is.check("operator>>(Istream&, parTriFace"); - + return is; } }; diff --git a/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.C b/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.C index 4880d4b180f3c12b60b1d7805392d6930ea7f768..412eae484ca5b42df85ef979a260aa2bc2559bff 100644 --- a/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.C +++ b/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,222 +40,222 @@ namespace Foam void sortEdgesIntoChains::createNodeLabels() { - label nPoints(0); - forAll(bEdges_, eI) - { - const edge& e = bEdges_[eI]; - if( !newNodeLabel_.found(e.start()) ) - newNodeLabel_.insert(e.start(), nPoints++); - if( !newNodeLabel_.found(e.end()) ) - newNodeLabel_.insert(e.end(), nPoints++); - } - - edgesAtPoint_.setSize(nPoints, DynList<label>(2)); - forAll(bEdges_, eI) - { - const edge& e = bEdges_[eI]; - label l = newNodeLabel_[e.start()]; - edgesAtPoint_[l].append(eI); - - l = newNodeLabel_[e.end()]; - edgesAtPoint_[l].append(eI); - } - - forAll(edgesAtPoint_, pI) - if( edgesAtPoint_[pI].size() % 2 ) - openEdges_ = true; + label nPoints(0); + forAll(bEdges_, eI) + { + const edge& e = bEdges_[eI]; + if( !newNodeLabel_.found(e.start()) ) + newNodeLabel_.insert(e.start(), nPoints++); + if( !newNodeLabel_.found(e.end()) ) + newNodeLabel_.insert(e.end(), nPoints++); + } + + edgesAtPoint_.setSize(nPoints, DynList<label>()); + forAll(bEdges_, eI) + { + const edge& e = bEdges_[eI]; + label l = newNodeLabel_[e.start()]; + edgesAtPoint_[l].append(eI); + + l = newNodeLabel_[e.end()]; + edgesAtPoint_[l].append(eI); + } + + forAll(edgesAtPoint_, pI) + if( edgesAtPoint_[pI].size() % 2 ) + openEdges_ = true; } - + bool sortEdgesIntoChains::findPointsBelongingToTheChain ( - const label currPos, - boolList& chainEdges + const label currPos, + boolList& chainEdges ) const { - # ifdef DEBUGSort - Info << "Finding point belonging to a chain" << endl; - # endif - - chainEdges.setSize(bEdges_.size()); - chainEdges = false; - - if( edgesAtPoint_[currPos].size() != 2 ) - return false; - - const label commonVrt = - bEdges_[edgesAtPoint_[currPos][0]].commonVertex - ( - bEdges_[edgesAtPoint_[currPos][1]] - ); - label prevVrt = bEdges_[edgesAtPoint_[currPos][0]].otherVertex(commonVrt); - label nextVrt = bEdges_[edgesAtPoint_[currPos][1]].otherVertex(commonVrt); - forAll(edgesAtPoint_[currPos], posI) - chainEdges[edgesAtPoint_[currPos][posI]] = true; - - # ifdef DEBUGSort - Info << "commonVrt " << commonVrt << endl; - Info << "prevVrt " << prevVrt << endl; - Info << "nextVrt " << nextVrt << endl; - # endif - - bool found; - do - { - found = false; - - const DynList<label>& vEdges = edgesAtPoint_[newNodeLabel_[prevVrt]]; - if( vEdges.size() == 2 ) - { - forAll(vEdges, eI) - if( !chainEdges[vEdges[eI]] ) - { - found = true; - chainEdges[vEdges[eI]] = true; - prevVrt = bEdges_[vEdges[eI]].otherVertex(prevVrt); - } - } - } while( found ); - - do - { - found = false; - - const DynList<label>& vEdges = edgesAtPoint_[newNodeLabel_[nextVrt]]; - if( vEdges.size() == 2 ) - { - forAll(vEdges, eI) - if( !chainEdges[vEdges[eI]] ) - { - found = true; - chainEdges[vEdges[eI]] = true; - nextVrt = bEdges_[vEdges[eI]].otherVertex(nextVrt); - } - } - } while( found ); - - if( - (edgesAtPoint_[newNodeLabel_[nextVrt]].size() != 2) && - (edgesAtPoint_[newNodeLabel_[prevVrt]].size() != 2) && - (prevVrt != nextVrt) - ) - { - chainEdges = false; - return false; - } - - # ifdef DEBUGSort - Info << "Chain edges " << chainEdges << endl; - # endif - - return true; + # ifdef DEBUGSort + Info << "Finding point belonging to a chain" << endl; + # endif + + chainEdges.setSize(bEdges_.size()); + chainEdges = false; + + if( edgesAtPoint_[currPos].size() != 2 ) + return false; + + const label commonVrt = + bEdges_[edgesAtPoint_[currPos][0]].commonVertex + ( + bEdges_[edgesAtPoint_[currPos][1]] + ); + label prevVrt = bEdges_[edgesAtPoint_[currPos][0]].otherVertex(commonVrt); + label nextVrt = bEdges_[edgesAtPoint_[currPos][1]].otherVertex(commonVrt); + forAll(edgesAtPoint_[currPos], posI) + chainEdges[edgesAtPoint_[currPos][posI]] = true; + + # ifdef DEBUGSort + Info << "commonVrt " << commonVrt << endl; + Info << "prevVrt " << prevVrt << endl; + Info << "nextVrt " << nextVrt << endl; + # endif + + bool found; + do + { + found = false; + + const DynList<label>& vEdges = edgesAtPoint_[newNodeLabel_[prevVrt]]; + if( vEdges.size() == 2 ) + { + forAll(vEdges, eI) + if( !chainEdges[vEdges[eI]] ) + { + found = true; + chainEdges[vEdges[eI]] = true; + prevVrt = bEdges_[vEdges[eI]].otherVertex(prevVrt); + } + } + } while( found ); + + do + { + found = false; + + const DynList<label>& vEdges = edgesAtPoint_[newNodeLabel_[nextVrt]]; + if( vEdges.size() == 2 ) + { + forAll(vEdges, eI) + if( !chainEdges[vEdges[eI]] ) + { + found = true; + chainEdges[vEdges[eI]] = true; + nextVrt = bEdges_[vEdges[eI]].otherVertex(nextVrt); + } + } + } while( found ); + + if( + (edgesAtPoint_[newNodeLabel_[nextVrt]].size() != 2) && + (edgesAtPoint_[newNodeLabel_[prevVrt]].size() != 2) && + (prevVrt != nextVrt) + ) + { + chainEdges = false; + return false; + } + + # ifdef DEBUGSort + Info << "Chain edges " << chainEdges << endl; + # endif + + return true; } void sortEdgesIntoChains::shrinkEdges(const boolList& chainEdges) { - forAll(chainEdges, eI) - if( chainEdges[eI] ) - { - const edge& e = bEdges_[eI]; - edgesAtPoint_[newNodeLabel_[e.start()]].removeElement - ( - edgesAtPoint_[newNodeLabel_[e.start()]].containsAtPosition(eI) - ); - - edgesAtPoint_[newNodeLabel_[e.end()]].removeElement - ( - edgesAtPoint_[newNodeLabel_[e.end()]].containsAtPosition(eI) - ); - } + forAll(chainEdges, eI) + if( chainEdges[eI] ) + { + const edge& e = bEdges_[eI]; + edgesAtPoint_[newNodeLabel_[e.start()]].removeElement + ( + edgesAtPoint_[newNodeLabel_[e.start()]].containsAtPosition(eI) + ); + + edgesAtPoint_[newNodeLabel_[e.end()]].removeElement + ( + edgesAtPoint_[newNodeLabel_[e.end()]].containsAtPosition(eI) + ); + } } void sortEdgesIntoChains::createChainFromEdges(const boolList& chainEdges) { - direction i(0); - forAll(chainEdges, eI) - if( chainEdges[eI] ) - ++i; - - labelList chainPoints(i); - i = 0; - - forAll(chainEdges, eI) - if( chainEdges[eI] ) - { - chainPoints[i++] = bEdges_[eI].start(); - chainPoints[i++] = bEdges_[eI].end(); - - # ifdef DEBUGSort - Info << "Init chainPoints " << chainPoints << endl; - # endif - - bool found; - do - { - # ifdef DEBUGSort - Info << "Iteration " << label(i-1) << endl; - # endif - - found = false; - const DynList<label>& pEdges = - edgesAtPoint_[newNodeLabel_[chainPoints[i-1]]]; - - forAll(pEdges, peI) - if( chainEdges[pEdges[peI]] ) - { - const label otherPoint = - bEdges_[pEdges[peI]].otherVertex(chainPoints[i-1]); - - # ifdef DEBUGSort - Info << "Other point " << otherPoint << endl; - # endif - if( otherPoint == -1 ) - continue; - if( chainPoints[i-2] == otherPoint ) - continue; - if( chainPoints[0] == otherPoint ) - continue; - - found = true; - chainPoints[i++] = otherPoint; - } - } while( found ); - - createdChains_.append(chainPoints); - - break; - } + direction i(0); + forAll(chainEdges, eI) + if( chainEdges[eI] ) + ++i; + + labelList chainPoints(i); + i = 0; + + forAll(chainEdges, eI) + if( chainEdges[eI] ) + { + chainPoints[i++] = bEdges_[eI].start(); + chainPoints[i++] = bEdges_[eI].end(); + + # ifdef DEBUGSort + Info << "Init chainPoints " << chainPoints << endl; + # endif + + bool found; + do + { + # ifdef DEBUGSort + Info << "Iteration " << label(i-1) << endl; + # endif + + found = false; + const DynList<label>& pEdges = + edgesAtPoint_[newNodeLabel_[chainPoints[i-1]]]; + + forAll(pEdges, peI) + if( chainEdges[pEdges[peI]] ) + { + const label otherPoint = + bEdges_[pEdges[peI]].otherVertex(chainPoints[i-1]); + + # ifdef DEBUGSort + Info << "Other point " << otherPoint << endl; + # endif + if( otherPoint == -1 ) + continue; + if( chainPoints[i-2] == otherPoint ) + continue; + if( chainPoints[0] == otherPoint ) + continue; + + found = true; + chainPoints[i++] = otherPoint; + } + } while( found ); + + createdChains_.append(chainPoints); + + break; + } } void sortEdgesIntoChains::sortEdges() { - createNodeLabels(); - - if( !openEdges_ ) - { - boolList chainEdges(bEdges_.size()); - forAll(edgesAtPoint_, pI) - if( findPointsBelongingToTheChain(pI, chainEdges) ) - { - createChainFromEdges(chainEdges); - - shrinkEdges(chainEdges); - } - } + createNodeLabels(); + + if( !openEdges_ ) + { + boolList chainEdges(bEdges_.size()); + forAll(edgesAtPoint_, pI) + if( findPointsBelongingToTheChain(pI, chainEdges) ) + { + createChainFromEdges(chainEdges); + + shrinkEdges(chainEdges); + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// sortEdgesIntoChains::sortEdgesIntoChains(const DynList<edge>& bEdges) : - bEdges_(bEdges), - openEdges_(false), - newNodeLabel_(), - edgesAtPoint_(), - createdChains_() + bEdges_(bEdges), + openEdges_(false), + newNodeLabel_(), + edgesAtPoint_(), + createdChains_() { - sortEdges(); + sortEdges(); } - + sortEdgesIntoChains::~sortEdgesIntoChains() { } @@ -265,7 +264,7 @@ sortEdgesIntoChains::~sortEdgesIntoChains() // Member functions const DynList<labelList>& sortEdgesIntoChains::sortedChains() const { - return createdChains_; + return createdChains_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.H b/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.H index cfc646e21bfc3425a511c6a93374cdb732fa32bd..2ac39ec369bfed7420d8e6ac62aa4c3f8b3ef6df 100644 --- a/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.H +++ b/meshLibrary/utilities/helperClasses/sortEdgesIntoChains/sortEdgesIntoChains.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class sortEdgesIntoChains @@ -51,45 +50,45 @@ namespace Foam class sortEdgesIntoChains { - // Members - const DynList<edge>& bEdges_; - - bool openEdges_; - - Map<label> newNodeLabel_; - - List<DynList<label> > edgesAtPoint_; - - DynList<labelList> createdChains_; - - // Private member functions - void createNodeLabels(); - - bool findPointsBelongingToTheChain - ( - const label currPos, - boolList& chainEdges - ) const; - - void shrinkEdges(const boolList& chainEdges); - - void createChainFromEdges(const boolList& chainEdges); - - void sortEdges(); - - public: - - sortEdgesIntoChains - ( - const DynList<edge>& bEdges - ); - - ~sortEdgesIntoChains(); - - // Member functions - - //- a list of points which have not yet been resolved - const DynList<labelList>& sortedChains() const; + // Members + const DynList<edge>& bEdges_; + + bool openEdges_; + + Map<label> newNodeLabel_; + + List<DynList<label> > edgesAtPoint_; + + DynList<labelList> createdChains_; + + // Private member functions + void createNodeLabels(); + + bool findPointsBelongingToTheChain + ( + const label currPos, + boolList& chainEdges + ) const; + + void shrinkEdges(const boolList& chainEdges); + + void createChainFromEdges(const boolList& chainEdges); + + void sortEdges(); + + public: + + sortEdgesIntoChains + ( + const DynList<edge>& bEdges + ); + + ~sortEdgesIntoChains(); + + // Member functions + + //- a list of points which have not yet been resolved + const DynList<labelList>& sortedChains() const; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.C b/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.C index 876d7c191090ab07563dea4267b2b8387e17abe7..30acb22cb364b20665285018eb79c42362ef3be3 100644 --- a/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.C +++ b/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -38,7 +37,7 @@ void trianglePlaneIntersections::calculateIntersections() const pointField& points = ts_.points(); const labelledTri& lt = ts_[ltri_]; - direction i(0); + label i(0); forAll(lt, pI) { vector v = points[lt[pI]] - pp_; @@ -47,12 +46,12 @@ void trianglePlaneIntersections::calculateIntersections() if( mag(v & n_) < SMALL ) { intersectedPoints_[pI] = true; - i++; + ++i; } } // hold the number of intersected edges - direction j(0); + label j(0); if( i == 2 ) { @@ -62,7 +61,7 @@ void trianglePlaneIntersections::calculateIntersections() { forAll(lt, eI) { - const direction next = (eI+1) % 3; + const label next = (eI+1) % 3; if( !intersectedPoints_[eI] && !intersectedPoints_[next] ) { @@ -76,7 +75,7 @@ void trianglePlaneIntersections::calculateIntersections() { edgePoints_[eI] = points[lt[eI]] + t * v; intersectedEdges_[eI] = true; - j++; + ++j; } } } @@ -103,7 +102,7 @@ trianglePlaneIntersections::trianglePlaneIntersections ( const vector& n, const point& pp, - const triSurface& ts, + const triSurf& ts, const label lI ) : @@ -124,7 +123,7 @@ trianglePlaneIntersections::~trianglePlaneIntersections() // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// // Member functions -direction trianglePlaneIntersections::triInfluence() const +label trianglePlaneIntersections::triInfluence() const { return influence_; } @@ -152,7 +151,7 @@ label trianglePlaneIntersections::determineRotation const face& f, const pointField& polyPoints, const face& newF, - const direction npI, + const label npI, const DynList<point>& newPoints ) const { @@ -163,7 +162,7 @@ label trianglePlaneIntersections::determineRotation bool in1 = help::pointInsideFace(intersectionPoints[1], f, n, polyPoints); // Info << "in0 " << in0 << " in1 " << in1 << endl; - + if( in0 && !in1 ) { return intersectedNeighbours[0]; @@ -172,11 +171,11 @@ label trianglePlaneIntersections::determineRotation { return intersectedNeighbours[1]; } - + vector ev(intersectionPoints[1] - intersectionPoints[0]); ev /= mag(ev); - const direction prev = (npI-1) >= 0?(npI-1):(newF.size()-1); + const label prev = (npI-1) >= 0?(npI-1):(newF.size()-1); vector pv = newPoints[newF[npI]] - newPoints[newF[prev]]; pv /= mag(pv); @@ -200,18 +199,18 @@ label trianglePlaneIntersections::determineRotation const vector& n, const pointField& fp, const face& newF, - const direction npI, + const label npI, const DynList<point>& newPoints, - direction& pointI + label& pointI ) const { - const labelList& fe = ts_.faceEdges()[ltri_]; - const labelListList& ef = ts_.edgeFaces(); + const constRow fe = ts_.facetEdges()[ltri_]; + const VRWGraph& ef = ts_.edgeFacets(); labelList neis(2); pointField eP(2); labelList interPoint(2, -1); - direction counter(0); + label counter(0); const pointField& points = ts_.points(); @@ -223,37 +222,37 @@ label trianglePlaneIntersections::determineRotation pointI = pI; return -1; } - + neis[counter] = -1; interPoint[counter] = pI; eP[counter++] = points[ts_[ltri_][pI]]; } - + forAll(intersectedEdges_, eJ) if( intersectedEdges_[eJ] ) { - label neighbour = ef[fe[eJ]][0]; + label neighbour = ef(fe[eJ], 0); if( neighbour == ltri_ ) - neighbour = ef[fe[eJ]][1]; - + neighbour = ef(fe[eJ], 1); + if( edgePointInsideFace(f, n, fp, eJ) ) return neighbour; - + neis[counter] = neighbour; eP[counter++] = edgePoints_[eJ]; } - + //- rotation is still not determined if( counter == 2 ) { vector v(eP[1] - eP[0]); v /= mag(v); - - const direction prev = ((npI-1)>=0?(npI-1):(newF.size()-1)); + + const label prev = ((npI-1)>=0?(npI-1):(newF.size()-1)); vector e(newPoints[newF[npI]] - newPoints[newF[prev]]); e /= mag(e); - + if( ((e ^ v) & n) >= 0.0 ) { if( interPoint[1] != -1 ) @@ -276,7 +275,7 @@ bool trianglePlaneIntersections::edgePointInsideFace const face& f, const vector& n, const pointField& fp, - const direction eI + const label eI ) const { return help::pointInsideFace(edgePoints_[eI], f, n, fp); @@ -287,7 +286,7 @@ bool trianglePlaneIntersections::pointInsideFace const face& f, const vector& n, const pointField& fp, - const direction pI + const label pI ) const { const pointField& points = ts_.points(); diff --git a/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.H b/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.H index e4aca2191d51f4b576dd73e17f48189365342bfa..cb0e6dc9a6adf7f247be3e3121d9670ca0d990a9 100644 --- a/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.H +++ b/meshLibrary/utilities/helperClasses/trianglePlaneIntersections/trianglePlaneIntersections.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class trianglePlaneIntersections @@ -36,8 +35,9 @@ SourceFiles #ifndef trianglePlaneIntersections_H #define trianglePlaneIntersections_H -#include "triSurface.H" +#include "triSurf.H" #include "DynList.H" +#include "boolList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -50,14 +50,14 @@ class trianglePlaneIntersections const vector& n_; const point& pp_; - const triSurface& ts_; + const triSurf& ts_; const label ltri_; boolList intersectedPoints_; pointField edgePoints_; boolList intersectedEdges_; - direction influence_; + label influence_; // Private member functions void calculateIntersections(); @@ -70,7 +70,7 @@ public: ( const vector&, const point&, - const triSurface&, + const triSurf&, const label ); @@ -90,7 +90,7 @@ public: // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Member functions - direction triInfluence() const; + label triInfluence() const; const boolList& intersectedPoints() const; @@ -106,7 +106,7 @@ public: const face&, const pointField&, const face&, - const direction, + const label, const DynList<point>& ) const; @@ -116,9 +116,9 @@ public: const vector&, const pointField&, const face&, - const direction, + const label, const DynList<point>&, - direction& + label& ) const; bool edgePointInsideFace @@ -126,7 +126,7 @@ public: const face&, const vector&, const pointField&, - const direction + const label ) const; bool pointInsideFace @@ -134,7 +134,7 @@ public: const face&, const vector&, const pointField&, - const direction + const label ) const; }; diff --git a/meshLibrary/utilities/helperFunctions/helperFunctions.H b/meshLibrary/utilities/helperFunctions/helperFunctions.H index 384d2f674af63a0b0eedfc9e71d96fda92ac79c5..02448841bc04ca8322da623027d91765539e5317 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctions.H +++ b/meshLibrary/utilities/helperFunctions/helperFunctions.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Namespace Foam::help @@ -41,6 +40,7 @@ SourceFiles #include "helperFunctionsTopologyManipulation.H" #include "helperFunctionsStringConversion.H" #include "helperFunctionsPar.H" +#include "helperFunctionsFrontalMarking.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsFrontalMarking.C b/meshLibrary/utilities/helperFunctions/helperFunctionsFrontalMarking.C new file mode 100644 index 0000000000000000000000000000000000000000..0c39b5c8cfbb7ea9dd69edad61386bf69c227b17 --- /dev/null +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsFrontalMarking.C @@ -0,0 +1,505 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "error.H" +#include "helperFunctionsFrontalMarking.H" +#include "DynList.H" +#include "labelPair.H" +#include "HashSet.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +namespace help +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +template<class labelListType, class neiOp, class filterOp> +void frontalMarking +( + labelListType& result, + const label startingIndex, + const neiOp& neighbourCalculator, + const filterOp& selector +) +{ + //- add the starting element + result.clear(); + result.append(startingIndex); + + //- add the starting element to the front + labelLongList front; + front.append(startingIndex); + + //- store information which element were already visited + boolList alreadySelected(neighbourCalculator.size(), false); + + //- start with frontal marking + while( front.size() ) + { + const label eLabel = front.removeLastElement(); + + //- find neighbours of the current element + DynList<label> neighbours; + neighbourCalculator(eLabel, neighbours); + + forAll(neighbours, neiI) + { + const label nei = neighbours[neiI]; + + if( nei < 0 ) + continue; + if( alreadySelected[nei] ) + continue; + + if( selector(nei) ) + { + alreadySelected[nei] = true; + front.append(nei); + result.append(nei); + } + } + } +} + +class graphNeiOp +{ + // Private data + //- const reference to VRWGraph + const VRWGraph& neiGroups_; + +public: + + // Constructors + //- Construct from VRWGraph + inline graphNeiOp(const VRWGraph& neiGroups) + : + neiGroups_(neiGroups) + {} + + // Public member functions + //- return the size of the graph + inline label size() const + { + return neiGroups_.size(); + } + + //- operator for finding neighbours + inline void operator()(const label groupI, DynList<label>& ng) const + { + ng.setSize(neiGroups_.sizeOfRow(groupI)); + forAllRow(neiGroups_, groupI, i) + ng[i] = neiGroups_(groupI, i); + } +}; + +class graphSelectorOp +{ + // Private data + //- const reference to VRWGraph + const VRWGraph& neiGroups_; + +public: + + // Constructors + //- Construct from VRWGraph + inline graphSelectorOp(const VRWGraph& neiGroups) + : + neiGroups_(neiGroups) + {} + + // Public member functions + //- operator for selecting elements + inline bool operator()(const label groupI) const + { + if( (groupI < 0) || (groupI >= neiGroups_.size()) ) + return false; + + return true; + } +}; + +template<class labelListType, class neiOp, class filterOp> +label groupMarking +( + labelListType& elementInGroup, + const neiOp& neighbourCalculator, + const filterOp& selector +) +{ + label nGroups(0); + + elementInGroup.setSize(neighbourCalculator.size()); + elementInGroup = -1; + + VRWGraph neighbouringGroups; + + label nThreads(1); + + # ifdef USE_OMP + //nThreads = 3 * omp_get_num_procs(); + # endif + + DynList<label> nGroupsAtThread(nThreads, 0); + + # ifdef USE_OMP + # pragma omp parallel num_threads(nThreads) + # endif + { + const label chunkSize = + Foam::max(1, neighbourCalculator.size() / nThreads); + + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif + + LongList<std::pair<label, label> > threadCommPairs; + + const label minEl = threadI * chunkSize; + + label maxEl = minEl + chunkSize; + if( threadI == (nThreads - 1) ) + maxEl = Foam::max(maxEl, neighbourCalculator.size()); + + label& groupI = nGroupsAtThread[threadI]; + groupI = 0; + + for(label elI=minEl;elI<maxEl;++elI) + { + if( elementInGroup[elI] != -1 ) + continue; + if( !selector(elI) ) + continue; + + elementInGroup[elI] = groupI; + labelLongList front; + front.append(elI); + + while( front.size() ) + { + const label eLabel = front.removeLastElement(); + + DynList<label> neighbours; + neighbourCalculator(eLabel, neighbours); + + forAll(neighbours, neiI) + { + const label nei = neighbours[neiI]; + + if( (nei < 0) || (elementInGroup[nei] != -1) ) + continue; + + if( (nei < minEl) || (nei >= maxEl) ) + { + //- this is a communication interface between + //- two threads + threadCommPairs.append(std::make_pair(elI, nei)); + } + else if( selector(nei) ) + { + //- this element is part of the same group + elementInGroup[nei] = groupI; + front.append(nei); + } + } + } + + ++groupI; + } + + # ifdef USE_OMP + # pragma omp barrier + + # pragma omp master + { + forAll(nGroupsAtThread, i) + nGroups += nGroupsAtThread[i]; + } + # else + nGroups = groupI; + # endif + + label startGroup(0); + for(label i=0;i<threadI;++i) + startGroup += nGroupsAtThread[i]; + + for(label elI=minEl;elI<maxEl;++elI) + elementInGroup[elI] += startGroup; + + # ifdef USE_OMP + # pragma omp barrier + # endif + + //- find group to neighbouring groups addressing + List<DynList<label> > localNeiGroups(nGroups); + forAll(threadCommPairs, cfI) + { + const std::pair<label, label>& lp = threadCommPairs[cfI]; + const label groupI = elementInGroup[lp.first]; + const label neiGroup = elementInGroup[lp.second]; + + if( (neiGroup >= nGroups) || (groupI >= nGroups) ) + FatalError << "neiGroup " << neiGroup + << " groupI " << groupI << " are >= than " + << "nGroups " << nGroups << abort(FatalError); + + if( neiGroup != -1 ) + { + localNeiGroups[groupI].appendIfNotIn(neiGroup); + localNeiGroups[neiGroup].appendIfNotIn(groupI); + } + } + + # ifdef USE_OMP + # pragma omp critical + # endif + { + neighbouringGroups.setSize(nGroups); + + forAll(localNeiGroups, groupI) + { + const DynList<label>& lGroups = localNeiGroups[groupI]; + + neighbouringGroups.appendIfNotIn(groupI, groupI); + + forAll(lGroups, i) + neighbouringGroups.appendIfNotIn(groupI, lGroups[i]); + } + } + } + + forAll(neighbouringGroups, i) + { + labelList helper(neighbouringGroups.sizeOfRow(i)); + forAllRow(neighbouringGroups, i, j) + helper[j] = neighbouringGroups(i, j); + + sort(helper); + + neighbouringGroups[i] = helper; + } + + //- start processing connections between the group and merge the connected + //- ones into a new group + DynList<label> globalGroupLabel; + globalGroupLabel.setSize(nGroups); + globalGroupLabel = -1; + + //- reduce the information about the groups + label counter(0); + + forAll(neighbouringGroups, groupI) + { + if( globalGroupLabel[groupI] != -1 ) + continue; + + DynList<label> connectedGroups; + frontalMarking + ( + connectedGroups, + groupI, + graphNeiOp(neighbouringGroups), + graphSelectorOp(neighbouringGroups) + ); + + forAll(connectedGroups, gI) + globalGroupLabel[connectedGroups[gI]] = counter; + + ++counter; + } + + nGroups = counter; + + forAll(neighbouringGroups, groupI) + { + if( globalGroupLabel[groupI] != -1 ) + continue; + + forAllRow(neighbouringGroups, groupI, ngI) + globalGroupLabel[neighbouringGroups(groupI, ngI)] = counter; + + ++counter; + } + + if( Pstream::parRun() ) + { + //- reduce the groups over processors of an MPI run + //- count the total number of groups over all processors + labelList nGroupsAtProc(Pstream::nProcs()); + nGroupsAtProc[Pstream::myProcNo()] = nGroups; + + Pstream::gatherList(nGroupsAtProc); + Pstream::scatterList(nGroupsAtProc); + + label startGroup(0), totalNumGroups(0); + for(label procI=0;procI<Pstream::nProcs();++procI) + { + totalNumGroups += nGroupsAtProc[procI]; + + if( procI < Pstream::myProcNo() ) + startGroup += nGroupsAtProc[procI]; + } + + //- translate group labels + forAll(globalGroupLabel, groupI) + globalGroupLabel[groupI] += startGroup; + + //- find the neighbouring groups + //- collect groups on other processors + //- this operator implements the algorithm for exchanging data + //- over processors and collects information which groups + //- are connected over inter-processor boundaries + std::map<label, DynList<label> > neiGroups; + + neighbourCalculator.collectGroups + ( + neiGroups, + elementInGroup, + globalGroupLabel + ); + + //- create a graph of connections + List<List<labelPair> > globalNeiGroups(Pstream::nProcs()); + + DynList<labelPair> connsAtProc; + for + ( + std::map<label, DynList<label> >::const_iterator it = + neiGroups.begin(); + it!=neiGroups.end(); + ++it + ) + { + const DynList<label>& ng = it->second; + + forAll(ng, i) + connsAtProc.append(labelPair(it->first, ng[i])); + } + + //- copy the connections into the global neighbour list + globalNeiGroups[Pstream::myProcNo()].setSize(connsAtProc.size()); + + forAll(connsAtProc, i) + globalNeiGroups[Pstream::myProcNo()][i] = connsAtProc[i]; + + //- communicate partial graphs to the master processor + Pstream::gatherList(globalNeiGroups); + + labelList allGroupsNewLabel; + if( Pstream::master() ) + { + //- collect the graph of connections for the whole system + VRWGraph allGroups(totalNumGroups); + forAll(allGroups, i) + allGroups[i].append(i); + + forAll(globalNeiGroups, procI) + { + const List<labelPair>& connections = globalNeiGroups[procI]; + + forAll(connections, i) + { + const labelPair& lp = connections[i]; + + allGroups.appendIfNotIn(lp.first(), lp.second()); + allGroups.appendIfNotIn(lp.second(), lp.first()); + } + } + + //- assign a global label to each group + allGroupsNewLabel.setSize(totalNumGroups); + allGroupsNewLabel = -1; + counter = 0; + + forAll(allGroups, groupI) + { + if( allGroupsNewLabel[groupI] != -1 ) + continue; + + DynList<label> connectedGroups; + frontalMarking + ( + connectedGroups, + groupI, + graphNeiOp(allGroups), + graphSelectorOp(allGroups) + ); + + forAll(connectedGroups, gI) + allGroupsNewLabel[connectedGroups[gI]] = counter; + + ++counter; + } + + nGroups = counter; + } + + //- broadcast group labels from the master to other processors + Pstream::scatter(nGroups); + Pstream::scatter(allGroupsNewLabel); + + //- assign correct group labels + forAll(globalGroupLabel, groupI) + { + const label ngI = globalGroupLabel[groupI]; + globalGroupLabel[groupI] = allGroupsNewLabel[ngI]; + } + } + + //- set the global group label + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(elementInGroup, elI) + { + if( elementInGroup[elI] < 0 ) + continue; + + elementInGroup[elI] = globalGroupLabel[elementInGroup[elI]]; + } + + return nGroups; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +} // End namespace help + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsFrontalMarking.H b/meshLibrary/utilities/helperFunctions/helperFunctionsFrontalMarking.H new file mode 100644 index 0000000000000000000000000000000000000000..2e25145f92d07f8ac59e21e0335053416c67785a --- /dev/null +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsFrontalMarking.H @@ -0,0 +1,97 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + helperFunctionsPar + +Description + Functions used for exchanging data between processors + +SourceFiles + +\*---------------------------------------------------------------------------*/ + +#ifndef helperFunctionsFrontalMarking_H +#define helperFunctionsFrontalMarking_H + +#include "labelList.H" +#include "LongList.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +namespace help +{ + +//- template implementation of the fron-marking algorithm +//- labelListType contains indices of elements satisfying the filtering criteria +//- startingIndex is the first element from where the search is started +//- neiOp determines which neighbouring elements are available. It requires +//- an operator neiOp(const label, DynList<label>&) to be defined +//- filterOp determines which neighbouring elements shall be stored +//- in the result and used in the front. It requires an operator +//- bool filterOp(const label) which return true if the element shall be part +//- of the front +template<class labelListType, class neiOp, class filterOp> +void frontalMarking +( + labelListType& result, + const label startingIndex, + const neiOp& neighbourCalculator, + const filterOp& selector +); + +//- templated implementation of functionality for finding discrete groups +//- of elements depending on the user-defined criteria +//- the first argument is the result of the operation. Each element is assigned +//- to a group amd the ones failing the critearia are set to -1 +//- neiOp is the functionality for determining neighbours of the currently +//- processed front element. This class requires an operator +//- neiOp(const label, DynList<label>&) +//- filterOp represents the user-defined criteria and shall have an operator +//- bool filterOp(const label) +template<class labelListType, class neiOp, class filterOp> +label groupMarking +( + labelListType& elementInGroup, + const neiOp& neighbourCalculator, + const filterOp& selector +); + +} // End namespace help + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +#ifdef NoRepository +# include "helperFunctionsFrontalMarking.C" +#endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueries.H b/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueries.H index 4e02732bc869cb974d855201bd77125dc8ec0f96..6dd12535f6a8d983e1b99e6d39ee448b0747e4fd 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueries.H +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueries.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. InNamespace Foam::help @@ -39,22 +38,33 @@ SourceFiles #include "plane.H" #include "face.H" +#include "triSurf.H" +#include "triangle.H" +#include "tetrahedron.H" + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // class boolList; class labelHashSet; class boundBox; -class triSurface; namespace Foam { - + /*---------------------------------------------------------------------------*\ Namespace help functions Declaration \*---------------------------------------------------------------------------*/ namespace help { + //- check if a list has nan entries + template<class ListType> + bool isnan(const ListType&); + + //- check if a list has inf entries + template<class ListType> + bool isinf(const ListType&); + //- check if the faces share a convex edge bool isSharedEdgeConvex ( @@ -79,7 +89,7 @@ namespace help const edge& e, const pointField& ep ); - + //- check if the point p belongs to the plane inline bool vertexInPlane(const point& p, const plane& pl); @@ -90,7 +100,7 @@ namespace help const point& edgePoint1, const point& p ); - + //- find the vertex on the edge nearest to the point p inline point nearestPointOnTheEdgeExact ( @@ -98,7 +108,7 @@ namespace help const point& edgePoint1, const point& p ); - + //- find and return the distance between the edge and the point p inline scalar distanceOfPointFromTheEdge ( @@ -106,7 +116,7 @@ namespace help const point& edgePoint1, const point& p ); - + //- find the nearest points on the edge and the line inline bool nearestEdgePointToTheLine ( @@ -117,7 +127,7 @@ namespace help point& nearestOnEdge, point& nearestOnLine ); - + //- check if the edge intersects the plane inline bool planeIntersectsEdge ( @@ -126,17 +136,33 @@ namespace help const plane& pl, point& intersection ); - + + //- check if a vertex lies inside the tetrahedron + inline bool pointInTetrahedron + ( + const point& p, + const tetrahedron<point, point>& tet + ); + + //- check if a line intersects the triangle, and return the intersection + inline bool triLineIntersection + ( + const triangle<point, point>& tria, + const point& lineStart, + const point& lineEnd, + point& intersection + ); + //- check if a line intersects the triangle and return the intersection inline bool triLineIntersection ( - const triSurface&, + const triSurf&, const label, const point&, const point&, point& ); - + //- check if the line intersects the bounding box inline bool boundBoxLineIntersection ( @@ -144,24 +170,24 @@ namespace help const point&, const boundBox& ); - + //- check if the surface triangle and the face intersect inline bool doFaceAndTriangleIntersect ( - const triSurface& surface, + const triSurf& surface, const label triI, const face& f, const pointField& facePoints ); - + //- find the nearest vertex on the surface triangle to the given point inline point nearestPointOnTheTriangle ( const label, - const triSurface&, + const triSurf&, const point& ); - + //- check if the point is inside or outside the face inline bool pointInsideFace ( @@ -170,7 +196,7 @@ namespace help const vector& n, const pointField& fp ); - + //- check if the point is inside or outside the face inline bool pointInsideFace ( @@ -178,26 +204,26 @@ namespace help const face& f, const pointField& fp ); - + //- check if the vertex is on the positive side of the face plane inline bool isVertexVisible(const point& p, const plane& pl); - + //- find number of face groups within a given range inline label numberOfFaceGroups ( const labelHashSet& containedElements, const point& centre, const scalar range, - const triSurface& surface + const triSurf& surface ); - + //- find the number of edge groups within the given range inline label numberOfEdgeGroups ( const labelHashSet& containedEdges, const point& centre, const scalar range, - const triSurface& surface + const triSurf& surface ); } // End namespace help diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueriesI.H b/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueriesI.H index 66bf475c70401e5d68d72a359a5a96799f5fb911..d81f5a287591c27fb2a0143fe17b96ba98f960f5 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueriesI.H +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsGeometryQueriesI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -32,11 +31,12 @@ Description #include "edgeList.H" #include "pointField.H" #include "boolList.H" -#include "triSurface.H" +#include "triSurf.H" #include "matrix3D.H" #include "HashSet.H" #include "tetrahedron.H" #include "boundBox.H" +#include "Map.H" //#define DEBUG_pMesh @@ -50,6 +50,26 @@ namespace help // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// +template<class ListType> +inline bool isnan(const ListType& l) +{ + forAll(l, i) + if( l[i] != l[i] ) + return true; + + return false; +} + +template<class ListType> +bool isinf(const ListType& l) +{ + forAll(l, i) + if( (l[i] < -VGREAT) || (l[i] > VGREAT) ) + return true; + + return false; +} + inline bool isSharedEdgeConvex ( const pointField& points, @@ -108,7 +128,7 @@ inline faceList mergePatchFaces { //- merge faces which share a common edge faceList patchFaces(pfcs.size()); - direction counter(0); + label counter(0); forAll(pfcs, faceI) if( pfcs[faceI].size() > 2 ) { @@ -131,12 +151,12 @@ inline faceList mergePatchFaces counter = 0; merged = false; - for(direction nI=0;nI<(patchFaces.size()-1);nI++) + for(label nI=0;nI<(patchFaces.size()-1);nI++) { vector n0 = patchFaces[nI].normal(polyPoints); n0 /= mag(n0); - for(direction nJ=nI+1;nJ<patchFaces.size();nJ++) + for(label nJ=nI+1;nJ<patchFaces.size();nJ++) { vector n1 = patchFaces[nI].normal(polyPoints); n1 /= mag(n1); @@ -168,7 +188,7 @@ inline faceList mergePatchFaces if( merged ) { patchFaces.setSize(counter); - for(direction k=0;k<counter;k++) + for(label k=0;k<counter;k++) patchFaces[k] = mergedFaces[k]; } @@ -233,23 +253,16 @@ inline bool planeIntersectsEdge return false; } -inline bool triLineIntersection +inline bool pointInTetrahedron ( - const triSurface& surface, - const label tI, - const point& s, - const point& e, - point& intersection + const point& p, + const tetrahedron<point, point>& tet ) { - const pointField& points = surface.points(); - const labelledTri& ltri = surface.localFaces()[tI]; - - const point& p0 = points[ltri[0]]; - const vector v(s - e); - const vector v0 = points[ltri[1]] - p0; - const vector v1 = points[ltri[2]] - p0; - const vector sp = s - p0; + const vector v0 = tet.a() - tet.d(); + const vector v1 = tet.b() - tet.d(); + const vector v2 = tet.c() - tet.d(); + const vector sp = p - tet.d(); matrix3D mat; FixedList<scalar, 3> source; @@ -257,23 +270,20 @@ inline bool triLineIntersection { mat[i][0] = v0[i]; mat[i][1] = v1[i]; - mat[i][2] = v[i]; + mat[i][2] = v2[i]; source[i] = sp[i]; } + //- check the determinant of the transformation const scalar det = mat.determinant(); if( mag(det) < VSMALL ) return false; - const scalar t = mat.solveThird(source); - - if( (t < -SMALL) || (t > (1.0+SMALL)) ) - return false; - + //- get the coordinates of the point in the barycentric corrdinate system const scalar u0 = mat.solveFirst(source); - if( u0 < -SMALL ) + if( (u0 < -SMALL) || (u0 > (1.0+SMALL)) ) return false; const scalar u1 = mat.solveSecond(source); @@ -281,129 +291,87 @@ inline bool triLineIntersection if( (u1 < -SMALL) || ((u0+u1) > (1.0+SMALL)) ) return false; - intersection = s - t * v; + const scalar u2 = mat.solveThird(source); + + if( (u2 < -SMALL) || (u2 > (1.0+SMALL)) ) + return false; + + + const scalar u3 = 1.0 - u0 - u1 - u2; + + if( (u3 < -SMALL) || (u3 > (1.0+SMALL)) ) + return false; + return true; } -inline bool boundBoxLineIntersection +inline bool nearestEdgePointToTheLine ( - const point& s, - const point& e, - const boundBox& bb + const point& edgePoint0, + const point& edgePoint1, + const point& lp0, + const point& lp1, + point& nearestOnEdge, + point& nearestOnLine ) { - scalar tMax(1.0+SMALL), tMin(-SMALL); - - const vector v = e - s; - const scalar d = mag(v); - - //- check if the vector has length - if( d < VSMALL ) - { - if( bb.contains(s) ) - return true; + const vector v = lp1 - lp0; + const vector d = lp0 - edgePoint0; + const vector e = edgePoint1 - edgePoint0; + const scalar vMag = mag(v); + if( vMag < VSMALL ) return false; - } - const point& pMin = bb.min(); - const point& pMax = bb.max(); - - //- check coordinates - for(label dir=0;dir<3;++dir) + const scalar eMag = mag(e); + if( eMag < VSMALL ) { - const scalar vd = v[dir]; - const scalar sd = s[dir]; - - if( mag(vd) > (SMALL * d) ) - { - if( vd >= 0.0 ) - { - tMin = Foam::max(tMin, (pMin[dir] - sd) / vd); - tMax = Foam::min(tMax, (pMax[dir] - sd) / vd); - } - else - { - tMin = Foam::max(tMin, (pMax[dir] - sd) / vd); - tMax = Foam::min(tMax, (pMin[dir] - sd) / vd); - } - } - else if( (sd < pMin[dir]) || (sd > pMax[dir]) ) - { - return false; - } + nearestOnEdge = edgePoint0; + nearestOnLine = nearestPointOnTheEdge(lp0, lp1, nearestOnEdge); + return true; } - if( (tMax - tMin) > -SMALL ) - return true; + if( mag((v/vMag) & (e/eMag)) > (1.0 - SMALL) ) + return false; - return false; -} + tensor mat(tensor::zero); + mat.xx() = (v&v); + mat.xy() = mat.yx() = -1.0 * (v&e); + mat.yy() = (e&e); + mat.zz() = SMALL; -inline bool doFaceAndTriangleIntersect -( - const triSurface& surface, - const label triI, - const face& f, - const pointField& facePoints -) -{ - const pointField& triPoints = surface.localPoints(); + vector source(vector::zero); + source[0] = -1.0 * (d&v); + source[1] = (d&e); - vector n = f.normal(facePoints); - n /= mag(n); - const point centre = f.centre(facePoints); - plane pl(centre, n); - point intersection(vector::zero); + const vector sol = (inv(mat) & source); - //- check if any triangle edge intersects the face - const edgeList triEdges = surface[triI].edges(); - forAll(triEdges, eI) + nearestOnLine = lp0 + v * sol[0]; + if( sol[1] > 1.0 ) { - const edge& e = triEdges[eI]; - help::planeIntersectsEdge - ( - triPoints[e.start()], - triPoints[e.end()], - pl, - intersection - ); - - if( help::pointInsideFace(intersection, f, n, facePoints) ) - return true; + nearestOnEdge = edgePoint1; } - - //- check if any face edges intersect the triangle - const edgeList fEdges = f.edges(); - forAll(fEdges, feI) + else if( sol[1] < 0.0 ) { - const edge& e = fEdges[feI]; - - if( - help::triLineIntersection - ( - surface, - triI, - facePoints[e.start()], - facePoints[e.end()], - intersection - ) - ) - return true; + nearestOnEdge = edgePoint0; + } + else + { + nearestOnEdge = edgePoint0 + e * sol[1]; } - return false; + return true; } inline point nearestPointOnTheTriangle ( const label tI, - const triSurface& surface, + const triSurf& surface, const point& p ) { const labelledTri& ltri = surface[tI]; - const pointField& points = surface.localPoints(); + const pointField& points = surface.points(); const vector v0 = points[ltri[1]] - points[ltri[0]]; const vector v1 = points[ltri[2]] - points[ltri[0]]; @@ -516,6 +484,198 @@ inline point nearestPointOnTheTriangle return pProj; } +inline bool triLineIntersection +( + const triangle<point, point>& tria, + const point& lineStart, + const point& lineEnd, + point& intersection +) +{ + const point& p0 = tria.a(); + const vector v(lineStart - lineEnd); + const vector v0 = tria.b() - p0; + const vector v1 = tria.c() - p0; + const vector sp = lineStart - p0; + + matrix3D mat; + FixedList<scalar, 3> source; + for(label i=0;i<3;++i) + { + mat[i][0] = v0[i]; + mat[i][1] = v1[i]; + mat[i][2] = v[i]; + source[i] = sp[i]; + } + + const scalar det = mat.determinant(); + + if( mag(det) < SMALL ) + return false; + + const scalar t = mat.solveThird(source); + + if( (t < -SMALL) || (t > (1.0+SMALL)) ) + return false; + + const scalar u0 = mat.solveFirst(source); + + if( u0 < -SMALL ) + return false; + + const scalar u1 = mat.solveSecond(source); + + if( (u1 < -SMALL) || ((u0+u1) > (1.0+SMALL)) ) + return false; + + intersection = lineStart - t * v; + return true; +} + +inline bool triLineIntersection +( + const triSurf& surface, + const label tI, + const point& s, + const point& e, + point& intersection +) +{ + const pointField& pts = surface.points(); + const labelledTri& tri = surface[tI]; + + const triangle<point, point> tria + ( + pts[tri[0]], + pts[tri[1]], + pts[tri[2]] + ); + + return triLineIntersection(tria, s, e, intersection); +} + +inline bool boundBoxLineIntersection +( + const point& s, + const point& e, + const boundBox& bb +) +{ + scalar tMax(1.0+SMALL), tMin(-SMALL); + + const vector v = e - s; + const scalar d = mag(v); + + //- check if the vector has length + if( d < VSMALL ) + { + if( bb.contains(s) ) + return true; + + return false; + } + + const point& pMin = bb.min(); + const point& pMax = bb.max(); + + //- check coordinates + for(label dir=0;dir<3;++dir) + { + const scalar vd = v[dir]; + const scalar sd = s[dir]; + + if( mag(vd) > (SMALL * d) ) + { + if( vd >= 0.0 ) + { + tMin = Foam::max(tMin, (pMin[dir] - sd) / vd); + tMax = Foam::min(tMax, (pMax[dir] - sd) / vd); + } + else + { + tMin = Foam::max(tMin, (pMax[dir] - sd) / vd); + tMax = Foam::min(tMax, (pMin[dir] - sd) / vd); + } + } + else if( (sd < pMin[dir]) || (sd > pMax[dir]) ) + { + return false; + } + } + + if( (tMax - tMin) > -SMALL ) + return true; + + return false; +} + +inline bool doFaceAndTriangleIntersect +( + const triSurf& surface, + const label triI, + const face& f, + const pointField& facePoints +) +{ + const pointField& triPoints = surface.points(); + + const point centre = f.centre(facePoints); + point intersection; + + //- check if any triangle edge intersects the face + const labelledTri& tri = surface[triI]; + + forAll(tri, eI) + { + const point& s = triPoints[tri[eI]]; + const point& e = triPoints[tri[(eI+1)%3]]; + + forAll(f, pI) + { + const triangle<point, point> tria + ( + facePoints[f[pI]], + facePoints[f.nextLabel(pI)], + centre + ); + + const bool currIntersection = + help::triLineIntersection + ( + tria, + s, + e, + intersection + ); + + if( currIntersection ) + return true; + } + } + + //- check if any face edges intersect the triangle + forAll(f, pI) + { + const point& s = facePoints[f[pI]]; + const point& e = facePoints[f.nextLabel(pI)]; + + const bool intersected = + help::triLineIntersection + ( + surface, + triI, + s, + e, + intersection + ); + + if( intersected ) + return true; + } + + return false; +} + inline bool pointInsideFace ( const point& p, @@ -632,76 +792,18 @@ inline scalar distanceOfPointFromTheEdge return mag(nearestPointOnTheEdge(edgePoint0, edgePoint1, p) - p); } -inline bool nearestEdgePointToTheLine -( - const point& edgePoint0, - const point& edgePoint1, - const point& lp0, - const point& lp1, - point& nearestOnEdge, - point& nearestOnLine -) -{ - const vector v = lp1 - lp0; - const vector d = lp0 - edgePoint0; - const vector e = edgePoint1 - edgePoint0; - - const scalar vMag = mag(v); - if( vMag < VSMALL ) - return false; - - const scalar eMag = mag(e); - if( eMag < VSMALL ) - { - nearestOnEdge = edgePoint0; - nearestOnLine = nearestPointOnTheEdge(lp0, lp1, nearestOnEdge); - return true; - } - - if( mag((v/vMag) & (e/eMag)) > (1.0 - SMALL) ) - return false; - - tensor mat(tensor::zero); - mat.xx() = (v&v); - mat.xy() = mat.yx() = -1.0 * (v&e); - mat.yy() = (e&e); - mat.zz() = SMALL; - - vector source(vector::zero); - source[0] = -1.0 * (d&v); - source[1] = (d&e); - - const vector sol = (inv(mat) & source); - - nearestOnLine = lp0 + v * sol[0]; - if( sol[1] > 1.0 ) - { - nearestOnEdge = edgePoint1; - } - else if( sol[1] < 0.0 ) - { - nearestOnEdge = edgePoint0; - } - else - { - nearestOnEdge = edgePoint0 + e * sol[1]; - } - - return true; -} - inline label numberOfFaceGroups ( const labelHashSet& containedElements, const point& centre, const scalar range, - const triSurface& surface + const triSurf& surface ) { const pointField& points = surface.points(); - const edgeList& edges = surface.edges(); - const labelListList& faceEdges = surface.faceEdges(); - const labelListList& edgeFaces = surface.edgeFaces(); + const edgeLongList& edges = surface.edges(); + const VRWGraph& faceEdges = surface.facetEdges(); + const VRWGraph& edgeFaces = surface.edgeFacets(); labelHashSet triaInRange(containedElements.size()); const scalar rangeSq = range * range; @@ -717,7 +819,7 @@ inline label numberOfFaceGroups label nGroups(0); - DynList<label> front(containedElements.size()); + DynList<label> front; forAllConstIter(labelHashSet, triaInRange, it) if( !elGroup.found(it.key()) ) @@ -729,11 +831,10 @@ inline label numberOfFaceGroups while( front.size() ) { const label fLabel = front.removeLastElement(); - const labelList& fEdges = faceEdges[fLabel]; - forAll(fEdges, feI) + forAllRow(faceEdges, fLabel, feI) { - const label edgeI = fEdges[feI]; + const label edgeI = faceEdges(fLabel, feI); //- check if the edge intersects the bounding box if( testEdge.found(edgeI) ) @@ -757,10 +858,9 @@ inline label numberOfFaceGroups } } - const labelList& eFaces = edgeFaces[edgeI]; - forAll(eFaces, efI) + forAllRow(edgeFaces, edgeI, efI) { - const label nei = eFaces[efI]; + const label nei = edgeFaces(edgeI, efI); if ( triaInRange.found(nei) && @@ -785,12 +885,12 @@ inline label numberOfEdgeGroups const labelHashSet& containedEdges, const point& centre, const scalar range, - const triSurface& surface + const triSurf& surface ) { const pointField& points = surface.points(); - const edgeList& edges = surface.edges(); - const labelListList& pointEdges = surface.pointEdges(); + const edgeLongList& edges = surface.edges(); + const VRWGraph& pointEdges = surface.pointEdges(); const scalar rangeSq = range * range; labelHashSet edgesInRange(containedEdges.size()); @@ -810,7 +910,7 @@ inline label numberOfEdgeGroups label nGroups(0); - DynList<label> front(containedEdges.size()); + DynList<label> front; forAllConstIter(labelHashSet, edgesInRange, it) if( !elGroup.found(it.key()) ) @@ -844,11 +944,9 @@ inline label numberOfEdgeGroups } } - const labelList& pEdges = pointEdges[e[i]]; - - forAll(pEdges, peI) + forAllRow(pointEdges, e[i], peI) { - const label nei = pEdges[peI]; + const label nei = pointEdges(e[i], peI); if( edgesInRange.found(nei) && !elGroup.found(nei) ) { diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsPar.C b/meshLibrary/utilities/helperFunctions/helperFunctionsPar.C index 0d894432a2a5c62cb8087ab39a329c76b2b99d28..5ba966482271e920719a313e247bdcffc1e2b5bd 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsPar.C +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsPar.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -32,9 +31,9 @@ Description #include "labelPair.H" #include "HashSet.H" +# ifdef USE_OMP #include <omp.h> - -#define DEBUGExchangeMap +# endif namespace Foam { @@ -51,11 +50,11 @@ void combineData(const sendOp& sop, combineOp& cop) { std::map<label, LongList<T> > sMap; sop(sMap); - + LongList<T> data; - + exchangeMap(sMap, data); - + cop(data); } @@ -74,7 +73,7 @@ void whisperReduce(const ListType& neis, const scatterOp& sop, gatherOp& gop) below.append(neis[i]); } } - + //- receive the data from the processors above forAll(above, aboveI) { @@ -82,23 +81,23 @@ void whisperReduce(const ListType& neis, const scatterOp& sop, gatherOp& gop) List<T> receivedData; IPstream fromOtherProc(Pstream::blocking, above[aboveI]); fromOtherProc >> receivedData; - + gop(receivedData); } - + //- send the data to the processors below forAll(below, belowI) { const label neiProc = below[belowI]; - + LongList<T> dts; sop(dts); - + //- send the data OPstream toOtherProc(Pstream::blocking, neiProc, dts.byteSize()); toOtherProc << dts; } - + //- gather the data from the processors below to the processors above //- receive the data from the processors below forAllReverse(below, belowI) @@ -107,24 +106,24 @@ void whisperReduce(const ListType& neis, const scatterOp& sop, gatherOp& gop) List<T> receivedData; IPstream fromOtherProc(Pstream::blocking, below[belowI]); fromOtherProc >> receivedData; - + gop(receivedData); } - + //- send the data to the processors below forAllReverse(above, aboveI) { const label neiProc = above[aboveI]; - + LongList<T> dts; sop(dts); - + //- send the data OPstream toOtherProc(Pstream::blocking, neiProc, dts.byteSize()); toOtherProc << dts; } } - + template<class T, class ListType> void exchangeMap ( @@ -134,44 +133,44 @@ void exchangeMap ) { data.clear(); - + if( !contiguous<T>() ) FatalError << "Data is not contiguous" << exit(FatalError); - + typename std::map<label, ListType>::const_iterator iter; - + //- check which processors shall exchange the data and which ones shall not labelHashSet receiveData; for(iter=m.begin();iter!=m.end();++iter) { OPstream toOtherProc(Pstream::blocking, iter->first, sizeof(label)); - + toOtherProc << iter->second.size(); } - + for(iter=m.begin();iter!=m.end();++iter) { IPstream fromOtherProc(Pstream::blocking, iter->first, sizeof(label)); - + label s; fromOtherProc >> s; - + if( s != 0 ) receiveData.insert(iter->first); } - + if( commsType == Pstream::blocking ) { //- start with blocking type of send and received operation - + //- send data to other processors for(iter=m.begin();iter!=m.end();++iter) { const ListType& dts = iter->second; - + if( dts.size() == 0 ) continue; - + OPstream toOtherProc ( Pstream::blocking, @@ -180,13 +179,13 @@ void exchangeMap ); toOtherProc << dts; } - + //- receive data from other processors for(iter=m.begin();iter!=m.end();++iter) { if( !receiveData.found(iter->first) ) continue; - + IPstream fromOtherProc(Pstream::blocking, iter->first); data.appendFromStream(fromOtherProc); } @@ -196,7 +195,7 @@ void exchangeMap //- start with scheduled data transfer //- this type of transfer is intended for long messages because //- it does not require any buffer - + //- receive data from processors with lower ids for(iter=m.begin();iter!=m.end();++iter) { @@ -209,32 +208,32 @@ void exchangeMap IPstream fromOtherProc(Pstream::scheduled, iter->first); //fromOtherProc >> receive; data.appendFromStream(fromOtherProc); - + //forAll(receive, i) // data.append(receive[i]); } - + //- send data to processors with greater ids for(iter=m.begin();iter!=m.end();++iter) { if( iter->first <= Pstream::myProcNo() ) continue; - + const ListType& dts = iter->second; - + if( dts.size() == 0 ) continue; - + OPstream toOtherProc ( Pstream::scheduled, iter->first, dts.byteSize() ); - + toOtherProc << dts; } - + //- receive data from processors with greater ids typename std::map<label, ListType>::const_reverse_iterator riter; for(riter=m.rbegin();riter!=m.rend();++riter) @@ -248,29 +247,29 @@ void exchangeMap //List<T> receive; //fromOtherProc >> receive; data.appendFromStream(fromOtherProc); - + //forAll(receive, i) // data.append(receive[i]); } - + //- send data to processors with lower ids for(riter=m.rbegin();riter!=m.rend();++riter) { if( riter->first >= Pstream::myProcNo() ) continue; - + const ListType& dts = riter->second; - + if( dts.size() == 0 ) continue; - + OPstream toOtherProc ( Pstream::scheduled, riter->first, dts.byteSize() ); - + toOtherProc << dts; } } @@ -284,14 +283,14 @@ void exchangeMap " const Pstream::commsTypes commsType)" ) << "Unknown communication type" << exit(FatalError); } - + # ifdef DEBUGExchangeMap labelList nReceived(Pstream::nProcs(), 0); for(iter=m.begin();iter!=m.end();++iter) nReceived[iter->first] += iter->second.size(); - + reduce(nReceived, sumOp<labelList>()); - + if( nReceived[Pstream::myProcNo()] != data.size() ) FatalError << "Invalid data read!" << abort(FatalError); # endif @@ -305,17 +304,17 @@ void exchangeMap ) { mOut.clear(); - + if( !contiguous<T>() ) FatalError << "Data is not contigous" << exit(FatalError); - + typename std::map<label, ListType>::const_iterator iter; - + //- send data to other processors for(iter=m.begin();iter!=m.end();++iter) { const ListType& dataToSend = iter->second; - + OPstream toOtherProc ( Pstream::blocking, @@ -324,13 +323,13 @@ void exchangeMap ); toOtherProc << dataToSend; } - + //- receive data from other processors for(iter=m.begin();iter!=m.end();++iter) { mOut.insert(std::make_pair(iter->first, List<T>())); List<T>& dataToReceive = mOut[iter->first]; - + IPstream fromOtherProc(Pstream::blocking, iter->first); fromOtherProc >> dataToReceive; } @@ -345,69 +344,90 @@ void reverseAddressingSMP { reverseAddr.setSize(0); labelList nAppearances; - + label minRow(INT_MAX), maxRow(0); DynList<std::map<label, DynList<labelPair, 64> > > dataForOtherThreads; - + + # ifdef USE_OMP # pragma omp parallel + # endif { //- find min and max entry in the graph //- they are used for assigning ranges of values local for each process label localMinRow(minRow), localMaxRow(0); + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(addr, rowI) { const RowType& row = addr[rowI]; - + forAll(row, i) { localMaxRow = Foam::max(localMaxRow, row[i]); localMinRow = Foam::min(localMinRow, row[i]); } } - + ++localMaxRow; - + + # ifdef USE_OMP # pragma omp critical + # endif { minRow = Foam::min(minRow, localMinRow); maxRow = Foam::max(maxRow, localMaxRow); } - + + # ifdef USE_OMP # pragma omp barrier - + //- allocate the rows of the transposed graph # pragma omp master + # endif { + # ifdef USE_OMP dataForOtherThreads.setSize(omp_get_num_threads()); + # else + dataForOtherThreads.setSize(1); + # endif nAppearances.setSize(maxRow); reverseAddr.setSize(maxRow); } - + + # ifdef USE_OMP const label nProcs = omp_get_num_threads(); const label procNo = omp_get_thread_num(); - + # else + const label nProcs = 1; + const label procNo = 0; + # endif + + # ifdef USE_OMP # pragma omp barrier - + //- initialise appearances # pragma omp for + # endif for(label i=0;i<maxRow;++i) nAppearances[i] = 0; const label range = (maxRow - minRow) / nProcs + 1; const label localMin = minRow + procNo * range; const label localMax = Foam::min(localMin + range, maxRow); - + //- find the number of appearances of each element in the original graph + # ifdef USE_OMP # pragma omp for + # endif forAll(addr, rowI) { const RowType& row = addr[rowI]; - + forAll(row, j) { const label entryI = row[j]; - + const label procI = (entryI - minRow) / range; if( procI != procNo ) { @@ -422,28 +442,32 @@ void reverseAddressingSMP } } } - + + # ifdef USE_OMP # pragma omp barrier + # endif //- count the appearances which are not local to the processor for(label i=0;i<nProcs;++i) { const std::map<label, DynList<labelPair, 64> >& data = dataForOtherThreads[i]; - + std::map<label, DynList<labelPair, 64> >::const_iterator it = data.find(procNo); if( it != data.end() ) { const DynList<labelPair, 64>& entries = it->second; - + forAll(entries, j) ++nAppearances[entries[j].first()]; } } - + + # ifdef USE_OMP # pragma omp barrier + # endif //- allocate reverse matrix for(label i=localMin;i<localMax;++i) @@ -451,7 +475,7 @@ void reverseAddressingSMP reverseAddr[i].setSize(nAppearances[i]); nAppearances[i] = 0; } - + //- start filling reverse addressing graph //- update data from processors with smaller labels for(label i=0;i<procNo;++i) @@ -464,7 +488,7 @@ void reverseAddressingSMP if( it != data.end() ) { const DynList<labelPair, 64>& entries = it->second; - + forAll(entries, j) { const label entryI = entries[j].first(); @@ -475,11 +499,13 @@ void reverseAddressingSMP } //- update data local to the processor + # ifdef USE_OMP # pragma omp for + # endif forAll(addr, rowI) { const RowType& row = addr[rowI]; - + forAll(row, j) { const label entryI = row[j]; @@ -490,7 +516,7 @@ void reverseAddressingSMP } } } - + //- update data from the processors with higher labels for(label i=procNo+1;i<nProcs;++i) { @@ -502,7 +528,7 @@ void reverseAddressingSMP if( it != data.end() ) { const DynList<labelPair, 64>& entries = it->second; - + forAll(entries, j) { const label entryI = entries[j].first(); diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsPar.H b/meshLibrary/utilities/helperFunctions/helperFunctionsPar.H index 282c1c10f0b686460b0e37e9d38136ad4cd36cfc..e2b89119c16c2234f2c3a5fc6573d9a346126b51 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsPar.H +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsPar.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class helperFunctionsPar diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.C b/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.C index acd0c9dd98791b0be8417a8c40d4283dc241314f..0fd778fb4097c303a35f46261eab10368f1b6a28 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.C +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -45,12 +44,12 @@ namespace help scalar textToScalar(const word& w) { - std::stringstream ss; - ss << w; - - double s; - ss >> s; - return s; + std::stringstream ss; + ss << w; + + double s; + ss >> s; + return s; } //- convert the text to label @@ -61,18 +60,18 @@ label textToLabel(const word& w) word scalarToText(const scalar s) { - std::ostringstream ss; - ss << s; - - return ss.str(); + std::ostringstream ss; + ss << s; + + return ss.str(); } word labelToText(const label l) { std::ostringstream ss; - ss << l; - - return ss.str(); + ss << l; + + return ss.str(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.H b/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.H index b2efc7d5ecb5bebdde0646b3c527f4b5daa1d788..40199f6f22304d5288cff40e5236edfca79608ca 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.H +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsStringConversion.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. InNamespace Foam::help diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulation.H b/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulation.H index 25964803b15f1e6cad1657c27b8d1807a1dbfb77..cfb59ddd813d41e3e9034c325bb9b64231e6423e 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulation.H +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulation.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class helperFunctions @@ -54,51 +53,78 @@ namespace Foam namespace help { + //- check if the faces are equal + template<class faceType1, class faceType2> + bool areFacesEqual(const faceType1& f1, const faceType2& f2); + + //- local position of element in a list + template<class T, class ListType> + label positionInList(const T& elmt, const ListType& l); + + //- reverse the face + template<class faceType> + faceType reverseFace(const faceType& f); //- returns a merged face - inline face mergeTwoFaces(const face& f1, const face& f2); - + template<class faceType1, class faceType2> + inline face mergeTwoFaces + ( + const faceType1& f1, + const faceType2& f2 + ); + //- remove edges until faces share only one edge inline edgeList modifyFacesToShareOneEdge(face& f1, face& f2); - + //- create a face from the removed part inline face createFaceFromRemovedPart(const face& fOrig, const face& fCut); - + //- remove edges from face inline face removeEdgesFromFace ( const face& fOrig, const DynList<edge>& removeEdges ); - + //- find open edges for a set of faces forming a cell - inline void findOpenEdges(const faceList& cellFaces, DynList<edge>& openEdges); - + inline void findOpenEdges + ( + const faceList& cellFaces, + DynList<edge>& openEdges + ); + //- check if two faces share an edge - inline bool shareAnEdge(const face& f1, const face& f2); - + template<class faceType1, class faceType2> + inline bool shareAnEdge(const faceType1& f1, const faceType2& f2); + //- return the edge shared by the faces - inline edge sharedEdge(const face& f1, const face& f2); - + template<class faceType1, class faceType2> + inline edge sharedEdge(const faceType1& f1, const faceType2& f2); + //- return the position of edge in the face, -1 otherwise - inline label positionOfEdgeInFace(const edge& e, const face& f); - + template<class faceType> + inline label positionOfEdgeInFace(const edge& e, const faceType& f); + //- check if two faces share a vertex - inline bool shareAVertex(const face& f1, const face& f2); - + template<class faceType1, class faceType2> + inline bool shareAVertex(const faceType1& f1, const faceType2& f2); + //- shared vertex of two faces - inline label sharedVertex(const face& f1, const face& f2); - + template<class faceType1, class faceType2> + inline label sharedVertex(const faceType1& f1, const faceType2& f2); + //- find a vertex label common to all faces in the list - inline label sharedVertex(const faceList& fcs); - + template<class faceListType> + inline label sharedVertex(const faceListType& fcs); + //- check if selected elements are in one singly-connected chain - inline bool areElementsInChain(const boolList& sel); - + template<class boolListType> + inline bool areElementsInChain(const boolListType& sel); + //- sort the edge chain such that the end of one edge is the beginning //- of the next one (valid for singly-connected chains, only) inline labelList sortEdgeChain(const DynList<edge>& bEdges); - + //- creates closed edge chains from the open chain inline void zipOpenChain(DynList<edge>& bEdges); diff --git a/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulationI.H b/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulationI.H index d523e60623ca3d1a0b61fa317817552f2d4870fe..93f39ad17807ce32465f6dbadf08247958d82160 100644 --- a/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulationI.H +++ b/meshLibrary/utilities/helperFunctions/helperFunctionsTopologyManipulationI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,105 +42,210 @@ namespace help // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// -inline face mergeTwoFaces(const face& f1, const face& f2) +template<class faceType1, class faceType2> +bool areFacesEqual(const faceType1& f1, const faceType2& f2) { - const edgeList e1 = f1.edges(); - const edgeList e2 = f2.edges(); + //- their size mut be equal + if( f1.size() != f2.size() ) + return false; - boolList ce1(e1.size(), false), ce2(e2.size(), false); + //- find the starting point the the second face + label start(-1); + const label s = f2.size(); + bool equalOrientation(false); - forAll(e1, eI) - forAll(e2, eJ) - if( e1[eI] == e2[eJ] ) + forAll(f2, pI) + { + if( f1[0] == f2[pI] ) { - ce1[eI] = true; - ce2[eJ] = true; - break; + start = pI; + + if( f1[1] == f2[(pI+1)%s] ) + { + //- faces have the same orientation + equalOrientation = true; + } + else if( f1[1] != f2[(s-1+pI)%s] ) + { + //- faces shall have opposite orientation, but do not match + return false; + } + } + } + + if( start < 0 ) + return false; + + if( equalOrientation ) + { + //- same orientation, check if all points match + for(label pI=1;pI<s;++pI) + { + if( f1[pI] != f2[(pI+start)%s] ) + return false; + } + } + else + { + //- faces with opposite orientation, check if all points match + for(label pI=1;pI<s;++pI) + { + if( f1[pI] != f2[(start+s-pI)%s] ) + return false; + } + } + + //- faces are equal + return true; +} + +template<class T, class ListType > +label positionInList(const T& elmt, const ListType& l) +{ + for(label i=0;i<l.size();++i) + if( l[i] == elmt ) + return i; + + return -1; +} + +template<class faceType> +faceType reverseFace(const faceType& f) +{ + faceType rf; + rf.setSize(f.size()); + + rf[0] = f[0]; + + const label size = f.size(); + for(label i=1;i<size;++i) + rf[f.size()-i] = f[i]; + + return rf; +} + +template<class faceType1, class faceType2> +inline face mergeTwoFaces(const faceType1& f1, const faceType2& f2) +{ + DynList<bool> ce1, ce2; + ce1.setSize(f1.size()); + ce1 = false; + ce2.setSize(f2.size()); + ce2 = false; + + forAll(f1, eI) + { + const edge e1(f1[eI], f1[f1.fcIndex(eI)]); + + forAll(f2, eJ) + { + const edge e2(f2[eJ], f2[f2.fcIndex(eJ)]); + + if( e1 == e2 ) + { + ce1[eI] = true; + ce2[eJ] = true; + break; + } } + } DynList<edge> fEdges; forAll(ce1, eI) - if( !ce1[eI] ) fEdges.append(e1[eI]); + { + if( !ce1[eI] ) + { + const edge e1(f1[eI], f1[f1.fcIndex(eI)]); + fEdges.append(e1); + } + } + forAll(ce2, eI) - if( !ce2[eI] ) fEdges.append(e2[eI]); - + { + if( !ce2[eI] ) + { + const edge e2(f2[eI], f2[f2.fcIndex(eI)]); + fEdges.append(e2); + } + } + return face(sortEdgeChain(fEdges)); } inline edgeList modifyFacesToShareOneEdge(face& f1, face& f2) { - const edgeList edg1 = f1.edges(); - const edgeList edg2 = f2.edges(); - - boolList she1(f1.size(), false); - boolList she2(f2.size(), false); - - edgeList sharedEdges(edg1); - label nSharedEdges(0); - - forAll(edg1, eI) - forAll(edg2, eJ) - if( edg1[eI] == edg2[eJ] ) - { - sharedEdges.newElmt(nSharedEdges++) = edg1[eI]; - - she1[eI] = true; - she2[eJ] = true; - break; - } - - face newF(f1); - label i(0); - forAll(f1, pI) - if( !(she1[pI] && she1[(pI-1+f1.size())%f1.size()]) ) - newF[i++] = f1[pI]; - - newF.setSize(i); - f1 = newF; - - newF = f2; - i = 0; - forAll(f2, pI) - if( !(she2[pI] && she2[(pI-1+f2.size())%f2.size()]) ) + const edgeList edg1 = f1.edges(); + const edgeList edg2 = f2.edges(); + + boolList she1(f1.size(), false); + boolList she2(f2.size(), false); + + edgeList sharedEdges(edg1); + label nSharedEdges(0); + + forAll(edg1, eI) + forAll(edg2, eJ) + if( edg1[eI] == edg2[eJ] ) + { + sharedEdges.newElmt(nSharedEdges++) = edg1[eI]; + + she1[eI] = true; + she2[eJ] = true; + break; + } + + face newF(f1); + label i(0); + forAll(f1, pI) + if( !(she1[pI] && she1[(pI-1+f1.size())%f1.size()]) ) + newF[i++] = f1[pI]; + + newF.setSize(i); + f1 = newF; + + newF = f2; + i = 0; + forAll(f2, pI) + if( !(she2[pI] && she2[(pI-1+f2.size())%f2.size()]) ) newF[i++] = f2[pI]; - - newF.setSize(i); - f2 = newF; - sharedEdges.setSize(nSharedEdges); - return sharedEdges; + newF.setSize(i); + f2 = newF; + + sharedEdges.setSize(nSharedEdges); + return sharedEdges; } inline face createFaceFromRemovedPart(const face& fOrig, const face& fCut) { - if( fCut.size() == 0 ) - return fOrig; - - const edgeList eOrig = fOrig.edges(); - const edgeList eCut = fCut.edges(); - - boolList usedEdge(eOrig.size(), false); - - forAll(eOrig, eI) - forAll(eCut, eJ) - if( eOrig[eI] == eCut[eJ] ) - { - usedEdge[eI] = true; - break; - } - - face f(fOrig); - direction i(0); - - forAll(fOrig, pI) - if( !(usedEdge[pI] && usedEdge[(pI-1+fOrig.size())%fOrig.size()]) ) - { - f[i++] = fOrig[pI]; - } - - f.setSize(i); - - return f; + if( fCut.size() == 0 ) + return fOrig; + + const edgeList eOrig = fOrig.edges(); + const edgeList eCut = fCut.edges(); + + boolList usedEdge(eOrig.size(), false); + + forAll(eOrig, eI) + forAll(eCut, eJ) + if( eOrig[eI] == eCut[eJ] ) + { + usedEdge[eI] = true; + break; + } + + face f(fOrig); + direction i(0); + + forAll(fOrig, pI) + if( !(usedEdge[pI] && usedEdge[(pI-1+fOrig.size())%fOrig.size()]) ) + { + f[i++] = fOrig[pI]; + } + + f.setSize(i); + + return f; } inline face removeEdgesFromFace @@ -150,110 +254,126 @@ inline face removeEdgesFromFace const DynList<edge>& removeEdges ) { - boolList foundEdge(fOrig.size(), false); - - forAll(removeEdges, reI) - forAll(fOrig, eI) - if( removeEdges[reI] == fOrig.faceEdge(eI) ) - { - foundEdge[eI] = true; - break; - } - - face newF(fOrig.size()); - label i(0); - - forAll(fOrig, pI) - if( !(foundEdge[pI] && foundEdge[fOrig.rcIndex(pI)]) ) - newF[i++] = fOrig[pI]; - - newF.setSize(i); - - return newF; + boolList foundEdge(fOrig.size(), false); + + forAll(removeEdges, reI) + forAll(fOrig, eI) + if( removeEdges[reI] == fOrig.faceEdge(eI) ) + { + foundEdge[eI] = true; + break; + } + + face newF(fOrig.size()); + label i(0); + + forAll(fOrig, pI) + if( !(foundEdge[pI] && foundEdge[fOrig.rcIndex(pI)]) ) + newF[i++] = fOrig[pI]; + + newF.setSize(i); + + return newF; } inline void findOpenEdges(const faceList& cellFaces, DynList<edge>& openEdges) { - DynList<edge> cellEdges(12); - DynList<label> nAppearances(12); - - forAll(cellFaces, fI) - { - const edgeList edges = cellFaces[fI].edges(); - - forAll(edges, eI) - { - const label pos = cellEdges.containsAtPosition(edges[eI]); - - if( pos == -1 ) - { - cellEdges.append(edges[eI]); - nAppearances.append(1); - } - else - { - nAppearances[pos]++; - } - } - } - - openEdges.setSize(12); - openEdges.clear(); - - forAll(nAppearances, eI) - if( nAppearances[eI] == 1 ) - { - openEdges.append(cellEdges[eI]); - } - else if( nAppearances[eI] > 2 ) - { - FatalErrorIn - ( - "void findOpenEdges(const faceList& cellFaces," - "DynList<edge>& openEdges)" - ) << "More than two faces in " << cellFaces - << " share edge " << cellEdges[eI] << abort(FatalError); - } + DynList<edge> cellEdges; + DynList<label> nAppearances; + + forAll(cellFaces, fI) + { + const edgeList edges = cellFaces[fI].edges(); + + forAll(edges, eI) + { + const label pos = cellEdges.containsAtPosition(edges[eI]); + + if( pos == -1 ) + { + cellEdges.append(edges[eI]); + nAppearances.append(1); + } + else + { + nAppearances[pos]++; + } + } + } + + openEdges.setSize(12); + openEdges.clear(); + + forAll(nAppearances, eI) + if( nAppearances[eI] == 1 ) + { + openEdges.append(cellEdges[eI]); + } + else if( nAppearances[eI] > 2 ) + { + FatalErrorIn + ( + "void findOpenEdges(const faceList& cellFaces," + "DynList<edge>& openEdges)" + ) << "More than two faces in " << cellFaces + << " share edge " << cellEdges[eI] << abort(FatalError); + } } -inline bool shareAnEdge(const face& f1, const face& f2) +template<class faceType1, class faceType2> +inline bool shareAnEdge(const faceType1& f1, const faceType2& f2) { - const edgeList edges1 = f1.edges(); - const edgeList edges2 = f2.edges(); + forAll(f1, eI) + { + const edge e1(f1[eI], f1[f1.fcIndex(eI)]); + + forAll(f2, eJ) + { + const edge e2(f2[eJ], f2[f2.fcIndex(eJ)]); - forAll(edges1, eI) - forAll(edges2, eJ) - if( edges1[eI] == edges2[eJ] ) - return true; + if( e1 == e2 ) + return true; + } + } return false; } -inline edge sharedEdge(const face& f1, const face& f2) +template<class faceType1, class faceType2> +inline edge sharedEdge(const faceType1& f1, const faceType2& f2) { - const edgeList edges1 = f1.edges(); - const edgeList edges2 = f2.edges(); + forAll(f1, eI) + { + const edge e1(f1[eI], f1[f1.fcIndex(eI)]); + + forAll(f2, eJ) + { + const edge e2(f2[eJ], f2[f2.fcIndex(eJ)]); - forAll(edges1, eI) - forAll(edges2, eJ) - if( edges1[eI] == edges2[eJ] ) - return edges1[eI]; + if( e1 == e2 ) + return e1; + } + } return edge(-1, -1); } -inline label positionOfEdgeInFace(const edge& e, const face& f) +template<class faceType> +inline label positionOfEdgeInFace(const edge& e, const faceType& f) { - const edgeList edges = f.edges(); - - forAll(edges, eI) - if( edges[eI] == e ) - return eI; - - return -1; + forAll(f, eI) + { + const edge fe(f[eI], f[f.fcIndex(eI)]); + + if( fe == e ) + return eI; + } + + return -1; } -inline label sharedVertex(const face& f1, const face& f2) +template<class faceType1, class faceType2> +inline label sharedVertex(const faceType1& f1, const faceType2& f2) { forAll(f1, pI) forAll(f2, pJ) @@ -263,29 +383,29 @@ inline label sharedVertex(const face& f1, const face& f2) return -1; } -inline bool shareAVertex(const face& f1, const face& f2) +template<class faceType1, class faceType2> +inline bool shareAVertex(const faceType1& f1, const faceType2& f2) { forAll(f1, pI) forAll(f2, pJ) - if( f1[pI] == f2[pJ] ) - return true; + if( f1[pI] == f2[pJ] ) + return true; return false; } -inline label sharedVertex(const faceList& fcs) +template<class faceListType> +inline label sharedVertex(const faceListType& fcs) { - const face& f = fcs[0]; - - forAll(f, pI) + forAll(fcs[0], pI) { bool allFound(true); - for(label i=1;i<fcs.size();i++) + for(label i=1;i<fcs.size();++i) { bool found(false); forAll(fcs[i], pJ) - if( f[pI] == fcs[i][pJ] ) + if( fcs[0][pI] == fcs[i][pJ] ) found = true; if( !found ) @@ -296,151 +416,152 @@ inline label sharedVertex(const faceList& fcs) } if( allFound ) - return f[pI]; + return fcs[0][pI]; } return -1; } - -inline bool areElementsInChain(const boolList& sel) + +template<class boolListType> +inline bool areElementsInChain(const boolListType& sel) { - boolList selInChain(sel.size(), false); - - forAll(sel, eI) + DynList<bool> selInChain(sel.size(), false); + + forAll(sel, eI) { - if( sel[eI] ) - { - selInChain[eI] = true; - bool found; - do - { - found = false; - forAll(selInChain, eJ) - if( - !selInChain[eJ] && sel[eJ] && - ( - selInChain[sel.fcIndex(eJ)] || - selInChain[sel.rcIndex(eJ)] - ) - ) - { - found = true; - selInChain[eJ] = true; - } - } while( found ); - - break; - } + if( sel[eI] ) + { + selInChain[eI] = true; + bool found; + do + { + found = false; + forAll(selInChain, eJ) + if( + !selInChain[eJ] && sel[eJ] && + ( + selInChain[sel.fcIndex(eJ)] || + selInChain[sel.rcIndex(eJ)] + ) + ) + { + found = true; + selInChain[eJ] = true; + } + } while( found ); + + break; + } } - - forAll(sel, eI) + + forAll(sel, eI) { - if( sel[eI] && !selInChain[eI] ) - return false; + if( sel[eI] && !selInChain[eI] ) + return false; } - - return true; + + return true; } inline void zipOpenChain(DynList<edge>& bEdges) { - //- close the chain if open - DynList<label> chainVertices(5); - List<label> nAppearances(5); - forAll(bEdges, eI) - { - const edge& e = bEdges[eI]; - forAll(e, pI) - { - const label pos = chainVertices.containsAtPosition(e[pI]); - - if( pos == -1 ) - { - nAppearances[chainVertices.size()] = 1; - chainVertices.append(e[pI]); - } - else - { - ++nAppearances[pos]; - } - } - } - - bool closed(true); - DynList<label> openVertices(2); - forAll(chainVertices, pI) - if( nAppearances[pI] == 1 ) - { - closed = false; - openVertices.append(chainVertices[pI]); - } - - if( !closed && (openVertices.size() == 2) ) - { - forAll(bEdges, eI) - if( bEdges[eI].end() == openVertices[0] ) - { - bEdges.append(edge(openVertices[0], openVertices[1])); - break; - } - else if( bEdges[eI].end() == openVertices[1] ) - { - bEdges.append(edge(openVertices[1], openVertices[0])); - break; - } - } - else if( !closed ) - { - FatalErrorIn - ( - "void dualMeshExtractor::decomposeCreatedPoly::" + //- close the chain if open + DynList<label> chainVertices; + List<label> nAppearances; + forAll(bEdges, eI) + { + const edge& e = bEdges[eI]; + forAll(e, pI) + { + const label pos = chainVertices.containsAtPosition(e[pI]); + + if( pos == -1 ) + { + nAppearances[chainVertices.size()] = 1; + chainVertices.append(e[pI]); + } + else + { + ++nAppearances[pos]; + } + } + } + + bool closed(true); + DynList<label> openVertices(2); + forAll(chainVertices, pI) + if( nAppearances[pI] == 1 ) + { + closed = false; + openVertices.append(chainVertices[pI]); + } + + if( !closed && (openVertices.size() == 2) ) + { + forAll(bEdges, eI) + if( bEdges[eI].end() == openVertices[0] ) + { + bEdges.append(edge(openVertices[0], openVertices[1])); + break; + } + else if( bEdges[eI].end() == openVertices[1] ) + { + bEdges.append(edge(openVertices[1], openVertices[0])); + break; + } + } + else if( !closed ) + { + FatalErrorIn + ( + "void dualMeshExtractor::decomposeCreatedPoly::" "createMissingFaces(List<faceList>& cFaces)" - ) << "Chain has " << openVertices << " open vertices" - << abort(FatalError); - } + ) << "Chain has " << openVertices << " open vertices" + << abort(FatalError); + } } inline labelList sortEdgeChain(const DynList<edge>& bEdges) { - boolList sorted(bEdges.size(), false); - - DynList<edge> sortedEdges; - sortedEdges.append(bEdges[0]); - sorted[0] = true; - direction i(0); - - bool finished; - do - { - finished = true; - - forAll(bEdges, eI) - if( !sorted[eI] ) - { - if( sortedEdges[i].end() == bEdges[eI].start() ) - { - sorted[eI] = true; - finished = false; - sortedEdges.append(bEdges[eI]); - ++i; - } - else if( sortedEdges[i].end() == bEdges[eI].end() ) - { - FatalErrorIn - ( - "labelList sortEdgeChain(" - "const DynList<edge>& bEdges)" - ) << "Chain is not oriented correctly!" - << abort(FatalError); - } - } - } while( !finished ); - - labelList sortPoints(bEdges.size()); - forAll(sortedEdges, eI) - sortPoints[eI] = sortedEdges[eI].start(); - - return sortPoints; + boolList sorted(bEdges.size(), false); + + DynList<edge> sortedEdges; + sortedEdges.append(bEdges[0]); + sorted[0] = true; + direction i(0); + + bool finished; + do + { + finished = true; + + forAll(bEdges, eI) + if( !sorted[eI] ) + { + if( sortedEdges[i].end() == bEdges[eI].start() ) + { + sorted[eI] = true; + finished = false; + sortedEdges.append(bEdges[eI]); + ++i; + } + else if( sortedEdges[i].end() == bEdges[eI].end() ) + { + FatalErrorIn + ( + "labelList sortEdgeChain(" + "const DynList<edge>& bEdges)" + ) << "Chain is not oriented correctly!" + << abort(FatalError); + } + } + } while( !finished ); + + labelList sortPoints(bEdges.size()); + forAll(sortedEdges, eI) + sortPoints[eI] = sortedEdges[eI].start(); + + return sortPoints; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.C b/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.C index 2f7510bb62e5f6838d8497a021301a0c9fb4a42c..84f51f6b2bfc7932835a0f7f1649ec0256ab09a3 100644 --- a/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.C +++ b/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,7 +34,9 @@ Description #include "labelPair.H" #include "HashSet.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -59,7 +60,9 @@ bool allHexMesh(const polyMeshGen& mesh) bool allHex(true); + # ifdef USE_OMP # pragma omp parallel for schedule(static, 1) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; @@ -80,7 +83,7 @@ label findColumnCells ( const polyMeshGen& mesh, const label faceI, - labelListPMG& columnCells + labelLongList& columnCells ) { columnCells.setSize(0); @@ -92,7 +95,7 @@ label findColumnCells boolList addedCell(mesh.cells().size(), false); - labelListPMG front; + labelLongList front; front.append(faceI); while( front.size() ) @@ -129,7 +132,7 @@ label findColumnCells const word& columnCellSet ) { - labelListPMG columnCells; + labelLongList columnCells; findColumnCells(mesh, faceI, columnCells); const label cID = mesh.addCellSubset(columnCellSet); @@ -147,7 +150,9 @@ bool selfIntersectingColumn(const polyMeshGen& mesh, const boolList& columnCells const cellListPMG& cells = mesh.cells(); bool selfIntersecting(false); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 20) + # endif forAll(cells, cellI) { if( !columnCells[cellI] || selfIntersecting ) @@ -185,11 +190,13 @@ bool selfIntersectingColumn(const polyMeshGen& mesh, const boolList& columnCells return selfIntersecting; } -bool selfIntersectingColumn(const polyMeshGen& mesh, const labelListPMG& columnCells) +bool selfIntersectingColumn(const polyMeshGen& mesh, const labelLongList& columnCells) { boolList cellsInColumn(mesh.cells().size(), false); + # ifdef USE_OMP # pragma omp parallel for schedule(static, 1) + # endif forAll(columnCells, i) cellsInColumn[columnCells[i]] = true; @@ -198,7 +205,7 @@ bool selfIntersectingColumn(const polyMeshGen& mesh, const labelListPMG& columnC bool selfIntersectingColumn(const polyMeshGen& mesh, const word& columnCellSet) { - labelListPMG columnCells; + labelLongList columnCells; const label setID = mesh.cellSubsetIndex(columnCellSet); mesh.cellsInSubset(setID, columnCells); @@ -226,7 +233,7 @@ label findSheetCells ( const polyMeshGen& mesh, const edge& sheetEdge, - labelListPMG& cellsInSheet + labelLongList& cellsInSheet ) { cellsInSheet.setSize(0); @@ -241,7 +248,7 @@ label findSheetCells const VRWGraph& edgeCells = mesh.addressingData().edgeCells(); const VRWGraph& cellEdges = mesh.addressingData().cellEdges(); - labelListPMG front; + labelLongList front; forAllRow(pointEdges, sheetEdge.start(), peI) { @@ -318,7 +325,7 @@ label findSheetCells const word& sheetCellSet ) { - labelListPMG sheetCells; + labelLongList sheetCells; findSheetCells(mesh, sheetEdge, sheetCells); const label cID = mesh.addCellSubset(sheetCellSet); @@ -339,8 +346,10 @@ bool hasSheetDigons(const polyMeshGen& mesh, const boolList& sheetCells) bool hasDigons(false); + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); # pragma omp parallel for num_threads(nThreads) schedule(static) + # endif forAll(sheetCells, cellI) { if( !sheetCells[cellI] ) @@ -378,20 +387,26 @@ bool hasSheetDigons(const polyMeshGen& mesh, const boolList& sheetCells) bool hasSheetDigons ( const polyMeshGen& mesh, - const labelListPMG& sheetCells + const labelLongList& sheetCells ) { boolList sCells(mesh.cells().size()); + # ifdef USE_OMP # pragma omp parallel if( mesh.cells().size() > 1000 ) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(sCells, i) sCells[i] = false; + # ifdef USE_OMP # pragma omp barrier # pragma omp for schedule(static, 1) + # endif forAll(sheetCells, i) sCells[sheetCells[i]] = true; } @@ -403,7 +418,7 @@ bool hasSheetDigons(const polyMeshGen& mesh, const word& sheetCellSet) { const label sheetID = mesh.cellSubsetIndex(sheetCellSet); - labelListPMG sheetCells; + labelLongList sheetCells; mesh.cellsInSubset(sheetID, sheetCells); return hasSheetDigons(mesh, sheetCells); @@ -429,7 +444,7 @@ bool collapseColumn const label positionInFace ) { - labelListPMG columnCells; + labelLongList columnCells; findColumnCells(mesh, faceI, columnCells); const label pointI = mesh.faces()[faceI][positionInFace]; @@ -442,7 +457,7 @@ bool collapseColumn bool collapseColumn ( polyMeshGen& mesh, - const labelListPMG& columnCells, + const labelLongList& columnCells, const label pointI ) { @@ -552,7 +567,7 @@ bool collapseColumn //- find all points connected to the selected point boolList removePoint(mesh.points().size(), false); - labelListPMG front; + labelLongList front; front.append(pointI); while( front.size() ) { @@ -597,7 +612,7 @@ bool collapseColumn FatalErrorIn ( "bool collapseColumn(polyMeshGen&," - "const labelListPMG&, const label" + "const labelLongList&, const label" ) << "Cannot find position in face " << faceI << exit(FatalError); const label pPos = f[pos]; @@ -781,7 +796,7 @@ bool collapseColumn const label pointI ) { - labelListPMG columnCells; + labelLongList columnCells; const label cID = mesh.cellSubsetIndex(columnCellSet); mesh.cellsInSubset(cID, columnCells); @@ -792,7 +807,7 @@ bool collapseColumn //- the sheet into a set of faces bool extractSheet(polyMeshGen& mesh, const edge& sheetEdge) { - labelListPMG sheetCells; + labelLongList sheetCells; findSheetCells(mesh, sheetEdge, sheetCells); return extractSheet(mesh, sheetCells); @@ -821,7 +836,7 @@ bool extractSheet(polyMeshGen& mesh, const boolList& sheetCells) VRWGraph pFaces; pFaces.reverseAddressing(mesh.points().size(), faces); - labelListPMG newPointLabel(mesh.points().size(), -1); + labelLongList newPointLabel(mesh.points().size(), -1); //- find faces which shall be removed from the mesh //- as a consequence of sheet extraction @@ -1130,11 +1145,13 @@ bool extractSheet(polyMeshGen& mesh, const boolList& sheetCells) return true; } -bool extractSheet(polyMeshGen& mesh, const labelListPMG& cellsInSheet) +bool extractSheet(polyMeshGen& mesh, const labelLongList& cellsInSheet) { boolList sheetCells(mesh.cells().size(), false); + # ifdef USE_OMP # pragma omp parallel for + # endif forAll(cellsInSheet, i) sheetCells[cellsInSheet[i]] = true; @@ -1143,7 +1160,7 @@ bool extractSheet(polyMeshGen& mesh, const labelListPMG& cellsInSheet) bool extractSheet(polyMeshGen& mesh, const word& sheetCellSet) { - labelListPMG sheetCells; + labelLongList sheetCells; const label cID = mesh.cellSubsetIndex(sheetCellSet); mesh.cellsInSubset(cID, sheetCells); diff --git a/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.H b/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.H index 14bbc97ea7ee1d0d2e067ab8c2116d824aa9ceb6..58f9d369ea75232518c7588dfde26631e34e6c03 100644 --- a/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.H +++ b/meshLibrary/utilities/hexahedra/hexHelpers/hexHelpers.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class @@ -58,7 +57,7 @@ namespace hexHelpers ( const polyMeshGen& mesh, const label faceI, - labelListPMG& columnCells + labelLongList& columnCells ); label findColumnCells ( @@ -77,7 +76,7 @@ namespace hexHelpers bool selfIntersectingColumn ( const polyMeshGen& mesh, - const labelListPMG& columnCells + const labelLongList& columnCells ); bool selfIntersectingColumn ( @@ -93,7 +92,7 @@ namespace hexHelpers ( const polyMeshGen& mesh, const edge& sheetEdge, - labelListPMG& cellsInSheet + labelLongList& cellsInSheet ); label findSheetCells ( @@ -107,7 +106,7 @@ namespace hexHelpers bool hasSheetDigons ( const polyMeshGen& mesh, - const labelListPMG& sheetCells + const labelLongList& sheetCells ); bool hasSheetDigons(const polyMeshGen& mesh, const word& sheetCellSet); @@ -130,7 +129,7 @@ namespace hexHelpers bool collapseColumn ( polyMeshGen& mesh, - const labelListPMG& columnCells, + const labelLongList& columnCells, const label pointI ); bool collapseColumn @@ -146,7 +145,7 @@ namespace hexHelpers //- extract the sheet of cells bool extractSheet(polyMeshGen& mesh, const boolList& sheetCells); - bool extractSheet(polyMeshGen& mesh, const labelListPMG& cellsInSheet); + bool extractSheet(polyMeshGen& mesh, const labelLongList& cellsInSheet); bool extractSheet(polyMeshGen& mesh, const word& sheetCellSet); } // End namespace hexHelpers diff --git a/meshLibrary/utilities/intersectionTools/findCellsIntersectingSurface/findCellsIntersectingSurface.C b/meshLibrary/utilities/intersectionTools/findCellsIntersectingSurface/findCellsIntersectingSurface.C new file mode 100644 index 0000000000000000000000000000000000000000..62149e18716cc2a51637c5f9715fc6e7e152b985 --- /dev/null +++ b/meshLibrary/utilities/intersectionTools/findCellsIntersectingSurface/findCellsIntersectingSurface.C @@ -0,0 +1,347 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "findCellsIntersectingSurface.H" +#include "polyMeshGen.H" +#include "polyMeshGenAddressing.H" +#include "triSurf.H" +#include "boundBox.H" +#include "helperFunctions.H" +#include "meshOctree.H" +#include "meshOctreeCreator.H" +#include "HashSet.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void findCellsIntersectingSurface::generateOctree(const triSurf& surf) +{ + octreePtr_ = new meshOctree(surf); + + meshOctreeCreator(*octreePtr_).createOctreeWithRefinedBoundary(15, 15); +} + +void findCellsIntersectingSurface::findIntersectedCells() +{ + const pointFieldPMG& points = mesh_.points(); + const faceListPMG& faces = mesh_.faces(); + const cellListPMG& cells = mesh_.cells(); + const labelList& owner = mesh_.owner(); + + const vectorField& faceCentres = mesh_.addressingData().faceCentres(); + const vectorField& cellCentres = mesh_.addressingData().cellCentres(); + + meshOctreeModifier octreeModifier(*octreePtr_); + const LongList<meshOctreeCube*>& leaves = octreeModifier.leavesAccess(); + + intersectedCells_.setSize(cells.size()); + facetsIntersectingCell_.setSize(cells.size()); + + const triSurf& surf = octreePtr_->surface(); + const VRWGraph& pointFacets = surf.pointFacets(); + const pointField& sp = surf.points(); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(cells, cellI) + { + bool intersected(false); + + const cell& c = cells[cellI]; + + //- find the bounding box of the cell + boundBox bb(cellCentres[cellI], cellCentres[cellI]); + + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + forAll(f, pI) + { + bb.min() = Foam::min(bb.min(), points[f[pI]]); + bb.max() = Foam::max(bb.max(), points[f[pI]]); + } + } + + const vector spanCorr = 0.01 * bb.span(); + bb.max() += spanCorr; + bb.min() -= spanCorr; + + //- find surface triangles within the bounding box + DynList<label> leavesInBox; + octreePtr_->findLeavesContainedInBox(bb, leavesInBox); + labelHashSet triangles; + forAll(leavesInBox, boxI) + { + const meshOctreeCube& oc = *leaves[leavesInBox[boxI]]; + + if( oc.hasContainedElements() ) + { + const meshOctreeSlot& slot = *oc.slotPtr(); + const label ceI = oc.containedElements(); + + forAllRow(slot.containedTriangles_, ceI, tI) + triangles.insert(slot.containedTriangles_(ceI, tI)); + } + } + + //- remove triangles which do not intersect the bounding box + labelHashSet reasonableCandidates; + + forAllConstIter(labelHashSet, triangles, tIter) + { + const labelledTri& tri = surf[tIter.key()]; + + boundBox obb(sp[tri[0]], sp[tri[0]]); + for(label i=1;i<3;++i) + { + const point& v = sp[tri[i]]; + obb.min() = Foam::min(obb.min(), v); + obb.max() = Foam::max(obb.max(), v); + } + + const vector spanTriCorr = SMALL * obb.span(); + obb.min() -= spanTriCorr; + obb.max() += spanTriCorr; + + if( obb.overlaps(bb) ) + reasonableCandidates.insert(tIter.key()); + } + + triangles.transfer(reasonableCandidates); + + //- check if any of the surface vertices is contained within the cell + labelHashSet nodes, facetsInCell; + forAllConstIter(labelHashSet, triangles, tIter) + { + const labelledTri& tri = surf[tIter.key()]; + + forAll(tri, i) + nodes.insert(tri[i]); + } + + //- check which surface nodes are within the cell + forAllConstIter(labelHashSet, nodes, nIter) + { + const point& p = sp[nIter.key()]; + + if( !bb.contains(p) ) + continue; + + bool foundIntersection(false); + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + if( owner[c[fI]] == cellI ) + { + forAll(f, pI) + { + tetrahedron<point, point> tet + ( + points[f[pI]], + points[f.prevLabel(pI)], + faceCentres[c[fI]], + cellCentres[cellI] + ); + + if( help::pointInTetrahedron(p, tet) ) + { + intersected = true; + forAllRow(pointFacets, nIter.key(), ptI) + { + facetsInCell.insert + ( + pointFacets(nIter.key(), ptI) + ); + } + + foundIntersection = true; + break; + } + } + + if( foundIntersection ) + break; + } + else + { + forAll(f, pI) + { + tetrahedron<point, point> tet + ( + points[f[pI]], + points[f.nextLabel(pI)], + faceCentres[c[fI]], + cellCentres[cellI] + ); + + if( help::pointInTetrahedron(p, tet) ) + { + intersected = true; + forAllRow(pointFacets, nIter.key(), ptI) + { + facetsInCell.insert + ( + pointFacets(nIter.key(), ptI) + ); + } + + foundIntersection = true; + break; + } + } + + if( foundIntersection ) + break; + } + } + } + + //- check if any triangle in the surface mesh + //- intersects any of the cell's faces + forAllConstIter(labelHashSet, triangles, tIter) + { + if( facetsInCell.found(tIter.key()) ) + continue; + + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + const bool intersect = + help::doFaceAndTriangleIntersect + ( + surf, + tIter.key(), + f, + points + ); + + if( intersect ) + { + intersected = true; + facetsInCell.insert(tIter.key()); + break; + } + } + } + + //- store the results for this cell + intersectedCells_[cellI] = intersected; + if( intersected ) + { + # ifdef USE_OMP + # pragma omp critical + # endif + { + facetsIntersectingCell_.setRow(cellI, facetsInCell.toc()); + } + } + } +} + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +findCellsIntersectingSurface::findCellsIntersectingSurface +( + polyMeshGen& mesh, + const meshOctree& octree +) +: + mesh_(mesh), + octreePtr_(const_cast<meshOctree*>(&octree)), + octreeGenerated_(false), + intersectedCells_(), + facetsIntersectingCell_() +{ + findIntersectedCells(); +} + +findCellsIntersectingSurface::findCellsIntersectingSurface +( + polyMeshGen& mesh, + const triSurf& surface +) +: + mesh_(mesh), + octreePtr_(NULL), + octreeGenerated_(true), + intersectedCells_(), + facetsIntersectingCell_() +{ + generateOctree(surface); + + findIntersectedCells(); +} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +findCellsIntersectingSurface::~findCellsIntersectingSurface() +{ + if( octreeGenerated_ ) + deleteDemandDrivenData(octreePtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +const boolList& findCellsIntersectingSurface::intersectedCells() const +{ + return intersectedCells_; +} + +const VRWGraph& findCellsIntersectingSurface::facetsIntersectingCells() const +{ + return facetsIntersectingCell_; +} + +void findCellsIntersectingSurface::addIntersectedCellsToSubset +( + const word subsetName +) +{ + const label setId = mesh_.addCellSubset(subsetName); + + forAll(intersectedCells_, cellI) + if( intersectedCells_[cellI] ) + mesh_.addCellToSubset(setId, cellI); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/intersectionTools/findCellsIntersectingSurface/findCellsIntersectingSurface.H b/meshLibrary/utilities/intersectionTools/findCellsIntersectingSurface/findCellsIntersectingSurface.H new file mode 100644 index 0000000000000000000000000000000000000000..9b6f65f5d0549bc95bdb3a87f7e7fd05accad6eb --- /dev/null +++ b/meshLibrary/utilities/intersectionTools/findCellsIntersectingSurface/findCellsIntersectingSurface.H @@ -0,0 +1,123 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + findCellsIntersectingSurface + +Description + Finds which cells in the mesh intersect the surface mesh + +SourceFiles + findCellsIntersectingSurface.C + +\*---------------------------------------------------------------------------*/ + +#ifndef findCellsIntersectingSurface_H +#define findCellsIntersectingSurface_H + +#include "boolList.H" +#include "VRWGraph.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +class polyMeshGen; +class triSurf; +class meshOctree; + +/*---------------------------------------------------------------------------*\ + Class findCellsIntersectingSurface Declaration +\*---------------------------------------------------------------------------*/ + +class findCellsIntersectingSurface +{ + // Private data + //- Reference to the mesh + polyMeshGen& mesh_; + + //- Pointer to the octree + meshOctree* octreePtr_; + + //- check whether the octree was generated or not + const bool octreeGenerated_; + + //- stores information about intersected cells + boolList intersectedCells_; + + //- stores information which surface facets intersect each cell + VRWGraph facetsIntersectingCell_; + + // Private member functions + //- generate the octree + void generateOctree(const triSurf&); + + //- check for the intersected cells + void findIntersectedCells(); + +public: + + // Constructors + + //- Construct from mesh and octree + findCellsIntersectingSurface + ( + polyMeshGen& mesh, + const meshOctree& octree + ); + + //- Construct from mesh and surface + findCellsIntersectingSurface + ( + polyMeshGen& mesh, + const triSurf& surface + ); + + // Destructor + ~findCellsIntersectingSurface(); + + // Public member functions + //- return the list of intersected cells; + const boolList& intersectedCells() const; + + //- return the graph of facets intersecting each cell + const VRWGraph& facetsIntersectingCells() const; + + //- create a cell subset containing intersected cells + void addIntersectedCellsToSubset + ( + const word subsetName = "intersectedCells" + ); +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.C b/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.C index 34f195b5470a736006cf12b67397311e2d95930a..f16e8691015e03331f8e7dcf90efc1ec2f834f07 100644 --- a/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.C +++ b/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -34,7 +33,10 @@ Description #include "helperFunctions.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGSmooth @@ -47,109 +49,109 @@ namespace Foam partTetMesh::partTetMesh(polyMeshGen& mesh) : - origMesh_(mesh), - points_(), - tets_(), - nodeLabelInOrigMesh_(), - smoothVertex_(), - pointTets_(), + origMesh_(mesh), + points_(), + tets_(), + nodeLabelInOrigMesh_(), + smoothVertex_(), + pointTets_(), internalPointsOrderPtr_(NULL), boundaryPointsOrderPtr_(NULL), pAtProcsPtr_(NULL), globalToLocalPointAddressingPtr_(NULL), neiProcsPtr_(NULL), - pAtParallelBoundariesPtr_(NULL), + pAtParallelBoundariesPtr_(NULL), pAtBufferLayersPtr_(NULL) { - List<direction> useCell(mesh.cells().size(), direction(1)); - - createPointsAndTets(useCell); + List<direction> useCell(mesh.cells().size(), direction(1)); + + createPointsAndTets(useCell); } partTetMesh::partTetMesh ( - polyMeshGen& mesh, - labelHashSet& badFaces, - const direction additionalLayers + polyMeshGen& mesh, + labelHashSet& badFaces, + const direction additionalLayers ) : - origMesh_(mesh), - points_(), - tets_(), - nodeLabelInOrigMesh_(), - smoothVertex_(), - pointTets_(), + origMesh_(mesh), + points_(), + tets_(), + nodeLabelInOrigMesh_(), + smoothVertex_(), + pointTets_(), internalPointsOrderPtr_(NULL), boundaryPointsOrderPtr_(NULL), globalPointLabelPtr_(NULL), pAtProcsPtr_(NULL), globalToLocalPointAddressingPtr_(NULL), neiProcsPtr_(NULL), - pAtParallelBoundariesPtr_(NULL), + pAtParallelBoundariesPtr_(NULL), pAtBufferLayersPtr_(NULL) { - const faceListPMG& faces = mesh.faces(); - const cellListPMG& cells = mesh.cells(); - const VRWGraph& pointCells = mesh.addressingData().pointCells(); - - List<direction> useCell(cells.size(), direction(0)); - - //- select cells containing at least one vertex of the bad faces - forAll(faces, faceI) - if( badFaces.found(faceI) ) - { - const face& f = faces[faceI]; - - forAll(f, pI) - { - forAllRow(pointCells, f[pI], pcI) - useCell[pointCells(f[pI], pcI)] = 1; - } - } - - //- add additional layer of cells - for(label layerI=1;layerI<(additionalLayers+1);++layerI) - { - forAll(useCell, cI) - if( useCell[cI] == layerI ) - { - const cell& c = cells[cI]; - - forAll(c, fI) - { - const face& f = faces[c[fI]]; - - forAll(f, pI) - { - forAllRow(pointCells, f[pI], pcI) - { - const label cLabel = pointCells(f[pI], pcI); - if( !useCell[cLabel] ) - useCell[cLabel] = layerI + 1; - } - } - } - } - + const faceListPMG& faces = mesh.faces(); + const cellListPMG& cells = mesh.cells(); + const VRWGraph& pointCells = mesh.addressingData().pointCells(); + + List<direction> useCell(cells.size(), direction(0)); + + //- select cells containing at least one vertex of the bad faces + forAll(faces, faceI) + if( badFaces.found(faceI) ) + { + const face& f = faces[faceI]; + + forAll(f, pI) + { + forAllRow(pointCells, f[pI], pcI) + useCell[pointCells(f[pI], pcI)] = 1; + } + } + + //- add additional layer of cells + for(direction layerI=1;layerI<(additionalLayers+1);++layerI) + { + forAll(useCell, cI) + if( useCell[cI] == layerI ) + { + const cell& c = cells[cI]; + + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + forAll(f, pI) + { + forAllRow(pointCells, f[pI], pcI) + { + const label cLabel = pointCells(f[pI], pcI); + if( !useCell[cLabel] ) + useCell[cLabel] = layerI + 1; + } + } + } + } + if( Pstream::parRun() ) { - const labelListPMG& globalPointLabel = + const labelLongList& globalPointLabel = mesh.addressingData().globalPointLabel(); const VRWGraph& pProcs = mesh.addressingData().pointAtProcs(); const Map<label>& globalToLocal = mesh.addressingData().globalToLocalPointAddressing(); - + std::map<label, LongList<label> > eData; forAllConstIter(Map<label>, globalToLocal, iter) { const label pointI = iter(); - + forAllRow(pProcs, pointI, procI) { const label neiProc = pProcs(pointI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + if( eData.find(neiProc) == eData.end() ) { eData.insert @@ -157,7 +159,7 @@ partTetMesh::partTetMesh std::make_pair(neiProc, LongList<label>()) ); } - + forAllRow(pointCells, pointI, pcI) if( useCell[pointCells(pointI, pcI)] == layerI ) { @@ -166,15 +168,15 @@ partTetMesh::partTetMesh } } } - + //- exchange data with other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(eData, receivedData); - + forAll(receivedData, i) { const label pointI = globalToLocal[receivedData[i]]; - + forAllRow(pointCells, pointI, pcI) { const label cLabel = pointCells(pointI, pcI); @@ -183,9 +185,9 @@ partTetMesh::partTetMesh } } } - } - - createPointsAndTets(useCell); + } + + createPointsAndTets(useCell); } partTetMesh::~partTetMesh() @@ -196,7 +198,7 @@ partTetMesh::~partTetMesh() deleteDemandDrivenData(pAtProcsPtr_); deleteDemandDrivenData(globalToLocalPointAddressingPtr_); deleteDemandDrivenData(neiProcsPtr_); - deleteDemandDrivenData(pAtParallelBoundariesPtr_); + deleteDemandDrivenData(pAtParallelBoundariesPtr_); deleteDemandDrivenData(pAtBufferLayersPtr_); } @@ -204,6 +206,7 @@ partTetMesh::~partTetMesh() const VRWGraph& partTetMesh::internalPointOrdering() const { + # ifdef USE_OMP if( omp_in_parallel() ) { FatalErrorIn @@ -212,15 +215,17 @@ const VRWGraph& partTetMesh::internalPointOrdering() const ) << "Calculating addressing inside a parallel region." << " This is not thread safe" << exit(FatalError); } - + # endif + if( !internalPointsOrderPtr_ ) createSMOOTHPointsOrdering(); - + return *internalPointsOrderPtr_; } const VRWGraph& partTetMesh::boundaryPointOrdering() const { + # ifdef USE_OMP if( omp_in_parallel() ) { FatalErrorIn @@ -229,23 +234,24 @@ const VRWGraph& partTetMesh::boundaryPointOrdering() const ) << "Calculating addressing inside a parallel region." << " This is not thread safe" << exit(FatalError); } - + # endif + if( !boundaryPointsOrderPtr_ ) createBOUNDARYPointsOrdering(); - + return *boundaryPointsOrderPtr_; } void partTetMesh::updateVertex(const label pointI, const point& newP) { points_[pointI] = newP; - + if( smoothVertex_[pointI] & (FACECENTRE+CELLCENTRE) ) { Warning << "Smoothing auxiliary vertex." << " This has no effect on the original mesh" << endl; return; } - + //- find face centres attached DynList<label, 64> helper; forAllRow(pointTets_, pointI, ptI) @@ -254,12 +260,12 @@ void partTetMesh::updateVertex(const label pointI, const point& newP) if( smoothVertex_[centreI] & FACECENTRE ) helper.appendIfNotIn(centreI); } - + //- update coordinates of FACECENTRE vertices forAll(helper, i) { const label centreI = helper[i]; - + point centre(vector::zero); scalar faceArea(0.0); forAllRow(pointTets_, centreI, ptI) @@ -270,14 +276,14 @@ void partTetMesh::updateVertex(const label pointI, const point& newP) c += points_[tet[i]]; c /= 3; const scalar area = Foam::mag(tet.Sd(points_)) + VSMALL; - + centre += c * area; faceArea += area; } - + points_[centreI] = centre / faceArea; } - + //- find cell centres attached helper.clear(); forAllRow(pointTets_, pointI, ptI) @@ -286,12 +292,12 @@ void partTetMesh::updateVertex(const label pointI, const point& newP) if( smoothVertex_[centreI] & CELLCENTRE ) helper.appendIfNotIn(centreI); } - + //- update coordinates of CELLCENTRE vertices forAll(helper, i) { const label centreI = helper[i]; - + point centre(vector::zero); scalar cellVol(0.0); forAllRow(pointTets_, centreI, ptI) @@ -299,11 +305,11 @@ void partTetMesh::updateVertex(const label pointI, const point& newP) const partTet& tet = tets_[pointTets_(centreI, ptI)]; const point c = tet.centroid(points_); const scalar vol = Foam::mag(tet.mag(points_)) + VSMALL; - + centre += c * vol; cellVol += vol; } - + points_[centreI] = centre / cellVol; } } @@ -311,18 +317,24 @@ void partTetMesh::updateVertex(const label pointI, const point& newP) void partTetMesh::updateVerticesSMP(const List<LongList<labelledPoint> >& np) { List<direction> updateType(points_.size(), direction(0)); - + + # ifdef USE_OMP # pragma omp parallel num_threads(np.size()) + # endif { + # ifdef USE_OMP const LongList<labelledPoint>& newPoints = np[omp_get_thread_num()]; - + # else + const LongList<labelledPoint>& newPoints = np[0]; + # endif + forAll(newPoints, i) { const labelledPoint& lp = newPoints[i]; const label pointI = lp.pointLabel(); - + points_[pointI] = lp.coordinates(); - + forAllRow(pointTets_, pointI, ptI) { const partTet& pt = tets_[pointTets_(pointI, ptI)]; @@ -333,13 +345,15 @@ void partTetMesh::updateVerticesSMP(const List<LongList<labelledPoint> >& np) updateType[pt[2]] |= FACECENTRE; } } - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp flush(updateType) - + //- update coordinates of CELLCENTRE and FACECENTRE vertices # pragma omp for schedule(dynamic, 20) + # endif forAll(updateType, pI) { if( updateType[pI] & CELLCENTRE ) @@ -351,11 +365,11 @@ void partTetMesh::updateVerticesSMP(const List<LongList<labelledPoint> >& np) const partTet& tet = tets_[pointTets_(pI, ptI)]; const point c = tet.centroid(points_); const scalar vol = Foam::mag(tet.mag(points_)) + VSMALL; - + centre += c * vol; cellVol += vol; } - + points_[pI] = centre / cellVol; } else if( updateType[pI] & FACECENTRE ) @@ -370,11 +384,11 @@ void partTetMesh::updateVerticesSMP(const List<LongList<labelledPoint> >& np) c += points_[tet[i]]; c /= 3; const scalar area = Foam::mag(tet.Sd(points_)) + VSMALL; - + centre += c * area; faceArea += area; } - + points_[pI] = centre / faceArea; } } @@ -383,148 +397,152 @@ void partTetMesh::updateVerticesSMP(const List<LongList<labelledPoint> >& np) void partTetMesh::updateOrigMesh(boolList* changedFacePtr) { - pointFieldPMG& pts = origMesh_.points(); + pointFieldPMG& pts = origMesh_.points(); + + boolList changedNode(pts.size(), false); - boolList changedNode(pts.size(), false); - + # ifdef USE_OMP # pragma omp parallel for if( pts.size() > 1000 ) \ schedule(guided, 10) - forAll(nodeLabelInOrigMesh_, pI) - if( nodeLabelInOrigMesh_[pI] != -1 ) - { - changedNode[nodeLabelInOrigMesh_[pI]] = true; - pts[nodeLabelInOrigMesh_[pI]] = points_[pI]; - } - - if( changedFacePtr ) - { - boolList& chF = *changedFacePtr; - chF = false; - + # endif + forAll(nodeLabelInOrigMesh_, pI) + if( nodeLabelInOrigMesh_[pI] != -1 ) + { + changedNode[nodeLabelInOrigMesh_[pI]] = true; + pts[nodeLabelInOrigMesh_[pI]] = points_[pI]; + } + + if( changedFacePtr ) + { + boolList& chF = *changedFacePtr; + chF = false; + const cellListPMG& cells = origMesh_.cells(); const VRWGraph& pointCells = origMesh_.addressingData().pointCells(); - + + # ifdef USE_OMP # pragma omp parallel for if( pointCells.size() > 100 ) \ schedule(dynamic, 20) - forAll(pointCells, pointI) + # endif + forAll(pointCells, pointI) { if( changedNode[pointI] ) { forAllRow(pointCells, pointI, pcI) { const cell& c = cells[pointCells(pointI, pcI)]; - + forAll(c, fI) chF[c[fI]] = true; } } } - + //- make sure that neighbouring processors get the same information - const PtrList<writeProcessorPatch>& pBnd = origMesh_.procBoundaries(); + const PtrList<processorBoundaryPatch>& pBnd = origMesh_.procBoundaries(); forAll(pBnd, patchI) { const label start = pBnd[patchI].patchStart(); const label size = pBnd[patchI].patchSize(); - - labelListPMG sendData; + + labelLongList sendData; for(label faceI=0;faceI<size;++faceI) { if( chF[start+faceI] ) sendData.append(faceI); } - + OPstream toOtherProc ( Pstream::blocking, pBnd[patchI].neiProcNo(), sendData.byteSize() ); - + toOtherProc << sendData; } - + forAll(pBnd, patchI) { labelList receivedData; - + IPstream fromOtherProc ( Pstream::blocking, pBnd[patchI].neiProcNo() ); - + fromOtherProc >> receivedData; - + const label start = pBnd[patchI].patchStart(); forAll(receivedData, i) chF[start+receivedData[i]] = true; } - + //- update geometry information - const_cast<polyMeshGenAddressing&> - ( - origMesh_.addressingData() - ).updateGeometry(chF); - } - else - { - const_cast<polyMeshGenAddressing&> - ( - origMesh_.addressingData() - ).clearGeom(); - } + const_cast<polyMeshGenAddressing&> + ( + origMesh_.addressingData() + ).updateGeometry(chF); + } + else + { + const_cast<polyMeshGenAddressing&> + ( + origMesh_.addressingData() + ).clearGeom(); + } } void partTetMesh::createPolyMesh(polyMeshGen& pmg) const { - polyMeshGenModifier meshModifier(pmg); - - pointFieldPMG& pAccess = meshModifier.pointsAccess(); - pAccess.setSize(points_.size()); - forAll(points_, pI) - pAccess[pI] = points_[pI]; - - VRWGraphList cellFaces; - - forAll(tets_, tetI) - { - const partTet& tet = tets_[tetI]; - - FixedList<FixedList<label, 3>, 4> tetFaces; - - //- face 0 - tetFaces[0][0] = tet[0]; - tetFaces[0][1] = tet[2]; - tetFaces[0][2] = tet[1]; - - //- face 1 - tetFaces[1][0] = tet[0]; - tetFaces[1][1] = tet[1]; - tetFaces[1][2] = tet[3]; - - //- face 2 - tetFaces[2][0] = tet[0]; - tetFaces[2][1] = tet[3]; - tetFaces[2][2] = tet[2]; - - //- face 3 - tetFaces[3][0] = tet[1]; - tetFaces[3][1] = tet[2]; - tetFaces[3][2] = tet[3]; - + polyMeshGenModifier meshModifier(pmg); + + pointFieldPMG& pAccess = meshModifier.pointsAccess(); + pAccess.setSize(points_.size()); + forAll(points_, pI) + pAccess[pI] = points_[pI]; + + VRWGraphList cellFaces; + + forAll(tets_, tetI) + { + const partTet& tet = tets_[tetI]; + + FixedList<FixedList<label, 3>, 4> tetFaces; + + //- face 0 + tetFaces[0][0] = tet[0]; + tetFaces[0][1] = tet[2]; + tetFaces[0][2] = tet[1]; + + //- face 1 + tetFaces[1][0] = tet[0]; + tetFaces[1][1] = tet[1]; + tetFaces[1][2] = tet[3]; + + //- face 2 + tetFaces[2][0] = tet[0]; + tetFaces[2][1] = tet[3]; + tetFaces[2][2] = tet[2]; + + //- face 3 + tetFaces[3][0] = tet[1]; + tetFaces[3][1] = tet[2]; + tetFaces[3][2] = tet[3]; + cellFaces.appendGraph(tetFaces); - } - - meshModifier.addCells(cellFaces); - meshModifier.reorderBoundaryFaces(); - + } + + meshModifier.addCells(cellFaces); + meshModifier.reorderBoundaryFaces(); + //- store points into subsets const label bndPointID = pmg.addPointSubset("boundaryPoints"); const label smoothPointID = pmg.addPointSubset("smoothPoints"); const label faceCentreID = pmg.addPointSubset("faceCentres"); const label cellCentreID = pmg.addPointSubset("cellCentres"); - + forAll(smoothVertex_, pointI) { if( smoothVertex_[pointI] & SMOOTH ) @@ -536,24 +554,24 @@ void partTetMesh::createPolyMesh(polyMeshGen& pmg) const if( smoothVertex_[pointI] & CELLCENTRE ) pmg.addPointToSubset(cellCentreID, pointI); } - + const VRWGraph& internalOrdering = internalPointOrdering(); const VRWGraph& boundaryOrdering = boundaryPointOrdering(); - + forAll(internalOrdering, i) { const word name = "smoothPoints_"+help::scalarToText(i); const label orderID = pmg.addPointSubset(name); - + forAllRow(internalOrdering, i, nI) pmg.addPointToSubset(orderID, internalOrdering(i, nI)); } - + forAll(boundaryOrdering, i) { const word name = "boundaryPoints_"+help::scalarToText(i); const label orderID = pmg.addPointSubset(name); - + forAllRow(boundaryOrdering, i, nI) pmg.addPointToSubset(orderID, boundaryOrdering(i, nI)); } diff --git a/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.H b/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.H index 656ec946d91548bc7602941592e7aef28f60a8ea..61b0b77da155e3d8ca3885193666734c6d29e7de 100644 --- a/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.H +++ b/meshLibrary/utilities/meshes/partTetMesh/partTetMesh.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class partTetMesh @@ -37,7 +36,7 @@ SourceFiles #define partTetMesh_H #include "boolList.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "VRWGraph.H" #include "DynList.H" #include "partTet.H" @@ -60,86 +59,86 @@ class VRWGraph; class partTetMesh { - // Private data + // Private data //- reference to the original mesh - polyMeshGen& origMesh_; - + polyMeshGen& origMesh_; + //- points in the tet mesh - LongList<point> points_; - + LongList<point> points_; + //- tetrahedra making the mesh - LongList<partTet> tets_; - + LongList<partTet> tets_; + //- label of node in the polyMeshGen - labelListPMG nodeLabelInOrigMesh_; - + labelLongList nodeLabelInOrigMesh_; + //- shall a node be used for smoothing or not - LongList<direction> smoothVertex_; - - //- addressing data - VRWGraph pointTets_; - + LongList<direction> smoothVertex_; + + //- addressing data + VRWGraph pointTets_; + //- internal point ordering for parallel runs mutable VRWGraph* internalPointsOrderPtr_; - + //- boundary point ordering for parallel runs mutable VRWGraph* boundaryPointsOrderPtr_; - + // Private data for parallel runs //- global point label - mutable labelListPMG* globalPointLabelPtr_; - + mutable labelLongList* globalPointLabelPtr_; + //- processor for containing points mutable VRWGraph* pAtProcsPtr_; - + //- mapping between global and local point labels mutable Map<label>* globalToLocalPointAddressingPtr_; - + //- processors which should communicate with the current one mutable DynList<label>* neiProcsPtr_; - - //- labels of points at parallel boundaries - mutable labelListPMG* pAtParallelBoundariesPtr_; - + + //- labels of points at parallel boundaries + mutable labelLongList* pAtParallelBoundariesPtr_; + //- labels of points serving as buffer layers on other processors - mutable labelListPMG* pAtBufferLayersPtr_; - - // Private member functions - - //- create points and tets - void createPointsAndTets(const List<direction>&); - + mutable labelLongList* pAtBufferLayersPtr_; + + // Private member functions + + //- create points and tets + void createPointsAndTets(const List<direction>&); + //- create parallel addressing void createParallelAddressing ( - const labelListPMG& nodeLabelForPoint, - const labelListPMG& nodeLabelForFace, - const labelListPMG& nodeLabelForCell + const labelLongList& nodeLabelForPoint, + const labelLongList& nodeLabelForFace, + const labelLongList& nodeLabelForCell ); - + //- create buffer layers void createBufferLayers(); - + //- create ordering of internal points for parallel execution void createSMOOTHPointsOrdering() const; - + //- create order of boundary points for parallel execution void createBOUNDARYPointsOrdering() const; - + public: - - // Constructors - //- construct from polyMeshGen - partTetMesh(polyMeshGen& mesh); - - //- construct from polyMeshGen, bad faces and the number - //- of additional layers - partTetMesh - ( - polyMeshGen& mesh, - labelHashSet& badFaces, - const direction additionalLayers = 0 - ); + + // Constructors + //- construct from polyMeshGen + partTetMesh(polyMeshGen& mesh); + + //- construct from polyMeshGen, bad faces and the number + //- of additional layers + partTetMesh + ( + polyMeshGen& mesh, + labelHashSet& badFaces, + const direction additionalLayers = 0 + ); // Enumerators @@ -153,109 +152,109 @@ public: BOUNDARY = 16 }; - // Destructor - ~partTetMesh(); - - // Member functions - //- access to points, tets and other data + // Destructor + ~partTetMesh(); + + // Member functions + //- access to points, tets and other data inline const LongList<point>& points() const { return points_; } - - inline const LongList<partTet>& tets() const - { - return tets_; - } - - inline const VRWGraph& pointTets() const - { - return pointTets_; - } - - inline const LongList<direction>& smoothVertex() const - { - return smoothVertex_; - } - - inline const labelListPMG& nodeLabelInOrigMesh() const - { - return nodeLabelInOrigMesh_; - } - + + inline const LongList<partTet>& tets() const + { + return tets_; + } + + inline const VRWGraph& pointTets() const + { + return pointTets_; + } + + inline const LongList<direction>& smoothVertex() const + { + return smoothVertex_; + } + + inline const labelLongList& nodeLabelInOrigMesh() const + { + return nodeLabelInOrigMesh_; + } + // Access to point ordering for Gauss-Seidel type of iteration //- return vertex ordering which can be executed in parallel //- the points in each row can be treated in parallel //- make sure that points added to different rows of this graph are //- not treated concurrently const VRWGraph& internalPointOrdering() const; - + //- return vertex ordering for boundary points const VRWGraph& boundaryPointOrdering() const; - + // Access to parallel data - inline const labelListPMG& globalPointLabel() const + inline const labelLongList& globalPointLabel() const { if( !Pstream::parRun() ) FatalError << "This is a serial run" << abort(FatalError); - + return *globalPointLabelPtr_; } - + inline const VRWGraph& pointAtProcs() const { if( !Pstream::parRun() ) FatalError << "This is a serial run" << abort(FatalError); - + return *pAtProcsPtr_; } - + inline const Map<label>& globalToLocalPointAddressing() const { if( !Pstream::parRun() ) FatalError << "This is a serial run" << abort(FatalError); - + return *globalToLocalPointAddressingPtr_; } - + inline const DynList<label>& neiProcs() const { if( !Pstream::parRun() ) FatalError << "This is a serial run" << abort(FatalError); - + return *neiProcsPtr_; } - - inline const labelListPMG& pointsAtProcessorBoundaries() const - { - if( !Pstream::parRun() ) - FatalError << "This is a serial run" << abort(FatalError); - - return *pAtParallelBoundariesPtr_; - } - - inline const labelListPMG& bufferLayerPoints() const + + inline const labelLongList& pointsAtProcessorBoundaries() const + { + if( !Pstream::parRun() ) + FatalError << "This is a serial run" << abort(FatalError); + + return *pAtParallelBoundariesPtr_; + } + + inline const labelLongList& bufferLayerPoints() const { if( !Pstream::parRun() ) - FatalError << "This is a serial run" << abort(FatalError); - + FatalError << "This is a serial run" << abort(FatalError); + return *pAtBufferLayersPtr_; } - + // Modifiers - + //- move the vertex to a new position void updateVertex(const label pointI, const point& newP); - + //- move vertices to their new positions //- intended for SMP parallelisation void updateVerticesSMP(const List<LongList<labelledPoint> >&); - + //- updates the vertices of the original polyMeshGen - void updateOrigMesh(boolList* changedFacePtr = NULL); - + void updateOrigMesh(boolList* changedFacePtr = NULL); + //- creates polyMeshGen from this partTetMesh - void createPolyMesh(polyMeshGen& pmg) const; + void createPolyMesh(polyMeshGen& pmg) const; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshAddressing.C b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshAddressing.C index 99b935372c745d83d032e5c0a0726b5017607953..3c689aa281240e993ee034eabbf19c0203558b5e 100644 --- a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshAddressing.C +++ b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,18 +38,18 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void partTetMesh::createPointsAndTets(const List<direction>& useCell) { - const pointFieldPMG& points = origMesh_.points(); - const faceListPMG& faces = origMesh_.faces(); - const cellListPMG& cells = origMesh_.cells(); - const labelList& owner = origMesh_.owner(); - const labelList& neighbour = origMesh_.neighbour(); - const PtrList<writePatch>& boundaries = origMesh_.boundaries(); - const PtrList<writeProcessorPatch>& procBoundaries = + const pointFieldPMG& points = origMesh_.points(); + const faceListPMG& faces = origMesh_.faces(); + const cellListPMG& cells = origMesh_.cells(); + const labelList& owner = origMesh_.owner(); + const labelList& neighbour = origMesh_.neighbour(); + const PtrList<boundaryPatch>& boundaries = origMesh_.boundaries(); + const PtrList<processorBoundaryPatch>& procBoundaries = origMesh_.procBoundaries(); const label nInternalFaces = origMesh_.nInternalFaces(); @@ -76,7 +75,7 @@ void partTetMesh::createPointsAndTets(const List<direction>& useCell) const label start = procBoundaries[patchI].patchStart(); const label size = procBoundaries[patchI].patchSize(); - labelListPMG dataToSend; + labelLongList dataToSend; for(label faceI=0;faceI<size;++faceI) { if( usedFace[start+faceI] ) @@ -96,7 +95,7 @@ void partTetMesh::createPointsAndTets(const List<direction>& useCell) //- receive data at proc boundaries forAll(procBoundaries, patchI) { - labelListPMG receivedData; + labelLongList receivedData; IPstream fromOtherProc ( @@ -110,21 +109,21 @@ void partTetMesh::createPointsAndTets(const List<direction>& useCell) forAll(receivedData, faceI) ++usedFace[start+receivedData[faceI]]; } - - const vectorField& faceCentres = origMesh_.addressingData().faceCentres(); - const vectorField& cellCentres = origMesh_.addressingData().cellCentres(); - - labelListPMG nodeLabelForPoint(points.size(), -1); - labelListPMG nodeLabelForFace(faces.size(), -1); - labelListPMG nodeLabelForCell(cells.size(), -1); - + + const vectorField& faceCentres = origMesh_.addressingData().faceCentres(); + const vectorField& cellCentres = origMesh_.addressingData().cellCentres(); + + labelLongList nodeLabelForPoint(points.size(), -1); + labelLongList nodeLabelForFace(faces.size(), -1); + labelLongList nodeLabelForCell(cells.size(), -1); + points_.clear(); smoothVertex_.clear(); //- create BOUNDARY points forAll(boundaries, patchI) { - const writePatch& patch = boundaries[patchI]; + const boundaryPatch& patch = boundaries[patchI]; const label start = patch.patchStart(); const label end = start + patch.patchSize(); @@ -161,7 +160,7 @@ void partTetMesh::createPointsAndTets(const List<direction>& useCell) //- create points at processor boundaries forAll(procBoundaries, patchI) { - const writeProcessorPatch& patch = procBoundaries[patchI]; + const processorBoundaryPatch& patch = procBoundaries[patchI]; const label start = patch.patchStart(); const label end = start + patch.patchSize(); @@ -237,10 +236,10 @@ void partTetMesh::createPointsAndTets(const List<direction>& useCell) //- create tets tetMatcher tet; - forAll(useCell, cI) - if( useCell[cI] ) - { - const cell& c = cells[cI]; + forAll(useCell, cI) + if( useCell[cI] ) + { + const cell& c = cells[cI]; if( tet.matchShape(false, faces, owner, cI, cells[cI]) ) { @@ -260,110 +259,110 @@ void partTetMesh::createPointsAndTets(const List<direction>& useCell) continue; } - - nodeLabelForCell[cI] = points_.size(); - const label centreLabel = points_.size(); + + nodeLabelForCell[cI] = points_.size(); + const label centreLabel = points_.size(); points_.append(cellCentres[cI]); smoothVertex_.append(CELLCENTRE); - - forAll(c, fI) - { - const face& f = faces[c[fI]]; - - if( owner[c[fI]] == cI ) - { - if( f.size() == 3 ) - { - partTet tet - ( - nodeLabelForPoint[f[0]], - nodeLabelForPoint[f[2]], - nodeLabelForPoint[f[1]], - centreLabel - ); - - # ifdef DEBUGSmooth - Info << "1.1 Tet " << tets_.size() << " is " - << tet << endl; - # endif - - tets_.append(tet); - } - else - { - forAll(f, pI) - { - partTet tet - ( - nodeLabelForPoint[f[pI]], - nodeLabelForPoint[f.prevLabel(pI)], - nodeLabelForFace[c[fI]], - centreLabel - ); - - # ifdef DEBUGSmooth - Info << "1.2 Tet " << tets_.size() << " is " - << tet << endl; - # endif - - tets_.append(tet); - } - } - } - else - { - if( f.size() == 3 ) - { - partTet tet - ( - nodeLabelForPoint[f[0]], - nodeLabelForPoint[f[1]], - nodeLabelForPoint[f[2]], - centreLabel - ); - - # ifdef DEBUGSmooth - Info << "2.1 Tet " << tets_.size() << " is " - << tet << endl; - # endif - - tets_.append(tet); - } - else - { - forAll(f, pI) - { - partTet tet - ( - nodeLabelForPoint[f[pI]], - nodeLabelForPoint[f.nextLabel(pI)], - nodeLabelForFace[c[fI]], - centreLabel - ); - - # ifdef DEBUGSmooth - Info << "2.2 Tet " << tets_.size() << " is " - << tet << endl; - # endif - - tets_.append(tet); - } - } - } - } - } - - //- create node labels in origMesh_ - nodeLabelInOrigMesh_.setSize(points_.size()); - nodeLabelInOrigMesh_ = -1; - forAll(nodeLabelForPoint, pI) - if( nodeLabelForPoint[pI] != -1 ) - { - nodeLabelInOrigMesh_[nodeLabelForPoint[pI]] = pI; - } - - //- create pointTets_ - pointTets_.reverseAddressing(points_.size(), tets_); + + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + if( owner[c[fI]] == cI ) + { + if( f.size() == 3 ) + { + partTet tet + ( + nodeLabelForPoint[f[0]], + nodeLabelForPoint[f[2]], + nodeLabelForPoint[f[1]], + centreLabel + ); + + # ifdef DEBUGSmooth + Info << "1.1 Tet " << tets_.size() << " is " + << tet << endl; + # endif + + tets_.append(tet); + } + else + { + forAll(f, pI) + { + partTet tet + ( + nodeLabelForPoint[f[pI]], + nodeLabelForPoint[f.prevLabel(pI)], + nodeLabelForFace[c[fI]], + centreLabel + ); + + # ifdef DEBUGSmooth + Info << "1.2 Tet " << tets_.size() << " is " + << tet << endl; + # endif + + tets_.append(tet); + } + } + } + else + { + if( f.size() == 3 ) + { + partTet tet + ( + nodeLabelForPoint[f[0]], + nodeLabelForPoint[f[1]], + nodeLabelForPoint[f[2]], + centreLabel + ); + + # ifdef DEBUGSmooth + Info << "2.1 Tet " << tets_.size() << " is " + << tet << endl; + # endif + + tets_.append(tet); + } + else + { + forAll(f, pI) + { + partTet tet + ( + nodeLabelForPoint[f[pI]], + nodeLabelForPoint[f.nextLabel(pI)], + nodeLabelForFace[c[fI]], + centreLabel + ); + + # ifdef DEBUGSmooth + Info << "2.2 Tet " << tets_.size() << " is " + << tet << endl; + # endif + + tets_.append(tet); + } + } + } + } + } + + //- create node labels in origMesh_ + nodeLabelInOrigMesh_.setSize(points_.size()); + nodeLabelInOrigMesh_ = -1; + forAll(nodeLabelForPoint, pI) + if( nodeLabelForPoint[pI] != -1 ) + { + nodeLabelInOrigMesh_[nodeLabelForPoint[pI]] = pI; + } + + //- create pointTets_ + pointTets_.reverseAddressing(points_.size(), tets_); //- create addressing for parallel runs if( Pstream::parRun() ) @@ -377,19 +376,19 @@ void partTetMesh::createPointsAndTets(const List<direction>& useCell) createBufferLayers(); } - - # ifdef DEBUGSmooth - forAll(nodeLabelInOrigMesh_, pI) - if( - (nodeLabelInOrigMesh_[pI] != -1) && - (mag(points_[pI] - points[nodeLabelInOrigMesh_[pI]]) > SMALL) - ) - FatalErrorIn - ( - "void partTetMesh::createPointsAndTets" - "(const boolList& useCell)" - ) << "Node " << pI << " is dislocated" << abort(FatalError); - # endif + + # ifdef DEBUGSmooth + forAll(nodeLabelInOrigMesh_, pI) + if( + (nodeLabelInOrigMesh_[pI] != -1) && + (mag(points_[pI] - points[nodeLabelInOrigMesh_[pI]]) > SMALL) + ) + FatalErrorIn + ( + "void partTetMesh::createPointsAndTets" + "(const boolList& useCell)" + ) << "Node " << pI << " is dislocated" << abort(FatalError); + # endif } void partTetMesh::createSMOOTHPointsOrdering() const @@ -398,7 +397,7 @@ void partTetMesh::createSMOOTHPointsOrdering() const VRWGraph& internalPointsOrder = *internalPointsOrderPtr_; internalPointsOrder.setSize(0); - labelListPMG order(points_.size(), -1); + labelLongList order(points_.size(), -1); boolList helper(points_.size()); bool found; @@ -406,7 +405,7 @@ void partTetMesh::createSMOOTHPointsOrdering() const { found = false; helper = false; - labelListPMG selectedPoints; + labelLongList selectedPoints; forAll(points_, nodeI) { @@ -473,7 +472,7 @@ void partTetMesh::createBOUNDARYPointsOrdering() const VRWGraph& boundaryPointsOrder = *boundaryPointsOrderPtr_; boundaryPointsOrder.setSize(0); - labelListPMG order(points_.size(), -1); + labelLongList order(points_.size(), -1); boolList helper(points_.size()); bool found; @@ -482,7 +481,7 @@ void partTetMesh::createBOUNDARYPointsOrdering() const found = false; helper = false; - labelListPMG selectedPoints; + labelLongList selectedPoints; forAll(points_, nodeI) { if( smoothVertex_[nodeI] & BOUNDARY ) diff --git a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshParallelAddressing.C b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshParallelAddressing.C index c4d9c1e67bbb3c6f945e423f4586a2842d661650..f179f065f3b8ebba5921a548d802924fc74c0947 100644 --- a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshParallelAddressing.C +++ b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshParallelAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,14 +40,14 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void partTetMesh::createParallelAddressing ( - const labelListPMG& nodeLabelForPoint, - const labelListPMG& nodeLabelForFace, - const labelListPMG& nodeLabelForCell + const labelLongList& nodeLabelForPoint, + const labelLongList& nodeLabelForFace, + const labelLongList& nodeLabelForCell ) { //- vertices marked as SMOOTH and BOUNDARY are used by the smoother @@ -56,8 +55,8 @@ void partTetMesh::createParallelAddressing //- allocate global point labels if( !globalPointLabelPtr_ ) - globalPointLabelPtr_ = new labelListPMG(); - labelListPMG& globalTetPointLabel = *globalPointLabelPtr_; + globalPointLabelPtr_ = new labelLongList(); + labelLongList& globalTetPointLabel = *globalPointLabelPtr_; globalTetPointLabel.setSize(points_.size()); globalTetPointLabel = -1; @@ -75,14 +74,14 @@ void partTetMesh::createParallelAddressing globalToLocal.clear(); //- allocate storage for points at parallel boundaries - if( !pAtParallelBoundariesPtr_ ) - pAtParallelBoundariesPtr_ = new labelListPMG(); - labelListPMG& pAtParallelBoundaries = *pAtParallelBoundariesPtr_; - pAtParallelBoundaries.clear(); + if( !pAtParallelBoundariesPtr_ ) + pAtParallelBoundariesPtr_ = new labelLongList(); + labelLongList& pAtParallelBoundaries = *pAtParallelBoundariesPtr_; + pAtParallelBoundaries.clear(); //- create point-processors addressing - std::map<label, labelListPMG> exchangeData; - std::map<label, labelListPMG>::iterator iter; + std::map<label, labelLongList> exchangeData; + std::map<label, labelLongList>::iterator iter; const polyMeshGenAddressing& addressing = origMesh_.addressingData(); const Map<label>& globalToLocalPointAddressing = @@ -91,7 +90,7 @@ void partTetMesh::createParallelAddressing const DynList<label>& pNeiProcs = addressing.pointNeiProcs(); forAll(pNeiProcs, procI) - exchangeData.insert(std::make_pair(pNeiProcs[procI], labelListPMG())); + exchangeData.insert(std::make_pair(pNeiProcs[procI], labelLongList())); //- make sure that the same vertices are marked for smoothing on all procs //- this is performed by sending the labels of vertices which are not used @@ -117,7 +116,7 @@ void partTetMesh::createParallelAddressing } //- exchange data with other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); //- set the values according to other processors @@ -232,13 +231,13 @@ void partTetMesh::createParallelAddressing //- create global to local mapping forAll(globalTetPointLabel, pI) - { + { if( pProcs.sizeOfRow(pI) != 0 ) - { - pAtParallelBoundaries.append(pI); + { + pAtParallelBoundaries.append(pI); globalToLocal.insert(globalTetPointLabel[pI], pI); - } - } + } + } //- mark vertices at parallel boundaries forAll(smoothVertex_, pI) @@ -319,13 +318,13 @@ void partTetMesh::createParallelAddressing void partTetMesh::createBufferLayers() { VRWGraph& pProcs = *pAtProcsPtr_; - labelListPMG& globalTetPointLabel = *globalPointLabelPtr_; + labelLongList& globalTetPointLabel = *globalPointLabelPtr_; Map<label>& globalToLocal = *globalToLocalPointAddressingPtr_; const DynList<label>& neiProcs = *this->neiProcsPtr_; if( !pAtBufferLayersPtr_ ) - pAtBufferLayersPtr_ = new labelListPMG(); - labelListPMG& pAtBufferLayers = *pAtBufferLayersPtr_; + pAtBufferLayersPtr_ = new labelLongList(); + labelLongList& pAtBufferLayers = *pAtBufferLayersPtr_; pAtBufferLayers.clear(); //- create the map @@ -396,9 +395,9 @@ void partTetMesh::createBufferLayers() const parPartTet& tet = receivedTets[i]; DynList<label> tetPointLabels; - for(label i=0;i<4;++i) + for(label j=0;j<4;++j) { - const label gpI = tet[i].pointLabel(); + const label gpI = tet[j].pointLabel(); if( globalToLocal.found(gpI) ) { @@ -414,7 +413,7 @@ void partTetMesh::createBufferLayers() { newGlobalToLocal.insert(gpI, points_.size()); tetPointLabels.append(points_.size()); - points_.append(tet[i].coordinates()); + points_.append(tet[j].coordinates()); nodeLabelInOrigMesh_.append(-1); smoothVertex_.append(NONE); DynList<label> helper; diff --git a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.C b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.C index f0446181b4a72d1b6678e24bb8628fcac0fb40b1..79304261df24bb11ecf8725e711d0960b2e17882 100644 --- a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.C +++ b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -70,66 +69,66 @@ partTetMeshSimplex::partTetMeshSimplex } # ifdef DEBUGSmooth - Info << "Tet " << tetI << " is " << tet << endl; - # endif - - const label pos = tet.whichPosition(pI); - switch( pos ) - { - case 0: - { - tets_[tetI] = - partTet - ( - addr[tet.b()], - addr[tet.d()], - addr[tet.c()], - addr[tet.a()] - ); - } break; - case 1: - { - tets_[tetI] = - partTet - ( - addr[tet.a()], - addr[tet.c()], - addr[tet.d()], - addr[tet.b()] - ); - } break; - case 2: - { - tets_[tetI] = - partTet - ( - addr[tet.a()], - addr[tet.d()], - addr[tet.b()], - addr[tet.c()] - ); - } break; - case 3: - { - tets_[tetI] = - partTet - ( - addr[tet.a()], - addr[tet.b()], - addr[tet.c()], - addr[tet.d()] - ); - } break; - default: - { - FatalErrorIn - ( - "partTetMeshSimplex::partTetMeshSimplex(" + Info << "Tet " << tetI << " is " << tet << endl; + # endif + + const label pos = tet.whichPosition(pI); + switch( pos ) + { + case 0: + { + tets_[tetI] = + partTet + ( + addr[tet.b()], + addr[tet.d()], + addr[tet.c()], + addr[tet.a()] + ); + } break; + case 1: + { + tets_[tetI] = + partTet + ( + addr[tet.a()], + addr[tet.c()], + addr[tet.d()], + addr[tet.b()] + ); + } break; + case 2: + { + tets_[tetI] = + partTet + ( + addr[tet.a()], + addr[tet.d()], + addr[tet.b()], + addr[tet.c()] + ); + } break; + case 3: + { + tets_[tetI] = + partTet + ( + addr[tet.a()], + addr[tet.b()], + addr[tet.c()], + addr[tet.d()] + ); + } break; + default: + { + FatalErrorIn + ( + "partTetMeshSimplex::partTetMeshSimplex(" "(const partTetMesh& tm, const label pI)" - ) << "Point " << pI << " is not present in tet" << tet - << abort(FatalError); - } - } + ) << "Point " << pI << " is not present in tet" << tet + << abort(FatalError); + } + } } } @@ -163,63 +162,63 @@ partTetMeshSimplex::partTetMeshSimplex if( tet[i].pointLabel() == gpI ) pos = i; } - - switch( pos ) - { - case 0: - { - tets_[tetI] = - partTet - ( - addr[tet[1].pointLabel()], - addr[tet[3].pointLabel()], - addr[tet[2].pointLabel()], - addr[tet[0].pointLabel()] - ); - } break; - case 1: - { - tets_[tetI] = - partTet - ( - addr[tet[0].pointLabel()], - addr[tet[2].pointLabel()], - addr[tet[3].pointLabel()], - addr[tet[1].pointLabel()] - ); - } break; - case 2: - { - tets_[tetI] = - partTet - ( - addr[tet[0].pointLabel()], - addr[tet[3].pointLabel()], - addr[tet[1].pointLabel()], - addr[tet[2].pointLabel()] - ); - } break; - case 3: - { - tets_[tetI] = - partTet - ( - addr[tet[0].pointLabel()], - addr[tet[1].pointLabel()], - addr[tet[2].pointLabel()], - addr[tet[3].pointLabel()] - ); - } break; - default: - { - FatalErrorIn - ( - "partTetMeshSimplex::partTetMeshSimplex(" + + switch( pos ) + { + case 0: + { + tets_[tetI] = + partTet + ( + addr[tet[1].pointLabel()], + addr[tet[3].pointLabel()], + addr[tet[2].pointLabel()], + addr[tet[0].pointLabel()] + ); + } break; + case 1: + { + tets_[tetI] = + partTet + ( + addr[tet[0].pointLabel()], + addr[tet[2].pointLabel()], + addr[tet[3].pointLabel()], + addr[tet[1].pointLabel()] + ); + } break; + case 2: + { + tets_[tetI] = + partTet + ( + addr[tet[0].pointLabel()], + addr[tet[3].pointLabel()], + addr[tet[1].pointLabel()], + addr[tet[2].pointLabel()] + ); + } break; + case 3: + { + tets_[tetI] = + partTet + ( + addr[tet[0].pointLabel()], + addr[tet[1].pointLabel()], + addr[tet[2].pointLabel()], + addr[tet[3].pointLabel()] + ); + } break; + default: + { + FatalErrorIn + ( + "partTetMeshSimplex::partTetMeshSimplex(" "(const partTetMesh& tm, const label pI)" - ) << "Point " << gpI << " is not present in tet" << tet - << abort(FatalError); - } - } + ) << "Point " << gpI << " is not present in tet" << tet + << abort(FatalError); + } + } } } diff --git a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.H b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.H index 2e540d4ac7c52d27c6f31b50113a1649ae45c48c..32d38d525b02bdbac8a3b5aa34ab19a3b07ade68 100644 --- a/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.H +++ b/meshLibrary/utilities/meshes/partTetMesh/partTetMeshSimplex.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class partTetMeshSimplex diff --git a/meshLibrary/utilities/meshes/partTriMesh/partTriMesh.C b/meshLibrary/utilities/meshes/partTriMesh/partTriMesh.C new file mode 100644 index 0000000000000000000000000000000000000000..86b8f75b31e1190fcd979b2bcaa5b03e1c8113dc --- /dev/null +++ b/meshLibrary/utilities/meshes/partTriMesh/partTriMesh.C @@ -0,0 +1,504 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "demandDrivenData.H" +#include "partTriMesh.H" +#include "meshSurfacePartitioner.H" +#include "VRWGraphList.H" +#include "triSurfModifier.H" +#include "helperFunctions.H" + +#include <map> + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGSmooth + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +partTriMesh::partTriMesh(const meshSurfacePartitioner& mPart) +: + mPart_(mPart), + surf_(), + pointLabelInMeshSurface_(), + meshSurfacePointLabelInTriMesh_(), + pointType_(), + globalPointLabelPtr_(NULL), + pAtProcsPtr_(NULL), + globalToLocalPointAddressingPtr_(NULL), + neiProcsPtr_(NULL), + pAtParallelBoundariesPtr_(NULL), + pAtBufferLayersPtr_(NULL) +{ + const meshSurfaceEngine& meshSurface = mPart.surfaceEngine(); + List<direction> useFace(meshSurface.boundaryFaces().size(), direction(1)); + + createPointsAndTrias(useFace); +} + +partTriMesh::partTriMesh +( + const meshSurfacePartitioner& mPart, + const labelHashSet& invertedPoints, + const label additionalLayers +) +: + mPart_(mPart), + surf_(), + pointLabelInMeshSurface_(), + meshSurfacePointLabelInTriMesh_(), + pointType_(), + globalPointLabelPtr_(NULL), + pAtProcsPtr_(NULL), + globalToLocalPointAddressingPtr_(NULL), + neiProcsPtr_(NULL), + pAtParallelBoundariesPtr_(NULL), + pAtBufferLayersPtr_(NULL) +{ + const meshSurfaceEngine& meshSurface = mPart.surfaceEngine(); + const VRWGraph& pointFaces = meshSurface.pointFaces(); + const faceList::subList& bFaces = meshSurface.boundaryFaces(); + const labelList& bPoints = meshSurface.boundaryPoints(); + const labelList& bp = meshSurface.bp(); + + List<direction> useFace(bFaces.size(), direction(0)); + + //- select cells containing at least one vertex of the bad faces + forAll(pointFaces, bpI) + if( invertedPoints.found(bPoints[bpI]) ) + { + forAllRow(pointFaces, bpI, pfI) + useFace[pointFaces(bpI, pfI)] = 1; + } + + //- add additional layer of cells + for(direction layerI=1;layerI<(additionalLayers+direction(1));++layerI) + { + forAll(useFace, bfI) + if( useFace[bfI] == layerI ) + { + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + { + const label bpI = bp[bf[pI]]; + + forAllRow(pointFaces, bpI, pfI) + { + const label fLabel = pointFaces(bpI, pfI); + + if( !useFace[fLabel] ) + useFace[fLabel] = layerI + 1; + } + } + } + + if( Pstream::parRun() ) + { + const labelList& globalPointLabel = + meshSurface.globalBoundaryPointLabel(); + const VRWGraph& pProcs = meshSurface.bpAtProcs(); + const Map<label>& globalToLocal = + meshSurface.globalToLocalBndPointAddressing(); + + std::map<label, labelLongList> eData; + forAllConstIter(Map<label>, globalToLocal, iter) + { + const label bpI = iter(); + + forAllRow(pProcs, bpI, procI) + { + const label neiProc = pProcs(bpI, procI); + if( neiProc == Pstream::myProcNo() ) + continue; + + if( eData.find(neiProc) == eData.end() ) + { + eData.insert + ( + std::make_pair(neiProc, labelLongList()) + ); + } + + forAllRow(pointFaces, bpI, pfI) + if( useFace[pointFaces(bpI, pfI)] == layerI ) + { + eData[neiProc].append(globalPointLabel[bpI]); + break; + } + } + } + + //- exchange data with other processors + labelLongList receivedData; + help::exchangeMap(eData, receivedData); + + forAll(receivedData, i) + { + const label bpI = globalToLocal[receivedData[i]]; + + forAllRow(pointFaces, bpI, pfI) + { + const label fLabel = pointFaces(bpI, pfI); + if( !useFace[fLabel] ) + useFace[fLabel] = layerI + 1; + } + } + } + } + + createPointsAndTrias(useFace); +} + +partTriMesh::~partTriMesh() +{ + deleteDemandDrivenData(globalPointLabelPtr_); + deleteDemandDrivenData(pAtProcsPtr_); + deleteDemandDrivenData(globalToLocalPointAddressingPtr_); + deleteDemandDrivenData(neiProcsPtr_); + deleteDemandDrivenData(pAtParallelBoundariesPtr_); + deleteDemandDrivenData(pAtBufferLayersPtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void partTriMesh::updateVertex(const label pI, const point& newP) +{ + triSurfModifier sMod(surf_); + pointField& pts = sMod.pointsAccess(); + const VRWGraph& pointFacets = surf_.pointFacets(); + + pts[pI] = newP; + + if( pointType_[pI] & FACECENTRE ) + { + Warning << "Smoothing auxiliary vertex." + << " This has no effect on the original mesh" << endl; + return; + } + + //- find face centres attached + DynList<label> helper; + forAllRow(pointFacets, pI, ptI) + { + const label centreI = surf_[pointFacets(pI, ptI)][2]; + if( pointType_[centreI] & FACECENTRE ) + helper.appendIfNotIn(centreI); + } + + //- update coordinates of FACECENTRE vertices + forAll(helper, i) + { + const label centreI = helper[i]; + + point centre(vector::zero); + scalar faceArea(0.0); + forAllRow(pointFacets, centreI, ptI) + { + const labelledTri& tri = surf_[pointFacets(centreI, ptI)]; + point c(vector::zero); + for(label i=0;i<3;++i) + c += pts[tri[i]]; + c /= 3; + const scalar area = tri.mag(pts) + VSMALL; + + centre += c * area; + faceArea += area; + } + + pts[centreI] = centre / faceArea; + } +} + +void partTriMesh::updateVerticesSMP(const List<LongList<labelledPoint> >& np) +{ + triSurfModifier sMod(surf_); + pointField& pts = sMod.pointsAccess(); + const VRWGraph& pointFacets = surf_.pointFacets(); + + List<direction> updateType(pts.size(), direction(0)); + + # ifdef USE_OMP + # pragma omp parallel num_threads(np.size()) + # endif + { + # ifdef USE_OMP + const LongList<labelledPoint>& newPoints = np[omp_get_thread_num()]; + # else + const LongList<labelledPoint>& newPoints = np[0]; + # endif + + forAll(newPoints, i) + { + const labelledPoint& lp = newPoints[i]; + const label pointI = lp.pointLabel(); + + pts[pointI] = lp.coordinates(); + updateType[pointI] |= SMOOTH; + + forAllRow(pointFacets, pointI, ptI) + { + const labelledTri& tri = surf_[pointFacets(pointI, ptI)]; + + if( pointType_[tri[2]] & FACECENTRE ) + updateType[tri[2]] |= FACECENTRE; + } + } + } + + //- update coordinates of buffer layer points + if( Pstream::parRun() ) + { + const labelLongList& bufferLayerPoints = this->bufferLayerPoints(); + const VRWGraph& pProcs = this->pointAtProcs(); + const labelLongList& globalPointLabel = this->globalPointLabel(); + const Map<label>& globalToLocal = this->globalToLocalPointAddressing(); + const DynList<label>& neiProcs = this->neiProcs(); + + //- create the map + std::map<label, LongList<labelledPoint> > exchangeData; + forAll(neiProcs, i) + exchangeData.insert + ( + std::make_pair(neiProcs[i], LongList<labelledPoint>()) + ); + + //- add points into the map + forAll(bufferLayerPoints, pI) + { + const label pointI = bufferLayerPoints[pI]; + + if( !(updateType[pointI] & SMOOTH) ) + continue; + + forAllRow(pProcs, pointI, i) + { + const label neiProc = pProcs(pointI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelledPoint(globalPointLabel[pointI], pts[pointI]) + ); + } + } + + LongList<labelledPoint> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelledPoint& lp = receivedData[i]; + + const label triPointI = globalToLocal[lp.pointLabel()]; + pts[triPointI] = lp.coordinates(); + + forAllRow(pointFacets, triPointI, ptI) + { + const labelledTri& tri = surf_[pointFacets(triPointI, ptI)]; + + if( pointType_[tri[2]] & FACECENTRE ) + updateType[tri[2]] |= FACECENTRE; + } + } + } + + //- update coordinates of FACECENTRE vertices + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(updateType, pI) + { + if( updateType[pI] & FACECENTRE ) + { + point centre(vector::zero); + scalar faceArea(0.0); + forAllRow(pointFacets, pI, ptI) + { + const labelledTri& tri = surf_[pointFacets(pI, ptI)]; + point c(vector::zero); + for(label i=0;i<3;++i) + c += pts[tri[i]]; + c /= 3; + const scalar area = tri.mag(pts) + VSMALL; + + centre += c * area; + faceArea += area; + } + + pts[pI] = centre / faceArea; + } + } +} + +void partTriMesh::updateVertices() +{ + const meshSurfaceEngine& mse = mPart_.surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + labelLongList movedPoints(bPoints.size()); + forAll(movedPoints, i) + movedPoints[i] = i; + + updateVertices(movedPoints); +} + +void partTriMesh::updateVertices(const labelLongList& movedPoints) +{ + const meshSurfaceEngine& mse = mPart_.surfaceEngine(); + const pointFieldPMG& points = mse.points(); + const labelList& bPoints = mse.boundaryPoints(); + + triSurfModifier sMod(surf_); + pointField& pts = sMod.pointsAccess(); + const VRWGraph& pointFacets = surf_.pointFacets(); + + List<direction> updateType(pts.size(), direction(0)); + + //- update coordinates of vertices which exist in the surface + //- of the volume mesh + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(movedPoints, i) + { + const label bpI = movedPoints[i]; + const label pointI = bPoints[bpI]; + const label triPointI = meshSurfacePointLabelInTriMesh_[bpI]; + + pts[triPointI] = points[pointI]; + updateType[triPointI] |= SMOOTH; + + forAllRow(pointFacets, triPointI, ptI) + { + const labelledTri& tri = surf_[pointFacets(triPointI, ptI)]; + + if( pointType_[tri[2]] & FACECENTRE ) + updateType[tri[2]] |= FACECENTRE; + } + } + + //- update coordinates of buffer layer points + if( Pstream::parRun() ) + { + const labelLongList& bufferLayerPoints = this->bufferLayerPoints(); + const VRWGraph& pProcs = this->pointAtProcs(); + const labelLongList& globalPointLabel = this->globalPointLabel(); + const Map<label>& globalToLocal = this->globalToLocalPointAddressing(); + const DynList<label>& neiProcs = this->neiProcs(); + + //- create the map + std::map<label, LongList<labelledPoint> > exchangeData; + forAll(neiProcs, i) + exchangeData.insert + ( + std::make_pair(neiProcs[i], LongList<labelledPoint>()) + ); + + //- add points into the map + forAll(bufferLayerPoints, pI) + { + const label pointI = bufferLayerPoints[pI]; + + if( !(updateType[pointI] & SMOOTH) ) + continue; + + forAllRow(pProcs, pointI, i) + { + const label neiProc = pProcs(pointI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelledPoint(globalPointLabel[pointI], pts[pointI]) + ); + } + } + + LongList<labelledPoint> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelledPoint& lp = receivedData[i]; + + const label triPointI = globalToLocal[lp.pointLabel()]; + pts[triPointI] = lp.coordinates(); + + forAllRow(pointFacets, triPointI, ptI) + { + const labelledTri& tri = surf_[pointFacets(triPointI, ptI)]; + + if( pointType_[tri[2]] & FACECENTRE ) + updateType[tri[2]] |= FACECENTRE; + } + } + } + + //- update coordinates of FACECENTRE vertices + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(updateType, pI) + { + if( updateType[pI] & FACECENTRE ) + { + point centre(vector::zero); + scalar faceArea(0.0); + forAllRow(pointFacets, pI, ptI) + { + const labelledTri& tri = surf_[pointFacets(pI, ptI)]; + point c(vector::zero); + for(label i=0;i<3;++i) + c += pts[tri[i]]; + c /= 3; + const scalar area = tri.mag(pts) + VSMALL; + + centre += c * area; + faceArea += area; + } + + pts[pI] = centre / faceArea; + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/partTriMesh/partTriMesh.H b/meshLibrary/utilities/meshes/partTriMesh/partTriMesh.H new file mode 100644 index 0000000000000000000000000000000000000000..27d4fb9473a753d658893a449668ac49a0ee9292 --- /dev/null +++ b/meshLibrary/utilities/meshes/partTriMesh/partTriMesh.H @@ -0,0 +1,267 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + partTriMesh + +Description + Triangulation of mesh surface needed for surface smoothing + +SourceFiles + partTriMesh.C + +\*---------------------------------------------------------------------------*/ + +#ifndef partTriMesh_H +#define partTriMesh_H + +#include "boolList.H" +#include "labelLongList.H" +#include "VRWGraph.H" +#include "DynList.H" +#include "HashSet.H" +#include "labelledPoint.H" +#include "triSurf.H" +#include "Map.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class meshSurfacePartitioner; +class VRWGraph; + +/*---------------------------------------------------------------------------*\ + Class partTriMesh Declaration +\*---------------------------------------------------------------------------*/ + +class partTriMesh +{ + // Private data + //- const reference to the meshSurfacePartitioner + const meshSurfacePartitioner& mPart_; + + //- surface triangulation created from + triSurf surf_; + + //- label of point in the mesh surface + labelLongList pointLabelInMeshSurface_; + + //- label of mesh surface point in the partTriMesh + labelList meshSurfacePointLabelInTriMesh_; + + //- shall a node be used for smoothing or not + LongList<direction> pointType_; + + // Private data for parallel runs + //- global point label + mutable labelLongList* globalPointLabelPtr_; + + //- processor for containing points + mutable VRWGraph* pAtProcsPtr_; + + //- mapping between global and local point labels + mutable Map<label>* globalToLocalPointAddressingPtr_; + + //- processors which should communicate with the current one + mutable DynList<label>* neiProcsPtr_; + + //- labels of points at parallel boundaries + mutable labelLongList* pAtParallelBoundariesPtr_; + + //- labels of points serving as buffer layers on other processors + mutable labelLongList* pAtBufferLayersPtr_; + + // Private member functions + + //- create surface triangulation + void createPointsAndTrias(const List<direction>&); + + //- create parallel addressing + void createParallelAddressing + ( + const labelList& nodeLabelForPoint, + const labelList& nodeLabelForFace + ); + + //- create buffer layers + void createBufferLayers(); + + //- update buffer layer points + void updateBufferLayers(); + + //- disallow bitwise assignment + void operator=(const partTriMesh&); + + //- disallow bitwise copy construct + partTriMesh(const partTriMesh&); + +public: + + // Constructors + //- construct from meshSurfacePartitioner + partTriMesh(const meshSurfacePartitioner& mPart); + + //- construct from meshSurfacePartitioner, inverted points + //- and the number of additional layers + partTriMesh + ( + const meshSurfacePartitioner& mPart, + const labelHashSet& invertedPoints, + const label additionalLayers = 0 + ); + + // Enumerators + + enum vertexTypes + { + NONE = 0, + SMOOTH = 1, + FACECENTRE = 2, + PARALLELBOUNDARY = 8, + BOUNDARY = 16, + FEATUREEDGE = 32, + CORNER = 64 + }; + + // Destructor + ~partTriMesh(); + + // Member functions + //- access to points, tets and other data + inline const pointField& points() const + { + return surf_.points(); + } + + inline const LongList<labelledTri>& triangles() const + { + return surf_.facets(); + } + + inline const VRWGraph& pointTriangles() const + { + return surf_.pointFacets(); + } + + inline const LongList<direction>& pointType() const + { + return pointType_; + } + + inline const labelLongList& pointLabelInMeshSurface() const + { + return pointLabelInMeshSurface_; + } + + //- return indices of mesh sutrface points in the surface triangulation + //- additional points which do not exist in mesh surface are labelled -1 + inline const labelList& meshSurfacePointLabelInTriMesh() const + { + return meshSurfacePointLabelInTriMesh_; + } + + // Access to parallel data + inline const labelLongList& globalPointLabel() const + { + if( !Pstream::parRun() ) + FatalError << "This is a serial run" << abort(FatalError); + + return *globalPointLabelPtr_; + } + + inline const VRWGraph& pointAtProcs() const + { + if( !Pstream::parRun() ) + FatalError << "This is a serial run" << abort(FatalError); + + return *pAtProcsPtr_; + } + + inline const Map<label>& globalToLocalPointAddressing() const + { + if( !Pstream::parRun() ) + FatalError << "This is a serial run" << abort(FatalError); + + return *globalToLocalPointAddressingPtr_; + } + + inline const DynList<label>& neiProcs() const + { + if( !Pstream::parRun() ) + FatalError << "This is a serial run" << abort(FatalError); + + return *neiProcsPtr_; + } + + inline const labelLongList& pointsAtProcessorBoundaries() const + { + if( !Pstream::parRun() ) + FatalError << "This is a serial run" << abort(FatalError); + + return *pAtParallelBoundariesPtr_; + } + + inline const labelLongList& bufferLayerPoints() const + { + if( !Pstream::parRun() ) + FatalError << "This is a serial run" << abort(FatalError); + + return *pAtBufferLayersPtr_; + } + + // Modifiers + + //- move the vertex to a new position + void updateVertex(const label pointI, const point& newP); + + //- move vertices to their new positions + //- intended for SMP parallelisation + void updateVerticesSMP(const List<LongList<labelledPoint> >&); + + //- update coordinates of points in partTriMesh to match the coordinates + //- in the mesh surface + void updateVertices(); + + //- update coordinates of points in partTriMesh to match the coordinates + //- of the specified points in the mesh surface + void updateVertices(const labelLongList&); + + //- return triSurf from this partTriMesh + const triSurf& getTriSurf() const + { + return surf_; + } +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/partTriMesh/partTriMeshAddressing.C b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshAddressing.C new file mode 100644 index 0000000000000000000000000000000000000000..3507e71c2e344abcc529d8fd0d5e6e054745ba4f --- /dev/null +++ b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshAddressing.C @@ -0,0 +1,169 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "demandDrivenData.H" +#include "meshSurfacePartitioner.H" +#include "partTriMesh.H" +#include "meshSurfaceEngine.H" +#include "triSurfModifier.H" + +//#define DEBUGSmooth + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void partTriMesh::createPointsAndTrias +( + const List<direction>& useFace +) +{ + const labelList& facePatch = mPart_.boundaryFacePatches(); + const meshSurfaceEngine& meshSurface = mPart_.surfaceEngine(); + const pointFieldPMG& points = meshSurface.points(); + const vectorField& faceCentres = meshSurface.faceCentres(); + const labelList& bPoints = meshSurface.boundaryPoints(); + const labelList& bp = meshSurface.bp(); + const faceList::subList& bFaces = meshSurface.boundaryFaces(); + + meshSurfacePointLabelInTriMesh_.setSize(bPoints.size()); + meshSurfacePointLabelInTriMesh_ = -1; + labelList nodeLabelForFace(bFaces.size(), -1); + + label nTriPoints(0); + forAll(bFaces, bfI) + { + if( useFace[bfI] ) + { + const face& bf = bFaces[bfI]; + + //- create a point in the face centre + if( bf.size() > 3 ) + nodeLabelForFace[bfI] = nTriPoints++; + + //- create points at face points + forAll(bf, pI) + { + const label bpI = bp[bf[pI]]; + + if( meshSurfacePointLabelInTriMesh_[bpI] == -1 ) + meshSurfacePointLabelInTriMesh_[bpI] = nTriPoints++; + } + + //- create triangles + if( bf.size() > 3 ) + { + forAll(bf, eI) + { + labelledTri tri + ( + meshSurfacePointLabelInTriMesh_[bp[bf[eI]]], + meshSurfacePointLabelInTriMesh_[bp[bf.nextLabel(eI)]], + nodeLabelForFace[bfI], + facePatch[bfI] + ); + + surf_.appendTriangle(tri); + } + } + else + { + //- face is a triangle + labelledTri tri + ( + meshSurfacePointLabelInTriMesh_[bp[bf[0]]], + meshSurfacePointLabelInTriMesh_[bp[bf[1]]], + meshSurfacePointLabelInTriMesh_[bp[bf[2]]], + facePatch[bfI] + ); + + surf_.appendTriangle(tri); + } + } + } + + //- add points + triSurfModifier sMod(surf_); + pointField& pts = sMod.pointsAccess(); + pts.setSize(nTriPoints); + + pointType_.setSize(nTriPoints); + pointType_ = NONE; + + pointLabelInMeshSurface_.setSize(pts.size()); + pointLabelInMeshSurface_ = -1; + + forAll(meshSurfacePointLabelInTriMesh_, bpI) + if( meshSurfacePointLabelInTriMesh_[bpI] != -1 ) + { + const label npI = meshSurfacePointLabelInTriMesh_[bpI]; + pointLabelInMeshSurface_[npI] = bpI; + pts[npI] = points[bPoints[bpI]]; + pointType_[npI] |= SMOOTH; + } + + forAll(nodeLabelForFace, bfI) + if( nodeLabelForFace[bfI] != -1 ) + { + const label npI = nodeLabelForFace[bfI]; + pts[npI] = faceCentres[bfI]; + pointType_[npI] = FACECENTRE; + } + + //- set CORNER and FEATUREEDGE flags to surface points + forAllConstIter(labelHashSet, mPart_.corners(), it) + if( meshSurfacePointLabelInTriMesh_[it.key()] != -1 ) + pointType_[meshSurfacePointLabelInTriMesh_[it.key()]] |= CORNER; + + forAllConstIter(labelHashSet, mPart_.edgePoints(), it) + { + const label pI = meshSurfacePointLabelInTriMesh_[it.key()]; + if( pI != -1 ) + pointType_[pI] |= FEATUREEDGE; + } + + //- create addressing for parallel runs + if( Pstream::parRun() ) + { + createParallelAddressing + ( + meshSurfacePointLabelInTriMesh_, + nodeLabelForFace + ); + + createBufferLayers(); + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/partTriMesh/partTriMeshParallelAddressing.C b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshParallelAddressing.C new file mode 100644 index 0000000000000000000000000000000000000000..87d9397bc2658a73b212e1fe2bbdc62694dae400 --- /dev/null +++ b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshParallelAddressing.C @@ -0,0 +1,478 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "demandDrivenData.H" +#include "meshSurfacePartitioner.H" +#include "partTriMesh.H" +#include "triSurfModifier.H" +#include "meshSurfaceEngine.H" +#include "helperFunctionsPar.H" +#include "parTriFace.H" + +#include <map> + +//#define DEBUGSmooth + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void partTriMesh::createParallelAddressing +( + const labelList& nodeLabelForPoint, + const labelList& nodeLabelForFace +) +{ + const meshSurfaceEngine& mse = mPart_.surfaceEngine(); + + const pointField& pts = surf_.points(); + + //- vertices marked as SMOOTH are used by the smoother + const direction useType = SMOOTH; + + //- allocate global point labels + if( !globalPointLabelPtr_ ) + globalPointLabelPtr_ = new labelLongList(); + labelLongList& globalPointLabel = *globalPointLabelPtr_; + globalPointLabel.setSize(pts.size()); + globalPointLabel = -1; + + //- allocated point-processors addressing + if( !pAtProcsPtr_ ) + pAtProcsPtr_ = new VRWGraph(); + VRWGraph& pProcs = *pAtProcsPtr_; + pProcs.setSize(0); + pProcs.setSize(pts.size()); + + //- allocate global-to-local point addressing + if( !globalToLocalPointAddressingPtr_ ) + globalToLocalPointAddressingPtr_ = new Map<label>(); + Map<label>& globalToLocal = *globalToLocalPointAddressingPtr_; + globalToLocal.clear(); + + //- allocate storage for points at parallel boundaries + if( !pAtParallelBoundariesPtr_ ) + pAtParallelBoundariesPtr_ = new labelLongList(); + labelLongList& pAtParallelBoundaries = *pAtParallelBoundariesPtr_; + pAtParallelBoundaries.clear(); + + //- create point-processors addressing + std::map<label, labelLongList> exchangeData; + std::map<label, labelLongList>::iterator iter; + + const Map<label>& globalToLocalPointAddressing = + mse.globalToLocalBndPointAddressing(); + const VRWGraph& pAtProcs = mse.bpAtProcs(); + const DynList<label>& pNeiProcs = mse.bpNeiProcs(); + + forAll(pNeiProcs, procI) + exchangeData.insert(std::make_pair(pNeiProcs[procI], labelLongList())); + + //- make sure that the same vertices are marked for smoothing on all procs + //- this is performed by sending the labels of vertices which are not used + //- for tet mesh creation and the tet mesh vertices which are not moved + forAllConstIter(Map<label>, globalToLocalPointAddressing, it) + { + const label pI = it(); + + if( + nodeLabelForPoint[pI] == -1 || + !pointType_[nodeLabelForPoint[pI]] + ) + { + forAllRow(pAtProcs, pI, procI) + { + const label neiProc = pAtProcs(pI, procI); + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append(it.key()); + } + } + } + + //- exchange data with other processors + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + //- set the values according to other processors + forAll(receivedData, i) + { + const label pointI = globalToLocalPointAddressing[receivedData[i]]; + + if( nodeLabelForPoint[pointI] == -1 ) + continue; + + pointType_[nodeLabelForPoint[pointI]] = NONE; + } + + for(iter=exchangeData.begin();iter!=exchangeData.end();++iter) + iter->second.clear(); + + //- start creating global-to-local addressing + //- find the starting point labels + label startPoint(0), nLocalPoints(0), nSharedPoints(0); + + //- count the number of points at processor boundaries + forAllConstIter(Map<label>, globalToLocalPointAddressing, it) + { + const label pI = it(); + + if( nodeLabelForPoint[pI] == -1 ) + continue; + if( !(pointType_[nodeLabelForPoint[pI]] & useType) ) + continue; + + ++nSharedPoints; + + label pMin(Pstream::myProcNo()); + forAllRow(pAtProcs, pI, procI) + pMin = Foam::min(pMin, pAtProcs(pI, procI)); + + if( pMin == Pstream::myProcNo() ) + ++nLocalPoints; + } + + labelList nPointsAtProc(Pstream::nProcs()); + nSharedPoints -= nLocalPoints; + nPointsAtProc[Pstream::myProcNo()] = pts.size() - nSharedPoints; + Pstream::gatherList(nPointsAtProc); + Pstream::scatterList(nPointsAtProc); + + for(label i=0;i<Pstream::myProcNo();++i) + startPoint += nPointsAtProc[i]; + + //- create global labels for points at processor boundaries + forAllConstIter(Map<label>, globalToLocalPointAddressing, it) + { + const label pI = it(); + + if( nodeLabelForPoint[pI] == -1 ) + continue; + + const label pLabel = nodeLabelForPoint[pI]; + + if( !(pointType_[pLabel] & useType) ) + continue; + + label pMin(Pstream::myProcNo()); + forAllRow(pAtProcs, pI, procI) + { + const label neiProc = pAtProcs(pI, procI); + pProcs.append(pLabel, neiProc); + pMin = Foam::min(pMin, neiProc); + } + + if( pMin != Pstream::myProcNo() ) + continue; + + globalPointLabel[pLabel] = startPoint++; + + forAllRow(pAtProcs, pI, procI) + { + const label neiProc = pAtProcs(pI, procI); + + if( neiProc == Pstream::myProcNo() ) + continue; + + //- the following information is sent to other processor + //- 1. global point label in the original mesh + //- 2. global point label in the tet mesh + exchangeData[neiProc].append(it.key()); + exchangeData[neiProc].append(globalPointLabel[pLabel]); + } + } + + //- exchange data with other processors + receivedData.clear(); + help::exchangeMap(exchangeData, receivedData); + + label counter(0); + while( counter < receivedData.size() ) + { + const label gpI = receivedData[counter++]; + const label tgI = receivedData[counter++]; + const label pLabel = + nodeLabelForPoint[globalToLocalPointAddressing[gpI]]; + + globalPointLabel[pLabel] = tgI; + } + + //- set global labels for remaining points + forAll(globalPointLabel, pI) + { + if( globalPointLabel[pI] == -1 ) + globalPointLabel[pI] = startPoint++; + } + + //- create global to local mapping + forAll(globalPointLabel, pI) + { + if( pProcs.sizeOfRow(pI) != 0 ) + { + pAtParallelBoundaries.append(pI); + globalToLocal.insert(globalPointLabel[pI], pI); + } + } + + //- mark vertices at parallel boundaries + forAll(pointType_, pI) + if( (pointType_[pI] & useType) && (pProcs.sizeOfRow(pI) != 0) ) + pointType_[pI] |= PARALLELBOUNDARY; + + //- create neighbour processors addressing + if( !neiProcsPtr_ ) + neiProcsPtr_ = new DynList<label>(); + DynList<label>& neiProcs = *neiProcsPtr_; + + for(iter=exchangeData.begin();iter!=exchangeData.end();++iter) + neiProcs.append(iter->first); +} + +void partTriMesh::createBufferLayers() +{ + pointField& pts = triSurfModifier(surf_).pointsAccess(); + + VRWGraph& pProcs = *pAtProcsPtr_; + labelLongList& globalPointLabel = *globalPointLabelPtr_; + Map<label>& globalToLocal = *globalToLocalPointAddressingPtr_; + const DynList<label>& neiProcs = *this->neiProcsPtr_; + + if( !pAtBufferLayersPtr_ ) + pAtBufferLayersPtr_ = new labelLongList(); + labelLongList& pAtBufferLayers = *pAtBufferLayersPtr_; + pAtBufferLayers.clear(); + + //- create the map + std::map<label, LongList<parTriFace> > exchangeTrias; + forAll(neiProcs, procI) + exchangeTrias.insert + ( + std::make_pair(neiProcs[procI], LongList<parTriFace>()) + ); + + //- go through the tets and add the ones having vertices at parallel + //- boundaries for sending + forAll(surf_, triI) + { + const labelledTri& pt = surf_[triI]; + + DynList<label> sendToProcs; + forAll(pt, i) + { + const label pLabel = pt[i]; + + if( pointType_[pLabel] & PARALLELBOUNDARY ) + { + forAllRow(pProcs, pLabel, i) + { + const label neiProc = pProcs(pLabel, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + sendToProcs.appendIfNotIn(neiProc); + } + } + } + + if( sendToProcs.size() ) + { + const parTriFace tri + ( + globalPointLabel[pt[0]], + globalPointLabel[pt[1]], + globalPointLabel[pt[2]], + triangle<point, point>(pts[pt[0]], pts[pt[1]], pts[pt[2]]) + ); + + forAll(sendToProcs, i) + { + exchangeTrias[sendToProcs[i]].append(tri); + + forAll(pt, j) + { + if( pProcs.sizeOfRow(pt[j]) == 0 ) + pAtBufferLayers.append(pt[j]); + + pProcs.appendIfNotIn(pt[j], sendToProcs[i]); + } + } + } + } + + LongList<parTriFace> receivedTrias; + help::exchangeMap(exchangeTrias, receivedTrias); + exchangeTrias.clear(); + + Map<label> newGlobalToLocal; + std::map<label, point> addCoordinates; + label nPoints = pts.size(); + forAll(receivedTrias, i) + { + const parTriFace& tri = receivedTrias[i]; + + DynList<label, 3> triPointLabels; + for(label j=0;j<3;++j) + { + const label gpI = tri.globalLabelOfPoint(j); + + if( globalToLocal.found(gpI) ) + { + const label pI = globalToLocal[gpI]; + triPointLabels.append(pI); + } + else if( newGlobalToLocal.found(gpI) ) + { + triPointLabels.append(newGlobalToLocal[gpI]); + } + else + { + newGlobalToLocal.insert(gpI, nPoints); + triPointLabels.append(nPoints); + + point tp; + if( j == 0 ) + { + tp = tri.trianglePoints().a(); + } + else if( j == 1 ) + { + tp = tri.trianglePoints().b(); + } + else + { + tp = tri.trianglePoints().c(); + } + addCoordinates[nPoints] = tp; + ++nPoints; + + pointLabelInMeshSurface_.append(-1); + pointType_.append(NONE); + + DynList<label> helper; + helper.append(surf_.size()); + + globalPointLabel.append(gpI); + helper[0] = Pstream::myProcNo(); + pProcs.appendList(helper); + } + } + + //- append tet + surf_.appendTriangle + ( + labelledTri + ( + triPointLabels[0], + triPointLabels[1], + triPointLabels[2], + -1 + ) + ); + } + + //- store newly added points + pts.setSize(nPoints); + for + ( + std::map<label, point>::const_iterator it=addCoordinates.begin(); + it!=addCoordinates.end(); + ++it + ) + pts[it->first] = it->second; + + addCoordinates.clear(); + + //- insert the global labels of the buffer points + //- into the globalToLocal map + forAllConstIter(Map<label>, newGlobalToLocal, it) + globalToLocal.insert(it.key(), it()); + + //- update addressing of the surface mesh + surf_.clearAddressing(); +} + +void partTriMesh::updateBufferLayers() +{ + const pointField& points = surf_.points(); + const labelLongList& bufferLayerPoints = this->bufferLayerPoints(); + const VRWGraph& pProcs = this->pointAtProcs(); + const labelLongList& globalPointLabel = this->globalPointLabel(); + const Map<label>& globalToLocal = this->globalToLocalPointAddressing(); + const DynList<label>& neiProcs = this->neiProcs(); + + //- create the map + std::map<label, LongList<labelledPoint> > exchangeData; + forAll(neiProcs, i) + exchangeData.insert + ( + std::make_pair(neiProcs[i], LongList<labelledPoint>()) + ); + + //- add points into the map + forAll(bufferLayerPoints, pI) + { + const label pointI = bufferLayerPoints[pI]; + + forAllRow(pProcs, pointI, i) + { + const label neiProc = pProcs(pointI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelledPoint(globalPointLabel[pointI], points[pointI]) + ); + } + } + + LongList<labelledPoint> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelledPoint& lp = receivedData[i]; + + this->updateVertex + ( + globalToLocal[lp.pointLabel()], + lp.coordinates() + ); + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/partTriMesh/partTriMeshSimplex.C b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshSimplex.C new file mode 100644 index 0000000000000000000000000000000000000000..352c2abd22ced2862ca923536613110da060fea6 --- /dev/null +++ b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshSimplex.C @@ -0,0 +1,144 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "Map.H" +#include "partTriMeshSimplex.H" + +//#define DEBUGSmooth + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +partTriMeshSimplex::partTriMeshSimplex +( + const partTriMesh& tm, + const label pI +) +: + pts_(), + trias_() +{ + const pointField& points = tm.points(); + const LongList<labelledTri>& trias = tm.triangles(); + const VRWGraph& pt = tm.pointTriangles(); + + trias_.setSize(pt.sizeOfRow(pI)); + label counter(0); + + Map<label> addr(2*pt.sizeOfRow(pI)); + forAllRow(pt, pI, tI) + { + const labelledTri& tri = trias[pt(pI, tI)]; + for(label i=0;i<3;++i) + { + const label tpI = tri[i]; + + if( !addr.found(tpI) ) + { + addr.insert(tpI, counter); + pts_.append(points[tpI]); + ++counter; + } + } + + # ifdef DEBUGSmooth + Info << "Tet " << tetI << " is " << tet << endl; + # endif + + label pos(-1); + for(label i=0;i<3;++i) + if( tri[i] == pI ) + { + pos = i; + break; + } + + switch( pos ) + { + case 0: + { + trias_[tI] = triFace(addr[tri[0]], addr[tri[1]], addr[tri[2]]); + } break; + case 1: + { + trias_[tI] = triFace(addr[tri[1]], addr[tri[2]], addr[tri[0]]); + } break; + case 2: + { + trias_[tI] = triFace(addr[tri[2]], addr[tri[0]], addr[tri[1]]); + } break; + default: + { + FatalErrorIn + ( + "partTriMeshSimplex::partTriMeshSimplex(" + "(const partTriMesh& tm, const label pI)" + ) << "Point " << pI << " is not present in triangle" << tri + << abort(FatalError); + } + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +partTriMeshSimplex::~partTriMeshSimplex() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +vector partTriMeshSimplex::normal() const +{ + vector normal(vector::zero); + scalar magN(0.0); + + forAll(trias_, tI) + { + const triFace& t = trias_[tI]; + + vector n + ( + 0.5 * ((pts_[t[1]] - pts_[t[0]]) ^ (pts_[t[2]] - pts_[t[0]])) + ); + const scalar magn = mag(n); + + normal += n; + magN += magn; + } + + return (normal / (magN + VSMALL)); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/partTriMesh/partTriMeshSimplex.H b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshSimplex.H new file mode 100644 index 0000000000000000000000000000000000000000..d91849fe8d7c7308218baa67227dc6ac38481d1a --- /dev/null +++ b/meshLibrary/utilities/meshes/partTriMesh/partTriMeshSimplex.H @@ -0,0 +1,108 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + partTriMeshSimplex + +Description + A simplex which is used for smoothing purposes + +SourceFiles + + +\*---------------------------------------------------------------------------*/ + +#ifndef partTriMeshSimplex_H +#define partTriMeshSimplex_H + +#include "partTriMesh.H" +#include "triFace.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class partTriMesh; + +/*---------------------------------------------------------------------------*\ + Class partTriMeshSimplex Declaration +\*---------------------------------------------------------------------------*/ + +class partTriMeshSimplex +{ + // Private data + //- points making the simplex + DynList<point, 32> pts_; + + //- triangles making the simplex + DynList<triFace, 32> trias_; + + public: + + // Constructors + //- Construct from partTriMesh and point label + partTriMeshSimplex(const partTriMesh& tm, const label pI); + + // Destructor + ~partTriMeshSimplex(); + + // Member functions + //- return points + inline DynList<point, 32>& pts() + { + return pts_; + } + + //- return points + inline const DynList<point, 32>& pts() const + { + return pts_; + } + + //- return triangles + inline const DynList<triFace, 32>& triangles() const + { + return trias_; + } + + //- return centre point coordinates + inline const point& centrePoint() const + { + return pts_[trias_[0][0]]; + } + + //- return the normal of the simplex + vector normal() const; +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatch.C b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatch.C similarity index 61% rename from meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatch.C rename to meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatch.C index 2789aa3ab1ddb4d78702dcd3b930bdf9a777986a..c9a08e84d13a7cacb248eeb595c57c1a4543efe4 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatch.C +++ b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatch.C @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ -#include "writePatch.H" +#include "boundaryPatch.H" #include "Ostream.H" #include "Istream.H" #include "token.H" @@ -38,12 +37,12 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -defineTypeNameAndDebug(writePatch, 0); -addToRunTimeSelectionTable(writePatchBase, writePatch, dictionary); +defineTypeNameAndDebug(boundaryPatch, 0); +addToRunTimeSelectionTable(boundaryPatchBase, boundaryPatch, dictionary); // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -writePatch::writePatch +boundaryPatch::boundaryPatch ( const word& n, const word& t, @@ -51,22 +50,22 @@ writePatch::writePatch const label sF ) : - writePatchBase(n, t, nF, sF) + boundaryPatchBase(n, t, nF, sF) {} -writePatch::writePatch(const word& name, const dictionary& dict) +boundaryPatch::boundaryPatch(const word& name, const dictionary& dict) : - writePatchBase(name, dict) + boundaryPatchBase(name, dict) { } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -dictionary writePatch::dict() const +dictionary boundaryPatch::dict() const { dictionary dict; - dict.add("type", type_); + dict.add("type", type_); dict.add("nFaces", nFaces_); dict.add("startFace", startFace_); @@ -74,17 +73,17 @@ dictionary writePatch::dict() const return dict; } -void writePatch::write(Ostream& os) const +void boundaryPatch::write(Ostream& os) const { this->operator<<(os); } -void writePatch::writeDict(Ostream& os) const +void boundaryPatch::writeDict(Ostream& os) const { } -Ostream& writePatch::operator<<(Ostream& os) const +Ostream& boundaryPatch::operator<<(Ostream& os) const { os << name_ << nl << token::BEGIN_BLOCK << nl << " type " << type_ << token::END_STATEMENT << nl @@ -95,19 +94,19 @@ Ostream& writePatch::operator<<(Ostream& os) const return os; } -Istream& writePatch::operator>>(Istream& is) +Istream& boundaryPatch::operator>>(Istream& is) { - token t; - is >> name_ >> t; - is >> t >> type_ >> t; - is >> t >> nFaces_ >> t; - is >> t >> startFace_ >> t; - is >> t; + token t; + is >> name_ >> t; + is >> t >> type_ >> t; + is >> t >> nFaces_ >> t; + is >> t >> startFace_ >> t; + is >> t; return is; } -void writePatch::operator=(const writePatch& wp) +void boundaryPatch::operator=(const boundaryPatch& wp) { name_ = wp.name_; type_ = wp.type_; @@ -115,7 +114,7 @@ void writePatch::operator=(const writePatch& wp) startFace_ = wp.startFace_; } -bool writePatch::operator!=(const writePatch& wp) const +bool boundaryPatch::operator!=(const boundaryPatch& wp) const { if( name_ != wp.name_ ) { diff --git a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatch.H b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatch.H similarity index 59% rename from meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatch.H rename to meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatch.H index 1b5bd53ae9b39af3f8b731661343f31416a35e6d..10546b803d7dec4262d5e3d7d5187d56988484be 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatch.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatch.H @@ -1,44 +1,43 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class - writePatch + boundaryPatch Description Writes information for a given boundary patch SourceFiles - writePatch.C + boundaryPatch.C \*---------------------------------------------------------------------------*/ -#ifndef writePatch_H -#define writePatch_H +#ifndef boundaryPatch_H +#define boundaryPatch_H // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -#include "writePatchBase.H" +#include "boundaryPatchBase.H" #include "typeInfo.H" namespace Foam @@ -46,18 +45,18 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -class writePatch -: public writePatchBase +class boundaryPatch +: public boundaryPatchBase { public: - + //- Runtime type information TypeName("patch"); // Constructors - - writePatch + + boundaryPatch ( const word&, const word&, @@ -65,56 +64,56 @@ public: const label ); - writePatch(const word& name, const dictionary&); + boundaryPatch(const word& name, const dictionary&); // Return clone of the object - virtual autoPtr<writePatchBase> clone() const + virtual autoPtr<boundaryPatchBase> clone() const { - return autoPtr<writePatchBase> - ( - new writePatch - ( - patchName(), + return autoPtr<boundaryPatchBase> + ( + new boundaryPatch + ( + patchName(), patchType(), patchSize(), patchStart() - ) - ); + ) + ); } - - virtual autoPtr<writePatchBase> clone(const writePatch& wp) const + + virtual autoPtr<boundaryPatchBase> clone(const boundaryPatch& wp) const { - return autoPtr<writePatchBase> - ( - new writePatch - ( - wp.patchName(), + return autoPtr<boundaryPatchBase> + ( + new boundaryPatch + ( + wp.patchName(), wp.patchType(), wp.patchSize(), wp.patchStart() - ) - ); + ) + ); } - + //- Return as dictionary of entries dictionary dict() const; - + // Write //- write to Ostream void write(Ostream&) const; //- Write dictionary void writeDict(Ostream&) const; - + // Member operators - + Ostream& operator<<(Ostream&) const; - + Istream& operator>>(Istream&); - - void operator=(const writePatch&); - - bool operator!=(const writePatch&) const; + + void operator=(const boundaryPatch&); + + bool operator!=(const boundaryPatch&) const; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatchBase.C b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatchBase.C similarity index 64% rename from meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatchBase.C rename to meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatchBase.C index a53cb27a1b15b6b5272c48b20d933332a09e3496..d83f323f031aade12fb495f4513d54dc9d611888 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatchBase.C +++ b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatchBase.C @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ -#include "writePatchBase.H" +#include "boundaryPatchBase.H" #include "Ostream.H" #include "Istream.H" #include "token.H" @@ -40,17 +39,17 @@ namespace Foam defineTemplateTypeNameAndDebugWithName ( - IOPtrList<writePatchBase>, - "polyBoundaryMesh", - 0 + IOPtrList<boundaryPatchBase>, + "polyBoundaryMesh", + 0 ); -defineTypeNameAndDebug(writePatchBase, 0); -defineRunTimeSelectionTable(writePatchBase, dictionary); +defineTypeNameAndDebug(boundaryPatchBase, 0); +defineRunTimeSelectionTable(boundaryPatchBase, dictionary); // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -autoPtr<writePatchBase> writePatchBase::New +autoPtr<boundaryPatchBase> boundaryPatchBase::New ( const word& name, const dictionary& dict @@ -69,19 +68,19 @@ autoPtr<writePatchBase> writePatchBase::New { FatalIOErrorIn ( - "writePatchBase::New(const word&, const dictionary&)", + "boundaryPatchBase::New(const word&, const dictionary&)", dict - ) << "Unknown writePatchBase type " << type << nl << nl - << "Valid writePatchBase types are :" << nl + ) << "Unknown boundaryPatchBase type " << type << nl << nl + << "Valid boundaryPatchBase types are :" << nl << "[default: " << typeName_() << "]" << dictionaryConstructorTablePtr_->toc() << exit(FatalIOError); } - return autoPtr<writePatchBase>(cstrIter()(name, dict)); + return autoPtr<boundaryPatchBase>(cstrIter()(name, dict)); } -autoPtr<writePatchBase> writePatchBase::New +autoPtr<boundaryPatchBase> boundaryPatchBase::New ( Istream& is ) @@ -89,12 +88,12 @@ autoPtr<writePatchBase> writePatchBase::New word name(is); dictionary dict(is); - return writePatchBase::New(name, dict); + return boundaryPatchBase::New(name, dict); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -writePatchBase::writePatchBase +boundaryPatchBase::boundaryPatchBase ( const word& n, const word& t, @@ -108,7 +107,7 @@ writePatchBase::writePatchBase startFace_(sF) {} -writePatchBase::writePatchBase(const word& name, const dictionary& dict) +boundaryPatchBase::boundaryPatchBase(const word& name, const dictionary& dict) : name_(name), type_(), @@ -123,10 +122,10 @@ writePatchBase::writePatchBase(const word& name, const dictionary& dict) // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -Ostream& operator<<(Ostream& os, const writePatchBase& wpb) +Ostream& operator<<(Ostream& os, const boundaryPatchBase& wpb) { wpb.write(os); - os.check("Ostream& operator<<(Ostream& f, const writePatchBase& wpb"); + os.check("Ostream& operator<<(Ostream& f, const boundaryPatchBase& wpb"); return os; } diff --git a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatchBase.H b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatchBase.H similarity index 72% rename from meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatchBase.H rename to meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatchBase.H index 5fa92e7241e5369d835a1b51bd920af579467978..0da29bc5338bbc03a029389ef1a79e608a662441 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writePatchBase.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/boundaryPatchBase.H @@ -1,40 +1,39 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class - writePatchBase + boundaryPatchBase Description Writes information for a given boundary patch SourceFiles - writePatchBase.C + boundaryPatchBase.C \*---------------------------------------------------------------------------*/ -#ifndef writePatchBase_H -#define writePatchBase_H +#ifndef boundaryPatchBase_H +#define boundaryPatchBase_H // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -49,7 +48,7 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -class writePatchBase +class boundaryPatchBase { protected: @@ -65,11 +64,11 @@ protected: public: //- Runtime type information - TypeName("writePatchBase"); + TypeName("boundaryPatchBase"); // Constructors - writePatchBase + boundaryPatchBase ( const word&, const word&, @@ -77,11 +76,11 @@ public: const label ); - writePatchBase(const word& name, const dictionary&); + boundaryPatchBase(const word& name, const dictionary&); // Destructor - virtual ~writePatchBase() + virtual ~boundaryPatchBase() {} // Declare run-time constructor selection table @@ -89,7 +88,7 @@ public: declareRunTimeSelectionTable ( autoPtr, - writePatchBase, + boundaryPatchBase, dictionary, ( const word& name, @@ -100,20 +99,20 @@ public: // Selectors - static autoPtr<writePatchBase> New + static autoPtr<boundaryPatchBase> New ( const word& name, const dictionary& dict ); - static autoPtr<writePatchBase> New + static autoPtr<boundaryPatchBase> New ( Istream& ); // Construct and return a clone - autoPtr<writePatchBase> clone() const + autoPtr<boundaryPatchBase> clone() const { return New ( @@ -134,11 +133,11 @@ public: { return name_; } - - inline word& patchName() - { - return name_; - } + + inline word& patchName() + { + return name_; + } inline const word& patchType() const { @@ -174,10 +173,10 @@ public: virtual dictionary dict() const = 0; // Member operators - friend Ostream& operator<<(Ostream&, const writePatchBase&); + friend Ostream& operator<<(Ostream&, const boundaryPatchBase&); virtual Istream& operator>>(Istream&) = 0; - //virtual void operator=(const writePatchBase&) = 0; - //virtual bool operator!=(const writePatchBase&) const = 0; + //virtual void operator=(const boundaryPatchBase&) = 0; + //virtual bool operator!=(const boundaryPatchBase&) const = 0; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writeProcessorPatch.C b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/processorBoundaryPatch.C similarity index 65% rename from meshLibrary/utilities/meshes/polyMeshGen/writePatch/writeProcessorPatch.C rename to meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/processorBoundaryPatch.C index d9271201ee008a5f0ed99a4f9bd4548a24769ce7..80e53576f8830273b18604215f4a1fbdf9b100bc 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writeProcessorPatch.C +++ b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/processorBoundaryPatch.C @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ -#include "writeProcessorPatch.H" +#include "processorBoundaryPatch.H" #include "addToRunTimeSelectionTable.H" #include "dictionary.H" #include "Ostream.H" @@ -38,12 +37,12 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -defineTypeNameAndDebug(writeProcessorPatch, 0); -addToRunTimeSelectionTable(writePatchBase, writeProcessorPatch, dictionary); +defineTypeNameAndDebug(processorBoundaryPatch, 0); +addToRunTimeSelectionTable(boundaryPatchBase, processorBoundaryPatch, dictionary); // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -writeProcessorPatch::writeProcessorPatch +processorBoundaryPatch::processorBoundaryPatch ( const word& name, const word& type, @@ -53,18 +52,18 @@ writeProcessorPatch::writeProcessorPatch const label neighbProcNo ) : - writePatchBase(name, type, nFaces, startFace), + boundaryPatchBase(name, type, nFaces, startFace), myProcNo_(myProcNo), neighbProcNo_(neighbProcNo) {} -writeProcessorPatch::writeProcessorPatch +processorBoundaryPatch::processorBoundaryPatch ( const word& name, const dictionary& dict ) : - writePatchBase(name, dict), + boundaryPatchBase(name, dict), myProcNo_(readLabel(dict.lookup("myProcNo"))), neighbProcNo_(readLabel(dict.lookup("neighbProcNo"))) { @@ -72,31 +71,31 @@ writeProcessorPatch::writeProcessorPatch // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -dictionary writeProcessorPatch::dict() const +dictionary processorBoundaryPatch::dict() const { dictionary dict; - dict.add("type", type_); + dict.add("type", type_); dict.add("nFaces", nFaces_); dict.add("startFace", startFace_); - dict.add("myProcNo", myProcNo_); - dict.add("neighbProcNo", neighbProcNo_); + dict.add("myProcNo", myProcNo_); + dict.add("neighbProcNo", neighbProcNo_); return dict; } -void writeProcessorPatch::write(Ostream& os) const +void processorBoundaryPatch::write(Ostream& os) const { this->operator<<(os); } -void writeProcessorPatch::writeDict(Ostream& os) const +void processorBoundaryPatch::writeDict(Ostream& os) const { } -Ostream& writeProcessorPatch::operator<<(Ostream& os) const +Ostream& processorBoundaryPatch::operator<<(Ostream& os) const { os << patchName() << nl << token::BEGIN_BLOCK << nl << " type " << patchType() << token::END_STATEMENT << nl @@ -110,21 +109,21 @@ Ostream& writeProcessorPatch::operator<<(Ostream& os) const return os; } -Istream& writeProcessorPatch::operator>>(Istream& is) +Istream& processorBoundaryPatch::operator>>(Istream& is) { - token t; - is >> name_ >> t; - is >> t >> type_ >> t; - is >> t >> nFaces_ >> t; - is >> t >> startFace_ >> t; + token t; + is >> name_ >> t; + is >> t >> type_ >> t; + is >> t >> nFaces_ >> t; + is >> t >> startFace_ >> t; is >> t >> myProcNo_ >> t; is >> t >> neighbProcNo_ >> t; - is >> t; + is >> t; return is; } -void writeProcessorPatch::operator=(const writeProcessorPatch& wp) +void processorBoundaryPatch::operator=(const processorBoundaryPatch& wp) { name_ = wp.name_; type_ = wp.type_; @@ -134,7 +133,7 @@ void writeProcessorPatch::operator=(const writeProcessorPatch& wp) neighbProcNo_ = wp.neighbProcNo_; } -bool writeProcessorPatch::operator!=(const writeProcessorPatch& wp) const +bool processorBoundaryPatch::operator!=(const processorBoundaryPatch& wp) const { if( name_ != wp.name_ ) { diff --git a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writeProcessorPatch.H b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/processorBoundaryPatch.H similarity index 64% rename from meshLibrary/utilities/meshes/polyMeshGen/writePatch/writeProcessorPatch.H rename to meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/processorBoundaryPatch.H index cc0924be673896550c4ad4279b2e92fde5bd3315..890544efbe32aba5688d2cdf2be9cef7d4a69f37 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/writePatch/writeProcessorPatch.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/boundaryPatch/processorBoundaryPatch.H @@ -1,44 +1,43 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class - writeProcessorPatch + processorBoundaryPatch Description Writes information for a given processor patch SourceFiles - writeProcessorPatch.C + processorBoundaryPatch.C \*---------------------------------------------------------------------------*/ -#ifndef writeProcessorPatch_H -#define writeProcessorPatch_H +#ifndef processorBoundaryPatch_H +#define processorBoundaryPatch_H // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -#include "writePatchBase.H" +#include "boundaryPatchBase.H" #include "typeInfo.H" namespace Foam @@ -46,22 +45,22 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -class writeProcessorPatch -: public writePatchBase +class processorBoundaryPatch +: public boundaryPatchBase { // private data - + label myProcNo_; - + label neighbProcNo_; public: - - //- Runtime type information - TypeName("processor"); + + // Runtime type information + TypeName("processor"); // Construct from components - writeProcessorPatch + processorBoundaryPatch ( const word& name, const word& type, @@ -71,69 +70,69 @@ public: const label neighbProcNo ); - writeProcessorPatch(const word& name, const dictionary&); + processorBoundaryPatch(const word& name, const dictionary&); // Construct and return a clone - virtual autoPtr<writePatchBase> clone() const + virtual autoPtr<boundaryPatchBase> clone() const { - return autoPtr<writePatchBase> - ( - new writeProcessorPatch - ( - patchName(), + return autoPtr<boundaryPatchBase> + ( + new processorBoundaryPatch + ( + patchName(), patchType(), patchSize(), patchStart(), myProcNo_, neighbProcNo_ - ) - ); + ) + ); } - virtual autoPtr<writePatchBase> clone - ( - const writeProcessorPatch& pp - ) const + virtual autoPtr<boundaryPatchBase> clone + ( + const processorBoundaryPatch& pp + ) const { - return autoPtr<writePatchBase> - ( - new writeProcessorPatch - ( - pp.patchName(), + return autoPtr<boundaryPatchBase> + ( + new processorBoundaryPatch + ( + pp.patchName(), pp.patchType(), pp.patchSize(), pp.patchStart(), pp.myProcNo_, pp.neighbProcNo_ - ) - ); + ) + ); } - + // Member functions //- return the owner processor inline label myProcNo() const { return myProcNo_; } - + //- return the neighbour processor inline label neiProcNo() const { return neighbProcNo_; } - + //- check if the processor is the owner of the interface inline bool owner() const { if( myProcNo_ < neighbProcNo_ ) return true; - + return false; } - + //- Return as dictionary of entries dictionary dict() const; - + // Write //- write to Ostream void write(Ostream&) const; @@ -143,12 +142,12 @@ public: // Member operators Ostream& operator<<(Ostream&) const; - + Istream& operator>>(Istream&); - - void operator=(const writeProcessorPatch&); - - bool operator!=(const writeProcessorPatch&) const; + + void operator=(const processorBoundaryPatch&); + + bool operator!=(const processorBoundaryPatch&) const; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.C b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.C index 1b7b4ef267df0f20da3d3cd26af6d1a30135c5b9..1cf7d7216a83f4ddec8a09ea3b2a5361f7d99525 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.C +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -28,17 +27,18 @@ Description #include "polyMeshGen.H" #include "demandDrivenData.H" +#include "OFstream.H" namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // polyMeshGen::polyMeshGen(const Time& t) : - polyMeshGenCells(t) -{ -} + polyMeshGenCells(t), + metaDict_() +{} //- Construct from components without the boundary polyMeshGen::polyMeshGen @@ -49,9 +49,9 @@ polyMeshGen::polyMeshGen const cellList& cells ) : - polyMeshGenCells(t, points, faces, cells) -{ -} + polyMeshGenCells(t, points, faces, cells), + metaDict_() +{} //- Construct from components with the boundary polyMeshGen::polyMeshGen @@ -74,26 +74,81 @@ polyMeshGen::polyMeshGen patchNames, patchStart, nFacesInPatch - ) -{ -} - + ), + metaDict_() +{} + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Destructor polyMeshGen::~polyMeshGen() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void polyMeshGen::read() { polyMeshGenCells::read(); + + metaDict_ = + IOdictionary + ( + IOobject + ( + "meshMetaDict", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::READ_IF_PRESENT, + IOobject::NO_WRITE + ) + ); } void polyMeshGen::write() const { + //- remove old mesh before writting + const fileName meshDir = runTime_.path()/runTime_.constant()/"polyMesh"; + + rm(meshDir/"points"); + rm(meshDir/"faces"); + rm(meshDir/"owner"); + rm(meshDir/"neighbour"); + rm(meshDir/"cells"); + rm(meshDir/"boundary"); + rm(meshDir/"pointZones"); + rm(meshDir/"faceZones"); + rm(meshDir/"cellZones"); + rm(meshDir/"meshModifiers"); + rm(meshDir/"parallelData"); + rm(meshDir/"meshMetaDict"); + + // remove sets if they exist + if (isDir(meshDir/"sets")) + { + rmDir(meshDir/"sets"); + } + + //- write the mesh polyMeshGenCells::write(); + + //- write meta data + OFstream fName(meshDir/"meshMetaDict"); + IOdictionary writeMeta + ( + IOobject + ( + "meshMetaDict", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::NO_READ, + IOobject::AUTO_WRITE + ), + metaDict_ + ); + + writeMeta.writeHeader(fName); + writeMeta.writeData(fName); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.H b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.H index ca0e3933f0de91532443373784e0d514ec102e1e..95b73bac012c0e4f91c85ccfee253e6cfef7619c 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGen.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGen @@ -38,6 +37,7 @@ SourceFiles // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // #include "polyMeshGenCells.H" +#include "dictionary.H" namespace Foam { @@ -47,37 +47,54 @@ namespace Foam class polyMeshGen : public polyMeshGenCells { + // Private data + //- meta data about the meshing process + dictionary metaDict_; + public: // Constructors - //- Null constructor - polyMeshGen(const Time& t); - - //- Construct from components without the boundary - polyMeshGen - ( - const Time& t, - const pointField& points, - const faceList& faces, - const cellList& cells - ); - - //- Construct from components with the boundary - polyMeshGen - ( - const Time& t, - const pointField& points, - const faceList& faces, - const cellList& cells, - const wordList& patchNames, - const labelList& patchStart, - const labelList& nFacesInPatch - ); + //- Null constructor + polyMeshGen(const Time& t); + + //- Construct from components without the boundary + polyMeshGen + ( + const Time& t, + const pointField& points, + const faceList& faces, + const cellList& cells + ); + + //- Construct from components with the boundary + polyMeshGen + ( + const Time& t, + const pointField& points, + const faceList& faces, + const cellList& cells, + const wordList& patchNames, + const labelList& patchStart, + const labelList& nFacesInPatch + ); // Destructor ~polyMeshGen(); + // Public member functions + //- return a constant reference to metaDict + inline const dictionary& metaData() const + { + return metaDict_; + } + + //- return a reference to metaDict + inline dictionary& metaData() + { + return metaDict_; + } + // Read mesh void read(); diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.C b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.C index 7de4bbd12584857b25915121b48af3c9a78b149a..b84b722bd5abf890cc83179587be3c4439618ff5 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,10 @@ Description #include "demandDrivenData.H" #include "labelPair.H" + +# ifdef USE_OMP #include <omp.h> +# endif namespace Foam { @@ -81,16 +83,28 @@ void polyMeshGenCells::calculateOwnersAndNeighbours() const //- start calculating owners and neighbours nIntFaces_ = 0; + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); const label chunkSize = faces_.size() / nThreads + 1; + # else + const label nThreads = 1; + const label chunkSize = faces_.size(); + # endif label nInternalFaces(0); List<List<LongList<labelPair> > > dataForOtherThreads(nThreads); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) reduction(+ : nInternalFaces) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif + const label startingFace = threadI * chunkSize; const label endFace = Foam::min(startingFace + chunkSize, faces_.size()); @@ -104,7 +118,9 @@ void polyMeshGenCells::calculateOwnersAndNeighbours() const nei[faceI] = -1; } + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(cells_, cellI) { const cell& c = cells_[cellI]; @@ -148,10 +164,11 @@ void polyMeshGenCells::calculateOwnersAndNeighbours() const } } + # ifdef USE_OMP # pragma omp barrier # pragma omp critical - + # endif for(label i=0;i<nThreads;++i) { const LongList<labelPair>& data = @@ -218,7 +235,18 @@ void polyMeshGenCells::calculateOwnersAndNeighbours() const void polyMeshGenCells::calculateAddressingData() const { if( !ownerPtr_ || !neighbourPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline label polyMeshGenCells::calculateAddressingData() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calculateOwnersAndNeighbours(); + } addressingDataPtr_ = new polyMeshGenAddressing(*this); } @@ -299,7 +327,18 @@ polyMeshGenCells::~polyMeshGenCells() const polyMeshGenAddressing& polyMeshGenCells::addressingData() const { if( !addressingDataPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline label polyMeshGenCells::addressingData() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calculateAddressingData(); + } return *addressingDataPtr_; } @@ -452,7 +491,7 @@ void polyMeshGenCells::write() const ) ); - labelListPMG containedElements; + labelLongList containedElements; setIt->second.containedElements(containedElements); forAll(containedElements, i) diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.H b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.H index ca41d6b8b4b8f337d05dbaa5358f700ff96fd54d..8df85305c2d81048707e10bb858a869e60652237 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCells.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenCells diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCellsI.H b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCellsI.H index d9ed2c54400a209b545bf111857ef8dbdc416c16..71cfc879cd8605fdabc4064b4b4873adac68e8e6 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCellsI.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenCellsI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.C b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.C index 4f53cc86e808f6e42874c7bc7ce42b280a2e87e4..ec82091d99cd0a2188899139d6cc26ef19bf6b19 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.C +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,94 +39,94 @@ namespace Foam void polyMeshGenFaces::clearOut() const { - deleteDemandDrivenData(ownerPtr_); - deleteDemandDrivenData(neighbourPtr_); + deleteDemandDrivenData(ownerPtr_); + deleteDemandDrivenData(neighbourPtr_); } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Constructors //- Null constructor polyMeshGenFaces::polyMeshGenFaces(const Time& runTime) : - polyMeshGenPoints(runTime), - faces_ - ( - IOobject - ( - "faces", - runTime.constant(), - "polyMesh", - runTime - ), - 0 - ), + polyMeshGenPoints(runTime), + faces_ + ( + IOobject + ( + "faces", + runTime.constant(), + "polyMesh", + runTime + ), + 0 + ), procBoundaries_(), - boundaries_(), + boundaries_(), faceSubsets_(), - nIntFaces_(0), - ownerPtr_(NULL), - neighbourPtr_(NULL) + nIntFaces_(0), + ownerPtr_(NULL), + neighbourPtr_(NULL) { } //- Construct from components without the boundary polyMeshGenFaces::polyMeshGenFaces ( - const Time& runTime, - const pointField& points, - const faceList& faces + const Time& runTime, + const pointField& points, + const faceList& faces ) : - polyMeshGenPoints(runTime, points), - faces_ - ( - IOobject - ( - "faces", - runTime.constant(), - "polyMesh", - runTime - ), - faces - ), + polyMeshGenPoints(runTime, points), + faces_ + ( + IOobject + ( + "faces", + runTime.constant(), + "polyMesh", + runTime + ), + faces + ), procBoundaries_(), - boundaries_(), + boundaries_(), faceSubsets_(), - nIntFaces_(0), - ownerPtr_(NULL), - neighbourPtr_(NULL) + nIntFaces_(0), + ownerPtr_(NULL), + neighbourPtr_(NULL) { } //- Construct from components with the boundary polyMeshGenFaces::polyMeshGenFaces ( - const Time& runTime, - const pointField& points, - const faceList& faces, - const wordList& patchNames, - const labelList& patchStart, - const labelList& nFacesInPatch + const Time& runTime, + const pointField& points, + const faceList& faces, + const wordList& patchNames, + const labelList& patchStart, + const labelList& nFacesInPatch ) : - polyMeshGenPoints(runTime, points), - faces_ - ( - IOobject - ( - "faces", - runTime.constant(), - "polyMesh", - runTime - ), - faces - ), + polyMeshGenPoints(runTime, points), + faces_ + ( + IOobject + ( + "faces", + runTime.constant(), + "polyMesh", + runTime + ), + faces + ), procBoundaries_(), - boundaries_(), + boundaries_(), faceSubsets_(), - nIntFaces_(0), - ownerPtr_(NULL), - neighbourPtr_(NULL) + nIntFaces_(0), + ownerPtr_(NULL), + neighbourPtr_(NULL) { if( Pstream::parRun() ) FatalErrorIn @@ -141,28 +140,28 @@ polyMeshGenFaces::polyMeshGenFaces "const labelList& nFacesInPatch)" ) << "Cannot do this in parallel!" << exit(FatalError); - boundaries_.setSize(patchNames.size()); - forAll(patchNames, patchI) - { - boundaries_.set - ( - patchI, - new writePatch - ( - patchNames[patchI], - "patch", - nFacesInPatch[patchI], - patchStart[patchI] - ) - ); - } + boundaries_.setSize(patchNames.size()); + forAll(patchNames, patchI) + { + boundaries_.set + ( + patchI, + new boundaryPatch + ( + patchNames[patchI], + "patch", + nFacesInPatch[patchI], + patchStart[patchI] + ) + ); + } } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Destructor polyMeshGenFaces::~polyMeshGenFaces() { - clearOut(); + clearOut(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -183,10 +182,10 @@ label polyMeshGenFaces::faceIsInProcPatch(const label faceLabel) const return -1; forAllReverse(procBoundaries_, patchI) - if( faceLabel >= procBoundaries_[patchI].patchStart() ) - return patchI; + if( faceLabel >= procBoundaries_[patchI].patchStart() ) + return patchI; - return -1; + return -1; } label polyMeshGenFaces::faceIsInPatch(const label faceLabel) const @@ -195,11 +194,11 @@ label polyMeshGenFaces::faceIsInPatch(const label faceLabel) const if( faceLabel >= (boundaries_[i].patchStart()+boundaries_[i].patchSize()) ) return -1; - forAllReverse(boundaries_, patchI) - if( faceLabel >= boundaries_[patchI].patchStart() ) - return patchI; + forAllReverse(boundaries_, patchI) + if( faceLabel >= boundaries_[patchI].patchStart() ) + return patchI; - return -1; + return -1; } label polyMeshGenFaces::addFaceSubset(const word& setName) @@ -270,62 +269,62 @@ void polyMeshGenFaces::read() polyMeshGenPoints::read(); faceIOList fcs - ( - IOobject - ( - "faces", - runTime_.constant(), - "polyMesh", - runTime_, - IOobject::MUST_READ - ) - ); - faces_ = fcs; - - deleteDemandDrivenData(ownerPtr_); - deleteDemandDrivenData(neighbourPtr_); - - ownerPtr_ = - new labelIOList - ( - IOobject - ( - "owner", - runTime_.constant(), - "polyMesh", - runTime_, - IOobject::MUST_READ - ) - ); - - neighbourPtr_ = - new labelIOList - ( - IOobject - ( - "neighbour", - runTime_.constant(), - "polyMesh", - runTime_, - IOobject::MUST_READ - ) - ); + ( + IOobject + ( + "faces", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::MUST_READ + ) + ); + faces_ = fcs; + + deleteDemandDrivenData(ownerPtr_); + deleteDemandDrivenData(neighbourPtr_); + + ownerPtr_ = + new labelIOList + ( + IOobject + ( + "owner", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::MUST_READ + ) + ); + + neighbourPtr_ = + new labelIOList + ( + IOobject + ( + "neighbour", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::MUST_READ + ) + ); if( neighbourPtr_->size() != ownerPtr_->size() ) neighbourPtr_->setSize(ownerPtr_->size(), -1); - //- read boundary information - IOPtrList<writePatchBase> patches - ( - IOobject - ( - "boundary", - runTime_.constant(), - "polyMesh", - runTime_, - IOobject::MUST_READ - ) - ); + //- read boundary information + IOPtrList<boundaryPatchBase> patches + ( + IOobject + ( + "boundary", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::MUST_READ + ) + ); label i(0); forAll(patches, patchI) @@ -333,23 +332,23 @@ void polyMeshGenFaces::read() ++i; procBoundaries_.setSize(i); - boundaries_.setSize(patches.size()-i); - + boundaries_.setSize(patches.size()-i); + i=0; - forAll(patches, patchI) + forAll(patches, patchI) if( patches[patchI].type() != "processor" ) { - boundaries_.set - ( - i, - new writePatch - ( - patches[patchI].patchName(), - patches[patchI].patchType(), - patches[patchI].patchSize(), - patches[patchI].patchStart() - ) - ); + boundaries_.set + ( + i, + new boundaryPatch + ( + patches[patchI].patchName(), + patches[patchI].patchType(), + patches[patchI].patchSize(), + patches[patchI].patchStart() + ) + ); ++i; } @@ -360,7 +359,7 @@ void polyMeshGenFaces::read() procBoundaries_.set ( i++, - new writeProcessorPatch + new processorBoundaryPatch ( patches[patchI].patchName(), patches[patchI].dict() @@ -368,7 +367,7 @@ void polyMeshGenFaces::read() ); } - nIntFaces_ = boundaries_[0].patchStart(); + nIntFaces_ = boundaries_[0].patchStart(); //- read face subsets IOobjectList allSets @@ -396,14 +395,14 @@ void polyMeshGenFaces::write() const polyMeshGenPoints::write(); faces_.write(); - - if( !ownerPtr_ || !neighbourPtr_ ) - calculateOwnersAndNeighbours(); - ownerPtr_->write(); - neighbourPtr_->write(); - + + if( !ownerPtr_ || !neighbourPtr_ ) + calculateOwnersAndNeighbours(); + ownerPtr_->write(); + neighbourPtr_->write(); + //- write boundary data - PtrList<writePatchBase> ptchs + PtrList<boundaryPatchBase> ptchs ( procBoundaries_.size() + boundaries_.size() ); @@ -417,10 +416,10 @@ void polyMeshGenFaces::write() const dict.add("type", boundaries_[patchI].patchType()); dict.add("nFaces", boundaries_[patchI].patchSize()); dict.add("startFace", boundaries_[patchI].patchStart()); - ptchs.set + ptchs.set ( i++, - writePatchBase::New + boundaryPatchBase::New ( boundaries_[patchI].patchName(), dict @@ -434,29 +433,29 @@ void polyMeshGenFaces::write() const ptchs.set ( i++, - writePatchBase::New + boundaryPatchBase::New ( procBoundaries_[patchI].patchName(), procBoundaries_[patchI].dict() ) ); } - - IOPtrList<writePatchBase> patches - ( - IOobject - ( - "boundary", - runTime_.constant(), - "polyMesh", - runTime_, - IOobject::NO_READ, - IOobject::AUTO_WRITE - ), - ptchs - ); + + IOPtrList<boundaryPatchBase> patches + ( + IOobject + ( + "boundary", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::NO_READ, + IOobject::AUTO_WRITE + ), + ptchs + ); - patches.write(); + patches.write(); //- write face subsets std::map<label, meshSubset>::const_iterator setIt; @@ -475,7 +474,7 @@ void polyMeshGenFaces::write() const ) ); - labelListPMG containedElements; + labelLongList containedElements; setIt->second.containedElements(containedElements); forAll(containedElements, i) diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.H b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.H index caccdc4792f792af4890df3929e69a322a1320ed..7ee37e6876aa46801a721325267961ee25f075dc 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFaces.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenFaces @@ -41,8 +40,8 @@ SourceFiles #include "polyMeshGenPoints.H" #include "faceListPMG.H" #include "labelIOList.H" -#include "writeProcessorPatch.H" -#include "writePatch.H" +#include "processorBoundaryPatch.H" +#include "boundaryPatch.H" namespace Foam { @@ -55,94 +54,94 @@ class polyMeshGenFaces protected: // Protected data - //- list of faces - faceListPMG faces_; + //- list of faces + faceListPMG faces_; //- inter-processor boundaries. These faces are located after the other //- boundary faces in the list of faces. The processor //- boundaries are internal faces in the end. - PtrList<writeProcessorPatch> procBoundaries_; - - //- boundary data - PtrList<writePatch> boundaries_; + PtrList<processorBoundaryPatch> procBoundaries_; + + //- boundary data + PtrList<boundaryPatch> boundaries_; //- face subsets std::map<label, meshSubset> faceSubsets_; - - // Addressing data - //- number of internal faces, owner and neighbour - mutable label nIntFaces_; - mutable labelIOList* ownerPtr_; - mutable labelIOList* neighbourPtr_; - - // Private member functions + + // Addressing data + //- number of internal faces, owner and neighbour + mutable label nIntFaces_; + mutable labelIOList* ownerPtr_; + mutable labelIOList* neighbourPtr_; + + // Private member functions //- calculate owner and neighbour addressing virtual void calculateOwnersAndNeighbours() const = 0; - - //- clear all pointer data - void clearOut() const; - - // Disallow bitwise assignment - void operator=(const polyMeshGenFaces&); - - polyMeshGenFaces(const polyMeshGenFaces&); + + //- clear all pointer data + void clearOut() const; + + // Disallow bitwise assignment + void operator=(const polyMeshGenFaces&); + + polyMeshGenFaces(const polyMeshGenFaces&); public: - - friend class polyMeshGenModifier; - - // Constructors - //- Null constructor - polyMeshGenFaces(const Time&); - - //- Construct from components without the boundary - polyMeshGenFaces - ( - const Time&, - const pointField& points, - const faceList& faces - ); - - //- Construct from components with the boundary - polyMeshGenFaces - ( - const Time&, - const pointField& points, - const faceList& faces, - const wordList& patchNames, - const labelList& patchStart, - const labelList& nFacesInPatch - ); - - // Destructor - virtual ~polyMeshGenFaces(); - - // Member functions - - //- access to faces - inline const faceListPMG& faces() const; - - //- return number of internal faces - inline label nInternalFaces() const; - - //- owner and neighbour cells for faces - inline const labelList& owner() const; - inline const labelList& neighbour() const; - + + friend class polyMeshGenModifier; + + // Constructors + //- Null constructor + polyMeshGenFaces(const Time&); + + //- Construct from components without the boundary + polyMeshGenFaces + ( + const Time&, + const pointField& points, + const faceList& faces + ); + + //- Construct from components with the boundary + polyMeshGenFaces + ( + const Time&, + const pointField& points, + const faceList& faces, + const wordList& patchNames, + const labelList& patchStart, + const labelList& nFacesInPatch + ); + + // Destructor + virtual ~polyMeshGenFaces(); + + // Member functions + + //- access to faces + inline const faceListPMG& faces() const; + + //- return number of internal faces + inline label nInternalFaces() const; + + //- owner and neighbour cells for faces + inline const labelList& owner() const; + inline const labelList& neighbour() const; + // Boundary data //- inter-processor boundaries - inline const PtrList<writeProcessorPatch>& procBoundaries() const; + inline const PtrList<processorBoundaryPatch>& procBoundaries() const; //- return processor patch label for the given face label - label faceIsInProcPatch(const label faceLabel) const; + label faceIsInProcPatch(const label faceLabel) const; + + //- ordinary boundaries + inline const PtrList<boundaryPatch>& boundaries() const; - //- ordinary boundaries - inline const PtrList<writePatch>& boundaries() const; - - //- return patch label for the given face label - label faceIsInPatch(const label faceLabel) const; + //- return patch label for the given face label + label faceIsInPatch(const label faceLabel) const; // Subsets @@ -159,12 +158,12 @@ public: template<class ListType> inline void updateFaceSubsets(const ListType&); inline void updateFaceSubsets(const VRWGraph&); - - // Read mesh - void read(); - - // Write mesh - void write() const; + + // Read mesh + void read(); + + // Write mesh + void write() const; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFacesI.H b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFacesI.H index a71dc4caab251a47da3a3a4d743ff7757f138f86..ec3aa17beace7859b0a650a6c5614d161f88580d 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFacesI.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenFacesI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -32,49 +31,86 @@ Description #include "polyMeshGenFaces.H" +# ifdef USE_OMP +#include <omp.h> +# endif + namespace Foam { // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + inline const faceListPMG& polyMeshGenFaces::faces() const { - return faces_; + return faces_; } - + inline label polyMeshGenFaces::nInternalFaces() const { - if( !(ownerPtr_ && neighbourPtr_) ) - calculateOwnersAndNeighbours(); + if( !(ownerPtr_ && neighbourPtr_) ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline label polyMeshGenFaces::nInternalFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateOwnersAndNeighbours(); + } - return nIntFaces_; + return nIntFaces_; } inline const labelList& polyMeshGenFaces::owner() const { - if( !ownerPtr_ ) - calculateOwnersAndNeighbours(); - - return *ownerPtr_; + if( !ownerPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline label polyMeshGenFaces::owner() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateOwnersAndNeighbours(); + } + + return *ownerPtr_; } inline const labelList& polyMeshGenFaces::neighbour() const { - if( !neighbourPtr_ ) - calculateOwnersAndNeighbours(); - - return *neighbourPtr_; + if( !neighbourPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline label polyMeshGenFaces::neighbour() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateOwnersAndNeighbours(); + } + + return *neighbourPtr_; } -inline const PtrList<writeProcessorPatch>& +inline const PtrList<processorBoundaryPatch>& polyMeshGenFaces::procBoundaries() const { return procBoundaries_; } -inline const PtrList<writePatch>& polyMeshGenFaces::boundaries() const +inline const PtrList<boundaryPatch>& polyMeshGenFaces::boundaries() const { - return boundaries_; + return boundaries_; } inline void polyMeshGenFaces::addFaceToSubset diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.C b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.C index 2c6801f3732f2af3937fc3041fd29a1ae577abe8..da331809a5b56b88bd89c3939f4f3c3c6bdd4523 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.C +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,18 +38,18 @@ namespace Foam //- Null constructor polyMeshGenPoints::polyMeshGenPoints(const Time& runTime) : - runTime_(runTime), - points_ - ( - IOobject - ( - "points", - runTime.constant(), - "polyMesh", - runTime - ), - 0 - ), + runTime_(runTime), + points_ + ( + IOobject + ( + "points", + runTime.constant(), + "polyMesh", + runTime + ), + 0 + ), pointSubsets_() { } @@ -58,26 +57,26 @@ polyMeshGenPoints::polyMeshGenPoints(const Time& runTime) //- Construct from time and points polyMeshGenPoints::polyMeshGenPoints ( - const Time& runTime, - const pointField& points + const Time& runTime, + const pointField& points ) : - runTime_(runTime), - points_ - ( - IOobject - ( - "points", - runTime.constant(), - "polyMesh", - runTime - ), - points - ), + runTime_(runTime), + points_ + ( + IOobject + ( + "points", + runTime.constant(), + "polyMesh", + runTime + ), + points + ), pointSubsets_() { } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Destructor polyMeshGenPoints::~polyMeshGenPoints() @@ -147,18 +146,18 @@ label polyMeshGenPoints::pointSubsetIndex(const word& subsetName) const void polyMeshGenPoints::read() { - pointIOField pts - ( - IOobject - ( - "points", - runTime_.constant(), - "polyMesh", - runTime_, - IOobject::MUST_READ - ) - ); - points_ = pts; + pointIOField pts + ( + IOobject + ( + "points", + runTime_.constant(), + "polyMesh", + runTime_, + IOobject::MUST_READ + ) + ); + points_ = pts; //- read point subsets IOobjectList allSets @@ -186,7 +185,7 @@ void polyMeshGenPoints::write() const points_.write(); std::map<label, meshSubset>::const_iterator setIt; - labelListPMG containedElements; + labelLongList containedElements; //- write point selections for(setIt=pointSubsets_.begin();setIt!=pointSubsets_.end();++setIt) diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.H b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.H index 5ac98b6ee3d192733a46ed773bf3ba83d153df09..1274a36b0c6de1f9da9ad071dbe95dfc1f3be85e 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPoints.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenPoints @@ -55,44 +54,44 @@ class polyMeshGenPoints protected: // Protected data - //- reference to the Time registry - const Time& runTime_; + //- reference to the Time registry + const Time& runTime_; - //- list of vertices - pointFieldPMG points_; + //- list of vertices + pointFieldPMG points_; //- map of point subsets std::map<label, meshSubset> pointSubsets_; - - // Disallow bitwise assignment - void operator=(const polyMeshGenPoints&); - - polyMeshGenPoints(const polyMeshGenPoints&); + + // Disallow bitwise assignment + void operator=(const polyMeshGenPoints&); + + polyMeshGenPoints(const polyMeshGenPoints&); public: - - friend class polyMeshGenModifier; - - // Constructors - //- Null constructor - polyMeshGenPoints(const Time&); - - //- Construct from components without the boundary - polyMeshGenPoints - ( - const Time&, - const pointField& points - ); - - // Destructor - ~polyMeshGenPoints(); - - // Member functions - //- access to Time - inline const Time& returnTime() const; - - //- access to points - inline const pointFieldPMG& points() const; + + friend class polyMeshGenModifier; + + // Constructors + //- Null constructor + polyMeshGenPoints(const Time&); + + //- Construct from components without the boundary + polyMeshGenPoints + ( + const Time&, + const pointField& points + ); + + // Destructor + ~polyMeshGenPoints(); + + // Member functions + //- access to Time + inline const Time& returnTime() const; + + //- access to points + inline const pointFieldPMG& points() const; //- non-const access to points inline pointFieldPMG& points(); @@ -113,12 +112,12 @@ public: inline void pointsInSubset(const label, ListType&) const; template<class ListType> inline void updatePointSubsets(const ListType&); - - // Read mesh - void read(); - - // Write mesh - void write() const; + + // Read mesh + void read(); + + // Write mesh + void write() const; }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPointsI.H b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPointsI.H index 04931ddab8128011948795ebe6b4ca71aed03118..74549586ac5f8840a5bf0e32111f9e565c0b9a2a 100644 --- a/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPointsI.H +++ b/meshLibrary/utilities/meshes/polyMeshGen/polyMeshGenPointsI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,19 +38,19 @@ namespace Foam inline const Time& polyMeshGenPoints::returnTime() const { - return runTime_; + return runTime_; } - + inline const pointFieldPMG& polyMeshGenPoints::points() const { - return points_; + return points_; } inline pointFieldPMG& polyMeshGenPoints::points() { return points_; } - + inline void polyMeshGenPoints::appendVertex(const point& p) { points_.append(p); diff --git a/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngine.C b/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngine.C new file mode 100644 index 0000000000000000000000000000000000000000..89b075addd08ae3f1fe747121bc67d9a7139aea8 --- /dev/null +++ b/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngine.C @@ -0,0 +1,368 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "polyMeshGen2DEngine.H" +#include "polyMeshGenAddressing.H" +#include "demandDrivenData.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void polyMeshGen2DEngine::findActiveFaces() const +{ + const faceListPMG& faces = mesh_.faces(); + const boolList& zMinPoints = this->zMinPoints(); + const boolList& zMaxPoints = this->zMaxPoints(); + + activeFacePtr_ = new boolList(faces.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(faces, faceI) + { + bool hasZMin(false), hasZMax(false); + + const face& f = faces[faceI]; + forAll(f, pI) + { + hasZMin |= zMinPoints[f[pI]]; + hasZMax |= zMaxPoints[f[pI]]; + } + + activeFacePtr_->operator[](faceI) = (hasZMin && hasZMax); + } +} + +void polyMeshGen2DEngine::findActiveFaceLabels() const +{ + const boolList& activeFace = this->activeFace(); + + label counter(0); + + forAll(activeFace, faceI) + if( activeFace[faceI] ) + ++counter; + + activeFaceLabelsPtr_ = new labelList(counter); + + counter = 0; + forAll(activeFace, faceI) + if( activeFace[faceI] ) + activeFaceLabelsPtr_->operator[](counter++) = faceI; +} + +void polyMeshGen2DEngine::findZMinPoints() const +{ + const pointFieldPMG& points = mesh_.points(); + + zMinPointPtr_ = new boolList(points.size()); + + const scalar tZ = 0.05 * (bb_.max().z() - bb_.min().z());; + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(points, pointI) + { + if( Foam::mag(points[pointI].z() - bb_.min().z()) < tZ ) + { + zMinPointPtr_->operator[](pointI) = true; + } + else + { + zMinPointPtr_->operator[](pointI) = false; + } + } +} + +void polyMeshGen2DEngine::findZMinPointLabels() const +{ + const boolList& zMinPoints = this->zMinPoints(); + + label counter(0); + + forAll(zMinPoints, pointI) + if( zMinPoints[pointI] ) + ++counter; + + if( 2 * counter != zMinPoints.size() ) + { + FatalErrorIn + ( + "void polyMeshGen2DEngine::findZMinPointLabels()" + ) << "The number of points at smallest z coordinate is" + << " not half of the total number of points." + << " This is not a 2D mesh or is not aligned with the z axis" + << exit(FatalError); + } + + zMinPointLabelsPtr_ = new labelList(counter); + + counter = 0; + forAll(zMinPoints, pointI) + if( zMinPoints[pointI] ) + zMinPointLabelsPtr_->operator[](counter++) = pointI; +} + +void polyMeshGen2DEngine::findZMinOffsetPoints() const +{ + const boolList& zMinPoints = this->zMinPoints(); + const labelList& zMinPointLabels = this->zMinPointLabels(); + + zMinToZMaxPtr_ = new labelList(zMinPointLabels.size()); + + const VRWGraph& pointPoints = mesh_.addressingData().pointPoints(); + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(zMinPointLabels, pI) + { + const label pointI = zMinPointLabels[pI]; + + label nInactive(0), offsetPoint(-1); + forAllRow(pointPoints, pointI, ppI) + { + if( !zMinPoints[pointPoints(pointI, ppI)] ) + { + ++nInactive; + offsetPoint = pointPoints(pointI, ppI); + } + } + + if( nInactive == 1 ) + { + zMinToZMaxPtr_->operator[](pI) = offsetPoint; + } + else + { + FatalErrorIn + ( + "void polyMeshGen2DEngine::findZMinOffsetPoints()" + ) << "This cannot be a 2D mesh" << exit(FatalError); + } + } +} + +void polyMeshGen2DEngine::findZMaxPoints() const +{ + const pointFieldPMG& points = mesh_.points(); + + zMaxPointPtr_ = new boolList(points.size()); + + const scalar tZ = 0.05 * (bb_.max().z() - bb_.min().z()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(points, pointI) + { + if( Foam::mag(points[pointI].z() - bb_.max().z()) < tZ ) + { + zMaxPointPtr_->operator[](pointI) = true; + } + else + { + zMaxPointPtr_->operator[](pointI) = false; + } + } +} + +void polyMeshGen2DEngine::findZMaxPointLabels() const +{ + const boolList& zMaxPoints = this->zMaxPoints(); + + label counter(0); + + forAll(zMaxPoints, pointI) + if( zMaxPoints[pointI] ) + ++counter; + + if( 2 * counter != zMaxPoints.size() ) + { + FatalErrorIn + ( + "void polyMeshGen2DEngine::findZMaxPointLabels()" + ) << "The number of points at largest z coordinate is" + << " not half of the total number of points." + << " This is not a 2D mesh or is not aligned with the z axis" + << exit(FatalError); + } + + zMaxPointLabelsPtr_ = new labelList(counter); + + counter = 0; + forAll(zMaxPoints, pointI) + if( zMaxPoints[pointI] ) + zMaxPointLabelsPtr_->operator[](counter++) = pointI; +} + +void polyMeshGen2DEngine::findZMaxOffsetPoints() const +{ + const boolList& zMaxPoints = this->zMaxPoints(); + const labelList& zMaxPointLabels = this->zMaxPointLabels(); + + zMaxToZMinPtr_ = new labelList(zMaxPointLabels.size()); + + const VRWGraph& pointPoints = mesh_.addressingData().pointPoints(); + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(zMaxPointLabels, pI) + { + const label pointI = zMaxPointLabels[pI]; + + label nInactive(0), offsetPoint(-1); + forAllRow(pointPoints, pointI, ppI) + { + if( !zMaxPoints[pointPoints(pointI, ppI)] ) + { + ++nInactive; + offsetPoint = pointPoints(pointI, ppI); + } + } + + if( nInactive == 1 ) + { + zMaxToZMinPtr_->operator[](pI) = offsetPoint; + } + else + { + FatalErrorIn + ( + "void polyMeshGen2DEngine::findZMaxOffsetPoints()" + ) << "This cannot be a 2D mesh" << exit(FatalError); + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +polyMeshGen2DEngine::polyMeshGen2DEngine(polyMeshGen& mesh) +: + mesh_(mesh), + bb_(), + activeFacePtr_(NULL), + activeFaceLabelsPtr_(NULL), + zMinPointPtr_(NULL), + zMinPointLabelsPtr_(NULL), + zMinToZMaxPtr_(NULL), + zMaxPointPtr_(NULL), + zMaxPointLabelsPtr_(NULL), + zMaxToZMinPtr_(NULL) +{ + const pointFieldPMG& points = mesh_.points(); + + bb_.min() = point(VGREAT, VGREAT, VGREAT); + bb_.max() = point(-VGREAT, -VGREAT, -VGREAT); + + # ifdef USE_OMP + # pragma omp parallel + # endif + { + point localMin(VGREAT, VGREAT, VGREAT); + point localMax(-VGREAT, -VGREAT, -VGREAT); + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 50) + # endif + forAll(points, pointI) + { + localMin = Foam::min(localMin, points[pointI]); + localMax = Foam::max(localMax, points[pointI]); + } + + # ifdef USE_OMP + # pragma omp critical + # endif + { + bb_.min() = Foam::min(bb_.min(), localMin); + bb_.max() = Foam::max(bb_.max(), localMax); + } + } + + if( Pstream::parRun() ) + { + reduce(bb_.min(), minOp<point>()); + reduce(bb_.max(), maxOp<point>()); + } +} + +polyMeshGen2DEngine::~polyMeshGen2DEngine() +{ + clearOut(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void polyMeshGen2DEngine::correctPoints() +{ + pointFieldPMG& points = mesh_.points(); + + const labelList& zMinPointLabels = this->zMinPointLabels(); + const labelList& zMinOffset = this->zMinToZMax(); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(zMinPointLabels, apI) + { + point& p = points[zMinPointLabels[apI]]; + point& op = points[zMinOffset[apI]]; + + op.x() = p.x(); + op.y() = p.y(); + p.z() = bb_.min().z(); + op.z() = bb_.max().z(); + } +} + +void polyMeshGen2DEngine::clearOut() +{ + deleteDemandDrivenData(activeFacePtr_); + deleteDemandDrivenData(activeFaceLabelsPtr_); + deleteDemandDrivenData(zMinPointPtr_); + deleteDemandDrivenData(zMinPointLabelsPtr_); + deleteDemandDrivenData(zMinToZMaxPtr_); + deleteDemandDrivenData(zMaxPointPtr_); + deleteDemandDrivenData(zMaxPointLabelsPtr_); + deleteDemandDrivenData(zMaxToZMinPtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngine.H b/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngine.H new file mode 100644 index 0000000000000000000000000000000000000000..d6b54fefefa73d4ae4c1682f2c383fd57b9ecb96 --- /dev/null +++ b/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngine.H @@ -0,0 +1,172 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + polyMeshGen2DEngine + +Description + A simple engine which provides topological information of a 2D mesh + and allows for maintaining consistency + +SourceFiles + polyMeshGen2DEngine.C + +\*---------------------------------------------------------------------------*/ + +#ifndef polyMeshGen2DEngine_H +#define polyMeshGen2DEngine_H + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "polyMeshGen.H" +#include "boolList.H" +#include "labelList.H" +#include "boundBox.H" +#include "demandDrivenData.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +class polyMeshGen2DEngine +{ + // Private data + //- reference to the mesh + polyMeshGen& mesh_; + + //- bounding box + boundBox bb_; + + //- which faces are not in the x-y plane + mutable boolList* activeFacePtr_; + + //- labels of active faces + mutable labelList* activeFaceLabelsPtr_; + + //- which points are in the x-y plane and at smallest z + mutable boolList* zMinPointPtr_; + + //- labels of points at minimum z + mutable labelList* zMinPointLabelsPtr_; + + //- labels of offset points of zMin points + mutable labelList* zMinToZMaxPtr_; + + //- which points are in the x-y plane and at largest z + mutable boolList* zMaxPointPtr_; + + //- labels of points at maximum z + mutable labelList* zMaxPointLabelsPtr_; + + //- labels of zMin points of zMax points + mutable labelList* zMaxToZMinPtr_; + + // Private member functions + //- find active faces + void findActiveFaces() const; + + //- find active face labels + void findActiveFaceLabels() const; + + //- find points at minimum z + void findZMinPoints() const; + + //- find labels of points at minimum z + void findZMinPointLabels() const; + + //- find offset point to each zMin point + void findZMinOffsetPoints() const; + + //- find points at maximum z + void findZMaxPoints() const; + + //- find labels of points at minimum z + void findZMaxPointLabels() const; + + //- find offset point to each zMin point + void findZMaxOffsetPoints() const; + + //- disallow bitwise assignment + void operator=(const polyMeshGen2DEngine&); + + //- disallow copy construct + polyMeshGen2DEngine(const polyMeshGen2DEngine&); + +public: + + // Constructors + //- Construct from the reference to the mesh + polyMeshGen2DEngine(polyMeshGen& mesh); + + // Destructor + ~polyMeshGen2DEngine(); + + // Member functions + //- const access to active faces + inline const boolList& activeFace() const; + + //- labels of active faces + inline const labelList& activeFaceLabels() const; + + //- const access to an array of booleans which is true for points + //- in the x-y plane with the smallest z coordinate + inline const boolList& zMinPoints() const; + + //- labels of points in the x-y with the smallest z coordinate + inline const labelList& zMinPointLabels() const; + + //- offset points of points at minimum z + inline const labelList& zMinToZMax() const; + + //- const access to an array of booleans which is true for points + //- in the x-y plane with the largest z coordinate + inline const boolList& zMaxPoints() const; + + //- labels of points in the x-y with the largest z coordinate + inline const labelList& zMaxPointLabels() const; + + //- offset points of points at maximum z + inline const labelList& zMaxToZMin() const; + + //- correct x and y coordinates of offset points + //- and unify the z coordinate + void correctPoints(); + + //- delete all dynamically allocated data + void clearOut(); +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "polyMeshGen2DEngineI.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngineI.H b/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngineI.H new file mode 100644 index 0000000000000000000000000000000000000000..04bbfbbff2754854cf955af6e5f16107a7a2bbb5 --- /dev/null +++ b/meshLibrary/utilities/meshes/polyMeshGen2DEngine/polyMeshGen2DEngineI.H @@ -0,0 +1,118 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + polyMeshGen2DEngine + +Description + A simple engine which provides topological information of a 2D mesh + and allows for maintaining consistency + +SourceFiles + polyMeshGen2DEngine.C + +\*---------------------------------------------------------------------------*/ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "polyMeshGen2DEngine.H" +#include "boolList.H" +#include "labelList.H" +#include "boundBox.H" +#include "demandDrivenData.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +inline const boolList& polyMeshGen2DEngine::activeFace() const +{ + if( !activeFacePtr_ ) + findActiveFaces(); + + return *activeFacePtr_; +} + +inline const labelList& polyMeshGen2DEngine::activeFaceLabels() const +{ + if( !activeFaceLabelsPtr_ ) + findActiveFaceLabels(); + + return *activeFaceLabelsPtr_; +} + +inline const boolList& polyMeshGen2DEngine::zMinPoints() const +{ + if( !zMinPointPtr_ ) + findZMinPoints(); + + return *zMinPointPtr_; +} + +inline const labelList& polyMeshGen2DEngine::zMinPointLabels() const +{ + if( !zMinPointLabelsPtr_ ) + findZMinPointLabels(); + + return *zMinPointLabelsPtr_; +} + +inline const labelList& polyMeshGen2DEngine::zMinToZMax() const +{ + if( !zMinToZMaxPtr_ ) + findZMinOffsetPoints(); + + return *zMinToZMaxPtr_; +} + +inline const boolList& polyMeshGen2DEngine::zMaxPoints() const +{ + if( !zMaxPointPtr_ ) + findZMaxPoints(); + + return *zMaxPointPtr_; +} + +inline const labelList& polyMeshGen2DEngine::zMaxPointLabels() const +{ + if( !zMaxPointLabelsPtr_ ) + findZMaxPointLabels(); + + return *zMaxPointLabelsPtr_; +} + +inline const labelList& polyMeshGen2DEngine::zMaxToZMin() const +{ + if( !zMaxToZMinPtr_ ) + findZMaxOffsetPoints(); + + return *zMaxToZMinPtr_; +} + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.C index 0ca6b4e061c39dfe0ffc786ac5c36e6e2582abe1..3d442b1568c0a1ed89ab5f7200521321ddeb9ab9 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.H b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.H index 8e95e0e66621884f926d52fe717a94ff9f52339d..02ddb2796bb871318b5543f76c14765bd1e03d84 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.H +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressing.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenAddressing @@ -70,77 +69,77 @@ namespace Foam class polyMeshGenAddressing { - // Mesh data + // Mesh data //- reference to the mesh const polyMeshGenCells& mesh_; - // Shapes + // Shapes - //- Edges - mutable edgeList* edgesPtr_; + //- Edges + mutable edgeList* edgesPtr_; - // Connectivity + // Connectivity - //- Cell-cells - mutable VRWGraph* ccPtr_; + //- Cell-cells + mutable VRWGraph* ccPtr_; - //- Edge-cells - mutable VRWGraph* ecPtr_; + //- Edge-cells + mutable VRWGraph* ecPtr_; - //- Point-cells - mutable VRWGraph* pcPtr_; + //- Point-cells + mutable VRWGraph* pcPtr_; - //- Edge-faces - mutable VRWGraph* efPtr_; + //- Edge-faces + mutable VRWGraph* efPtr_; - //- Point-faces - mutable VRWGraph* pfPtr_; + //- Point-faces + mutable VRWGraph* pfPtr_; - //- Cell-edges - mutable VRWGraph* cePtr_; + //- Cell-edges + mutable VRWGraph* cePtr_; - //- Face-edges - mutable VRWGraph* fePtr_; + //- Face-edges + mutable VRWGraph* fePtr_; - //- Point-edges - mutable VRWGraph* pePtr_; + //- Point-edges + mutable VRWGraph* pePtr_; - //- Point-points - mutable VRWGraph* ppPtr_; + //- Point-points + mutable VRWGraph* ppPtr_; - //- Cell-points - mutable VRWGraph* cpPtr_; + //- Cell-points + mutable VRWGraph* cpPtr_; - // Geometric data + // Geometric data - //- Cell centres - mutable vectorField* cellCentresPtr_; + //- Cell centres + mutable vectorField* cellCentresPtr_; - //- Face centres - mutable vectorField* faceCentresPtr_; + //- Face centres + mutable vectorField* faceCentresPtr_; - //- Cell volumes - mutable scalarField* cellVolumesPtr_; + //- Cell volumes + mutable scalarField* cellVolumesPtr_; - //- Face areas - mutable vectorField* faceAreasPtr_; + //- Face areas + mutable vectorField* faceAreasPtr_; // Parallel demand driven data //- global point labels - mutable labelListPMG* globalPointLabelPtr_; + mutable labelLongList* globalPointLabelPtr_; //- global face labels - mutable labelListPMG* globalFaceLabelPtr_; + mutable labelLongList* globalFaceLabelPtr_; //- global cell labels - mutable labelListPMG* globalCellLabelPtr_; + mutable labelLongList* globalCellLabelPtr_; //- global edge labels - mutable labelListPMG* globalEdgeLabelPtr_; + mutable labelLongList* globalEdgeLabelPtr_; // Parallel addressing @@ -249,7 +248,7 @@ class polyMeshGenAddressing //- Calculate edge vectors void calcEdgeVectors() const; - // Disallow bitwise construct + // Disallow bitwise construct //- Default constructor polyMeshGenAddressing(); @@ -327,10 +326,10 @@ public: // Parallel addressing - const labelListPMG& globalPointLabel() const; - const labelListPMG& globalFaceLabel() const; - const labelListPMG& globalCellLabel() const; - const labelListPMG& globalEdgeLabel() const; + const labelLongList& globalPointLabel() const; + const labelLongList& globalFaceLabel() const; + const labelLongList& globalCellLabel() const; + const labelLongList& globalEdgeLabel() const; const VRWGraph& pointAtProcs() const; const Map<label>& globalToLocalPointAddressing() const; diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellCells.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellCells.C index c2210e9a54e8cf0276d76bc964a0ebb318fe23e7..f94cfb5d1a32b0c59a381d66855fcaa552c7ab8c 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellCells.C @@ -1,33 +1,34 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "polyMeshGenAddressing.H" #include "VRWGraphSMPModifier.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -46,70 +47,82 @@ void polyMeshGenAddressing::calcCellCells() const } else { - const cellListPMG& cells = mesh_.cells(); - + const cellListPMG& cells = mesh_.cells(); + const labelList& own = mesh_.owner(); const labelList& nei = mesh_.neighbour(); - + //- create the storage ccPtr_ = new VRWGraph(); VRWGraph& cellCellAddr = *ccPtr_; - + labelList nNei(cells.size()); - + + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); - + # endif + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(nNei, i) nNei[i] = 0; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; - + DynList<label> neiCells; - + forAll(c, fI) { label neiCell = own[c[fI]]; - if( (neiCell == cellI) && (nei[c[fI]] != -1) ) + if( (neiCell == cellI) && (nei[c[fI]] != -1) ) neiCell = nei[c[fI]]; - + if( neiCell != cellI ) neiCells.appendIfNotIn(neiCell); } - + nNei[cellI] = neiCells.size(); } - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif VRWGraphSMPModifier(cellCellAddr).setSizeAndRowSize(nNei); - + + # ifdef USE_OMP # pragma omp barrier - + //- fill the graph with data # pragma omp for schedule(static) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; - + DynList<label> neiCells; - + forAll(c, fI) { label neiCell = own[c[fI]]; - if( (neiCell == cellI) && (nei[c[fI]] != -1) ) + if( (neiCell == cellI) && (nei[c[fI]] != -1) ) neiCell = nei[c[fI]]; - + if( neiCell != cellI ) neiCells.appendIfNotIn(neiCell); } - + cellCellAddr.setRow(cellI, neiCells); } } @@ -121,7 +134,18 @@ void polyMeshGenAddressing::calcCellCells() const const VRWGraph& polyMeshGenAddressing::cellCells() const { if( !ccPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::cellCells() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcCellCells(); + } return *ccPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellEdges.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellEdges.C index ab8486af58adbfa23fb44700dad2ac9420195f52..bd80dd225236aff0d57198691969e541dd8994a0 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellEdges.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -28,7 +27,9 @@ License #include "DynList.H" #include "VRWGraphSMPModifier.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -52,57 +53,69 @@ void polyMeshGenAddressing::calcCellEdges() const cePtr_ = new VRWGraph(); VRWGraph& cellEdgeAddr = *cePtr_; - + labelList nEdges(cells.size()); - + + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); + # endif + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) if( cells.size() > 10000 ) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(nEdges, i) nEdges[i] = 0; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; - + DynList<label, 32> cEdges; - + forAll(c, fI) { const label faceI = c[fI]; - + forAllRow(fe, faceI, eI) cEdges.appendIfNotIn(fe(faceI, eI)); } - + nEdges[cellI] = cEdges.size(); } - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif VRWGraphSMPModifier(cellEdgeAddr).setSizeAndRowSize(nEdges); - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp for schedule(static) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; - + DynList<label, 32> cEdges; - + forAll(c, fI) { const label faceI = c[fI]; - + forAllRow(fe, faceI, eI) cEdges.appendIfNotIn(fe(faceI, eI)); } - + cellEdgeAddr.setRow(cellI, cEdges); } } @@ -114,7 +127,18 @@ void polyMeshGenAddressing::calcCellEdges() const const VRWGraph& polyMeshGenAddressing::cellEdges() const { if( !cePtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::cellEdges() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcCellEdges(); + } return *cePtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellPoints.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellPoints.C index 5d1c69d48114d3b7d360b5f93e13ef9969de3547..45ccbadabcdec3c8e158edd082d19efb2134cd89 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellPoints.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCellPoints.C @@ -1,33 +1,34 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "polyMeshGenAddressing.H" #include "VRWGraphSMPModifier.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -47,60 +48,69 @@ void polyMeshGenAddressing::calcCellPoints() const else { const cellListPMG& cells = mesh_.cells(); - const faceListPMG& faces = mesh_.faces(); - + const faceListPMG& faces = mesh_.faces(); + //- create the storage cpPtr_ = new VRWGraph(cells.size()); VRWGraph& cellPointsAddr = *cpPtr_; - + labelList nPoints(cells.size()); - + + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); - # pragma omp parallel num_threads(nThreads) if( cells.size() > 10000 ) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(nPoints, i) nPoints[i] = i; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; - + DynList<label, 32> cPoints; forAll(c, fI) { const face& f = faces[c[fI]]; - + forAll(f, pI) cPoints.appendIfNotIn(f[pI]); } - + nPoints[cellI] = cPoints.size(); } - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif VRWGraphSMPModifier(cellPointsAddr).setSizeAndRowSize(nPoints); - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp for schedule(static) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; - + DynList<label, 32> cPoints; forAll(c, fI) { const face& f = faces[c[fI]]; - + forAll(f, pI) cPoints.appendIfNotIn(f[pI]); } - + cellPointsAddr.setRow(cellI, cPoints); } } @@ -112,8 +122,19 @@ void polyMeshGenAddressing::calcCellPoints() const const VRWGraph& polyMeshGenAddressing::cellPoints() const { if( !cpPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::cellPoints() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcCellPoints(); - + } + return *cpPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndAreas.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndAreas.C index 7561931efeeafcdfdc8119a85731d3f5c2144efd..46f72ad941dc037c7f0cf54814132c75b8c3906d 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndAreas.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndAreas.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description Calulate the face centres and areas. @@ -48,9 +47,9 @@ void polyMeshGenAddressing::calcFaceCentresAndAreas() const << "Face centres or face areas already calculated" << abort(FatalError); } - - const pointFieldPMG& points = mesh_.points(); - const faceListPMG& faces = mesh_.faces(); + + const pointFieldPMG& points = mesh_.points(); + const faceListPMG& faces = mesh_.faces(); faceCentresPtr_ = new vectorField(faces.size()); vectorField& fCtrs = *faceCentresPtr_; @@ -71,7 +70,9 @@ void polyMeshGenAddressing::makeFaceCentresAndAreas const faceListPMG& fs = mesh_.faces(); const label nFaces = fs.size(); + # ifdef USE_OMP # pragma omp parallel for if( nFaces > 1000 ) + # endif for(label faceI=0;faceI<nFaces;++faceI) { const face& f = fs[faceI]; @@ -122,7 +123,18 @@ void polyMeshGenAddressing::makeFaceCentresAndAreas const vectorField& polyMeshGenAddressing::faceCentres() const { if( !faceCentresPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const vectorField& polyMeshGenAddressing::faceCentres() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcFaceCentresAndAreas(); + } return *faceCentresPtr_; } @@ -130,7 +142,18 @@ const vectorField& polyMeshGenAddressing::faceCentres() const const vectorField& polyMeshGenAddressing::faceAreas() const { if( !faceAreasPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const vectorField& polyMeshGenAddressing::faceAreas() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcFaceCentresAndAreas(); + } return *faceAreasPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndVols.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndVols.C index 49af006acd89ac764c03a2154b745c2411efadcc..7f08cd751dbdb7aad4ed026a83b6bb87a016af0b 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndVols.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingCentresAndVols.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenAddressing @@ -33,7 +32,9 @@ Description #include "polyMeshGenAddressing.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -50,8 +51,8 @@ void polyMeshGenAddressing::calcCellCentresAndVols() const << "Cell centres or cell volumes already calculated" << abort(FatalError); } - - const cellListPMG& cells = mesh_.cells(); + + const cellListPMG& cells = mesh_.cells(); // set the accumulated cell centre to zero vector cellCentresPtr_ = new vectorField(cells.size()); @@ -75,32 +76,34 @@ void polyMeshGenAddressing::makeCellCentresAndVols { const labelList& own = mesh_.owner(); const cellListPMG& cells = mesh_.cells(); - const label nCells = cells.size(); - + const label nCells = cells.size(); + + # ifdef USE_OMP # pragma omp parallel for if( nCells > 1000 ) + # endif for(label cellI=0;cellI<nCells;++cellI) { const cell& c = cells[cellI]; - + //- approximate the centre first vector cEst(vector::zero); forAll(c, fI) cEst += fCtrs[c[fI]]; - + cEst /= c.size(); - + //- start evaluating the volume and the cell centre vector cellCentre(vector::zero); scalar cellVol(0.0); - + forAll(c, fI) { // Calculate 3*face-pyramid volume scalar pyr3Vol = (fAreas[c[fI]] & (fCtrs[c[fI]] - cEst)); - + if( own[c[fI]] != cellI ) pyr3Vol *= -1.0; - + pyr3Vol = Foam::max(pyr3Vol, VSMALL); // Calculate face-pyramid centre @@ -112,7 +115,7 @@ void polyMeshGenAddressing::makeCellCentresAndVols // Accumulate face-pyramid volume cellVol += pyr3Vol; } - + cellCtrs[cellI] = cellCentre / cellVol; cellVols[cellI] = cellVol / 3.0; } @@ -123,7 +126,18 @@ void polyMeshGenAddressing::makeCellCentresAndVols const vectorField& polyMeshGenAddressing::cellCentres() const { if( !cellCentresPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const vectorField& polyMeshGenAddressing::cellCentres() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcCellCentresAndVols(); + } return *cellCentresPtr_; } @@ -131,7 +145,18 @@ const vectorField& polyMeshGenAddressing::cellCentres() const const scalarField& polyMeshGenAddressing::cellVolumes() const { if( !cellVolumesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const scalarField& polyMeshGenAddressing::cellVolumes() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcCellCentresAndVols(); + } return *cellVolumesPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingClear.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingClear.C index 870a371ba8c3f1c1f71fd1f8ad098e49540811f6..e37810c3ba5b10736b97ea1a21ad0df631866ed7 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingClear.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingClear.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -87,7 +86,7 @@ void polyMeshGenAddressing::printAllocated() const { Pout<< " Point-point" << endl; } - + if( cpPtr_ ) { Pout<< " Cell-point" << endl; @@ -161,7 +160,7 @@ void polyMeshGenAddressing::clearParallelAddressing() deleteDemandDrivenData(globalFaceLabelPtr_); deleteDemandDrivenData(globalCellLabelPtr_); deleteDemandDrivenData(globalEdgeLabelPtr_); - + deleteDemandDrivenData(pProcsPtr_); deleteDemandDrivenData(globalToLocalPointAddressingPtr_); deleteDemandDrivenData(pointNeiProcsPtr_); diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeCells.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeCells.C index 97fe901d179ad7d285bedfe92c8bde9244a4e806..0446a59ab890ced33a077f5ab85ff0d6192f672b 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -59,7 +58,18 @@ void polyMeshGenAddressing::calcEdgeCells() const const VRWGraph& polyMeshGenAddressing::edgeCells() const { if( !ecPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::edgeCells() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcEdgeCells(); + } return *ecPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeFaces.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeFaces.C index dbb011e31195de191a2f2ddaf8f2c00e7ab7b334..b2405f9494d14b659045337d127d5d0c72eb375d 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeFaces.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdgeFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -52,27 +51,35 @@ void polyMeshGenAddressing::calcEdgeFaces() const VRWGraph& edgeFaceAddr = *efPtr_; labelList nef(edges.size()); - + + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); - + # endif + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) if( edges.size() > 10000 ) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(nef, edgeI) nef[edgeI] = 0; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(edges, edgeI) { const edge& ee = edges[edgeI]; const label s = ee.start(); - + forAllRow(pointFaces, s, pfI) { const label faceI = pointFaces(s, pfI); - + const face& f = faces[faceI]; - + forAll(f, eI) { if( f.faceEdge(eI) == ee ) @@ -83,27 +90,31 @@ void polyMeshGenAddressing::calcEdgeFaces() const } } } - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif VRWGraphSMPModifier(edgeFaceAddr).setSizeAndRowSize(nef); - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp for schedule(static) + # endif forAll(edges, edgeI) { const edge& ee = edges[edgeI]; const label s = ee.start(); - + DynList<label> eFaces; forAllRow(pointFaces, s, pfI) { const label faceI = pointFaces(s, pfI); - + const face& f = faces[faceI]; - + forAll(f, eI) { if( f.faceEdge(eI) == ee ) @@ -113,7 +124,7 @@ void polyMeshGenAddressing::calcEdgeFaces() const } } } - + edgeFaceAddr.setRow(edgeI, eFaces); } } @@ -125,7 +136,18 @@ void polyMeshGenAddressing::calcEdgeFaces() const const VRWGraph& polyMeshGenAddressing::edgeFaces() const { if( !efPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::edgeFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcEdgeFaces(); + } return *efPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdges.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdges.C index 9bbec0176dc6000c6056fb68a58be348bb8bc999..c6daf31668f75d2ceff10c203cd746785ffdcfef 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdges.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -29,7 +28,9 @@ License #include "helperFunctions.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -50,33 +51,41 @@ void polyMeshGenAddressing::calcEdges() const { const faceListPMG& faces = mesh_.faces(); const VRWGraph& pointFaces = this->pointFaces(); - + edgesPtr_ = new edgeList(); label nEdges(0); labelList nfe(faces.size()); - + + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); labelList nEdgesForThread(nThreads); - + # else + labelList nEdgesForThread(1); + # endif + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) if( faces.size() > 1000 ) + # endif { LongList<edge> edgesHelper; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(faces, faceI) { const face& f = faces[faceI]; - + forAll(f, pI) { const edge fe = f.faceEdge(pI); const label s = fe.start(); const label e = fe.end(); - + DynList<label> edgeFaces; - + bool store(true); - + //- find all faces attached to this edge //- store the edge in case the face faceI is the face //- with the smallest label @@ -84,7 +93,7 @@ void polyMeshGenAddressing::calcEdges() const { const label ofI = pointFaces(s, pfI); const face& of = faces[ofI]; - + if( of.which(e) < 0 ) continue; if( ofI < faceI ) @@ -92,35 +101,50 @@ void polyMeshGenAddressing::calcEdges() const store = false; break; } - + edgeFaces.append(ofI); } - + if( store ) edgesHelper.append(fe); } } - + //- this enables other threads to see the number of edges //- generated by each thread + # ifdef USE_OMP nEdgesForThread[omp_get_thread_num()] = edgesHelper.size(); - + # else + nEdgesForThread[0] = edgesHelper.size(); + # endif + + # ifdef USE_OMP # pragma omp critical + # endif nEdges += edgesHelper.size(); - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif edgesPtr_->setSize(nEdges); - + + # ifdef USE_OMP # pragma omp barrier - + # endif + //- find the starting position of the edges generated by this thread //- in the global list of edges label localStart(0); - for(label i=0;i<omp_get_thread_num();++i) + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI = 0; + # endif + for(label i=0;i<threadI;++i) localStart += nEdgesForThread[i]; - + //- store edges into the global list forAll(edgesHelper, i) edgesPtr_->operator[](localStart+i) = edgesHelper[i]; @@ -133,7 +157,18 @@ void polyMeshGenAddressing::calcEdges() const const edgeList& polyMeshGenAddressing::edges() const { if( !edgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const edgeList& polyMeshGenAddressing::edges() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcEdges(); + } return *edgesPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingFaceEdges.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingFaceEdges.C index 2898eda4f03fbab11a2bf509a5ed8c1848239091..e4104f9f5080b96cfe41996785f8c585fb770c6a 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingFaceEdges.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingFaceEdges.C @@ -1,33 +1,34 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "polyMeshGenAddressing.H" #include "VRWGraphSMPModifier.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -48,39 +49,49 @@ void polyMeshGenAddressing::calcFaceEdges() const { fePtr_ = new VRWGraph(); VRWGraph& faceEdgesAddr = *fePtr_; - + const edgeList& edges = this->edges(); - + const VRWGraph& pointFaces = this->pointFaces(); const faceListPMG& faces = mesh_.faces(); - + labelList nfe(faces.size()); - + + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); - + # endif + + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) if( faces.size() > 10000 ) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(faces, faceI) nfe[faceI] = faces[faceI].size(); - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif VRWGraphSMPModifier(faceEdgesAddr).setSizeAndRowSize(nfe); - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp for schedule(static) + # endif forAll(edges, edgeI) { const edge ee = edges[edgeI]; const label s = ee.start(); - + forAllRow(pointFaces, s, pfI) { const label faceI = pointFaces(s, pfI); - + const face& f = faces[faceI]; forAll(f, eI) { @@ -101,7 +112,18 @@ void polyMeshGenAddressing::calcFaceEdges() const const VRWGraph& polyMeshGenAddressing::faceEdges() const { if( !fePtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::faceEdges() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcFaceEdges(); + } return *fePtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingParallelAddressing.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingParallelAddressing.C index 4af749d39107a9004112cbfb0baae4f5b7738414..4618d55ed3f9c4f8d395fbe5c61eceea9f222df5 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingParallelAddressing.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingParallelAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -31,9 +30,9 @@ License namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void polyMeshGenAddressing::calcGlobalPointLabels() const { if( !Pstream::parRun() ) @@ -42,30 +41,30 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const "void polyMeshGenAddressing::calcGlobalPointLabels() const" ) << "Cannot calculate global point addressing " << "for a serial run!" << exit(FatalError); - + if( !globalPointLabelPtr_ ) - globalPointLabelPtr_ = new labelListPMG(); - labelListPMG& globalPointLabel = *globalPointLabelPtr_; + globalPointLabelPtr_ = new labelLongList(); + labelLongList& globalPointLabel = *globalPointLabelPtr_; globalPointLabel.setSize(mesh_.points().size()); globalPointLabel = -1; - + if( !pProcsPtr_ ) pProcsPtr_ = new VRWGraph(); VRWGraph& pProcs = *pProcsPtr_; pProcs.setSize(mesh_.points().size()); - + if( !globalToLocalPointAddressingPtr_ ) globalToLocalPointAddressingPtr_ = new Map<label>(); Map<label>& globalToLocal = *globalToLocalPointAddressingPtr_; - + if( !pointNeiProcsPtr_ ) pointNeiProcsPtr_ = new DynList<label>(); DynList<label>& pNeiProcs = *pointNeiProcsPtr_; - + const faceListPMG& faces = mesh_.faces(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - + //- find which processors contain a given bnd point List<std::map<label, std::pair<label, label> > > patchPoints; patchPoints.setSize(procBoundaries.size()); @@ -73,49 +72,49 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const { const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - + std::map<label, std::pair<label, label> >& patchPointsMap = patchPoints[patchI]; - + for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; - + forAll(f, pI) { std::map<label, std::pair<label, label> >::iterator it = patchPointsMap.find(f[pI]); - + if( it != patchPointsMap.end() ) continue; - + const std::pair<label, label> pp ( faceI-start, (f.size()-pI)%f.size() ); patchPointsMap.insert(std::make_pair(f[pI], pp)); - + pProcs.appendIfNotIn(f[pI], procBoundaries[patchI].myProcNo()); pProcs.appendIfNotIn(f[pI], procBoundaries[patchI].neiProcNo()); } } } - + //- exchange data with other processor and update bProcs //- continue this process as long as there is some change bool finished; do { finished = true; - + forAll(procBoundaries, patchI) { const std::map<label, std::pair<label, label> >& patchPointsMap = patchPoints[patchI]; std::map<label, std::pair<label, label> >::const_iterator it; - - labelListPMG dataToSend; + + labelLongList dataToSend; for(it=patchPointsMap.begin();it!=patchPointsMap.end();++it) { //- data is sent as follows @@ -129,7 +128,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const forAllRow(pProcs, it->first, i) dataToSend.append(pProcs(it->first, i)); } - + OPstream toOtherProc ( Pstream::blocking, @@ -138,7 +137,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const ); toOtherProc << dataToSend; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -148,9 +147,9 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { @@ -168,10 +167,10 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const } } } - + reduce(finished, minOp<bool>()); } while( !finished ); - + //- start calculating global point labels label nLocalPoints(0); boolList localPoints(mesh_.points().size(), true); @@ -181,7 +180,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const label pMin = pProcs(pI, 0); forAllRow(pProcs, pI, procI) pMin = Foam::min(pMin, pProcs(pI, procI)); - + if( pMin == Pstream::myProcNo() ) { ++nLocalPoints; @@ -195,7 +194,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const { ++nLocalPoints; } - + //- give local points their labels label startPoint(0); labelList nPointsAtProc(Pstream::nProcs()); @@ -204,23 +203,23 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const Pstream::scatterList(nPointsAtProc); for(label i=0;i<Pstream::myProcNo();++i) startPoint += nPointsAtProc[i]; - + forAll(localPoints, pI) if( localPoints[pI] ) globalPointLabel[pI] = startPoint++; - + //- send labels to non-local points do { finished = true; - + forAll(procBoundaries, patchI) { const std::map<label, std::pair<label, label> >& patchPointsMap = patchPoints[patchI]; std::map<label, std::pair<label, label> >::const_iterator it; - - labelListPMG dataToSend; + + labelLongList dataToSend; for(it=patchPointsMap.begin();it!=patchPointsMap.end();++it) { if( globalPointLabel[it->first] != -1 ) @@ -234,7 +233,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const dataToSend.append(globalPointLabel[it->first]); } } - + OPstream toOtherProc ( Pstream::blocking, @@ -243,7 +242,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const ); toOtherProc << dataToSend; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -253,16 +252,16 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { const face& f = faces[start+receivedData[counter++]]; const label pI = receivedData[counter++]; const label globalLabel = receivedData[counter++]; - + if( globalPointLabel[f[pI]] == -1 ) { globalPointLabel[f[pI]] = globalLabel; @@ -279,7 +278,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const } } } - + reduce(finished, minOp<bool>()); } while( !finished ); @@ -288,7 +287,7 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const if( pProcs.sizeOfRow(pointI) != 0 ) { globalToLocal.insert(globalPointLabel[pointI], pointI); - + forAllRow(pProcs, pointI, i) pNeiProcs.appendIfNotIn(pProcs(pointI, i)); } @@ -297,39 +296,39 @@ void polyMeshGenAddressing::calcGlobalPointLabels() const void polyMeshGenAddressing::calcGlobalFaceLabels() const { if( !globalFaceLabelPtr_ ) - globalFaceLabelPtr_ = new labelListPMG(); - labelListPMG& globalFaceLabel = *globalFaceLabelPtr_; + globalFaceLabelPtr_ = new labelLongList(); + labelLongList& globalFaceLabel = *globalFaceLabelPtr_; globalFaceLabel.setSize(mesh_.faces().size()); globalFaceLabel = -1; - + if( !Pstream::parRun() ) return; - + const label nIntFaces = mesh_.nInternalFaces(); - - const PtrList<writeProcessorPatch>& procBoundaries = + + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - + label nBoundaryFaces = 0; forAll(procBoundaries, patchI) { if( procBoundaries[patchI].owner() ) nBoundaryFaces += procBoundaries[patchI].patchSize(); } - + label startFace(0); labelList numberOfInternalFaces(Pstream::nProcs()); numberOfInternalFaces[Pstream::myProcNo()] = nIntFaces + nBoundaryFaces; - + Pstream::gatherList(numberOfInternalFaces); Pstream::scatterList(numberOfInternalFaces); for(label i=0;i<Pstream::myProcNo();++i) startFace += numberOfInternalFaces[i]; - + //- calculate labels for internal faces for(label faceI=0;faceI<nIntFaces;++faceI) globalFaceLabel[faceI] = startFace++; - + //- calculate labels for processor boundaries forAll(procBoundaries, patchI) { @@ -342,7 +341,7 @@ void polyMeshGenAddressing::calcGlobalFaceLabels() const globalFaceLabel[start+bfI] = startFace; dataToSend[bfI] = startFace++; } - + OPstream toOtherProc ( Pstream::blocking, @@ -352,7 +351,7 @@ void polyMeshGenAddressing::calcGlobalFaceLabels() const toOtherProc << dataToSend; } } - + forAll(procBoundaries, patchI) { if( !procBoundaries[patchI].owner() ) @@ -362,10 +361,10 @@ void polyMeshGenAddressing::calcGlobalFaceLabels() const Pstream::blocking, procBoundaries[patchI].neiProcNo() ); - + labelList receivedLabels; fromOtherProc >> receivedLabels; - + const label start = procBoundaries[patchI].patchStart(); forAll(receivedLabels, bfI) { @@ -373,13 +372,13 @@ void polyMeshGenAddressing::calcGlobalFaceLabels() const } } } - + //- create global labels for boundary faces startFace = 0; forAll(numberOfInternalFaces, procI) startFace += numberOfInternalFaces[procI]; - - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); labelListList numberOfBoundaryFaces(Pstream::nProcs()); numberOfBoundaryFaces[Pstream::myProcNo()].setSize(boundaries.size()); forAll(boundaries, patchI) @@ -389,18 +388,18 @@ void polyMeshGenAddressing::calcGlobalFaceLabels() const } Pstream::gatherList(numberOfBoundaryFaces); Pstream::scatterList(numberOfBoundaryFaces); - + forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); const label nBoundaryFaces = boundaries[patchI].patchSize(); - + for(label procI=0;procI<Pstream::myProcNo();++procI) startFace += numberOfBoundaryFaces[procI][patchI]; - + for(label bfI=0;bfI<nBoundaryFaces;++bfI) globalFaceLabel[start+bfI] = startFace++; - + for(label procI=Pstream::myProcNo()+1;procI<Pstream::nProcs();++procI) startFace += numberOfBoundaryFaces[procI][patchI]; } @@ -409,14 +408,14 @@ void polyMeshGenAddressing::calcGlobalFaceLabels() const void polyMeshGenAddressing::calcGlobalCellLabels() const { if( !globalCellLabelPtr_ ) - globalCellLabelPtr_ = new labelListPMG(); - labelListPMG& globalCellLabel = *globalCellLabelPtr_; + globalCellLabelPtr_ = new labelLongList(); + labelLongList& globalCellLabel = *globalCellLabelPtr_; globalCellLabel.setSize(mesh_.cells().size()); globalCellLabel = -1; - + if( !Pstream::parRun() ) return; - + label startLabel(0); labelList nCellsAtProc(Pstream::nProcs()); nCellsAtProc[Pstream::myProcNo()] = globalCellLabel.size(); @@ -424,7 +423,7 @@ void polyMeshGenAddressing::calcGlobalCellLabels() const Pstream::scatterList(nCellsAtProc); for(label i=0;i<Pstream::myProcNo();++i) startLabel += nCellsAtProc[i]; - + forAll(globalCellLabel, cellI) globalCellLabel[cellI] = startLabel++; } @@ -437,31 +436,31 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const "void polyMeshGenAddressing::calcGlobalEdgeLabels() const" ) << "Cannot calculate global edge addressing " << "for a serial run?!?!" << exit(FatalError); - + if( !globalEdgeLabelPtr_ ) - globalEdgeLabelPtr_ = new labelListPMG(); - labelListPMG& globalEdgeLabel = *globalEdgeLabelPtr_; + globalEdgeLabelPtr_ = new labelLongList(); + labelLongList& globalEdgeLabel = *globalEdgeLabelPtr_; globalEdgeLabel.setSize(this->edges().size()); globalEdgeLabel = -1; - + if( !eProcsPtr_ ) eProcsPtr_ = new VRWGraph(); VRWGraph& eProcs = *eProcsPtr_; eProcs.setSize(this->edges().size()); - + if( !globalToLocalEdgeAddressingPtr_ ) globalToLocalEdgeAddressingPtr_ = new Map<label>(); Map<label>& globalToLocal = *globalToLocalEdgeAddressingPtr_; - + if( !edgeNeiProcsPtr_ ) edgeNeiProcsPtr_ = new DynList<label>(); DynList<label>& eNeiProcs = *edgeNeiProcsPtr_; - + const faceListPMG& faces = mesh_.faces(); const VRWGraph& faceEdges = this->faceEdges(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - + //- find which processor contain a given bnd edge forAll(procBoundaries, patchI) { @@ -484,19 +483,19 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const } } } - + //- exchange data with other processor and update eProcs //- continue this process as long as there is some change bool finished; do { finished = true; - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - + /* label nToSend(0); for(label faceI=start;faceI<end;++faceI) { @@ -506,8 +505,8 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const nToSend += eProcs.sizeOfRow(faceEdges(faceI, eI)); } } -*/ - labelListPMG dataToSend; +*/ + labelLongList dataToSend; //nToSend = 0; for(label faceI=start;faceI<end;++faceI) { @@ -527,7 +526,7 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const dataToSend.append(eProcs(edgeI, i)); } } - + OPstream toOtherProc ( Pstream::blocking, @@ -536,7 +535,7 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const ); toOtherProc << dataToSend; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -546,17 +545,17 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { const label faceI = start+receivedData[counter++]; const label eI = receivedData[counter++]; - + const label edgeI = faceEdges(faceI, eI); - + const label nProcs = receivedData[counter++]; for(label i=0;i<nProcs;++i) { @@ -569,10 +568,10 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const } } } - + reduce(finished, minOp<bool>()); } while( !finished ); - + //- start calculating global edge labels label nLocalEdges(0); boolList localEdges(eProcs.size(), true); @@ -583,7 +582,7 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const forAllRow(eProcs, edgeI, procI) if( eProcs(edgeI, procI) < pMin ) pMin = eProcs(edgeI, procI); - + if( pMin == Pstream::myProcNo() ) { ++nLocalEdges; @@ -597,7 +596,7 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const { ++nLocalEdges; } - + //- give local points their labels label startEdge(0); labelList nEdgesAtProc(Pstream::nProcs()); @@ -606,7 +605,7 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const Pstream::scatterList(nEdgesAtProc); for(label i=0;i<Pstream::myProcNo();++i) startEdge += nEdgesAtProc[i]; - + forAll(localEdges, pI) if( localEdges[pI] ) globalEdgeLabel[pI] = startEdge++; @@ -615,13 +614,13 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const do { finished = true; - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - - labelListPMG dataToSend; + + labelLongList dataToSend; for(label faceI=start;faceI<end;++faceI) { forAllRow(faceEdges, faceI, eI) @@ -640,7 +639,7 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const } } } - + OPstream toOtherProc ( Pstream::blocking, @@ -649,7 +648,7 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const ); toOtherProc << dataToSend; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -659,19 +658,19 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { const label faceI = start+receivedData[counter++]; const label eI = receivedData[counter++]; - + const label edgeI = faceEdges(faceI, eI); - + const label globalLabel = receivedData[counter++]; - + if( globalEdgeLabel[edgeI] == -1 ) { globalEdgeLabel[edgeI] = globalLabel; @@ -688,16 +687,16 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const } } } - + reduce(finished, minOp<bool>()); } while( !finished ); - + //- create globalToLocal addressing forAll(eProcs, edgeI) if( eProcs.sizeOfRow(edgeI) != 0 ) { globalToLocal.insert(globalEdgeLabel[edgeI], edgeI); - + forAllRow(eProcs, edgeI, i) eNeiProcs.appendIfNotIn(eProcs(edgeI, i)); } @@ -705,83 +704,188 @@ void polyMeshGenAddressing::calcGlobalEdgeLabels() const // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // -const labelListPMG& polyMeshGenAddressing::globalPointLabel() const +const labelLongList& polyMeshGenAddressing::globalPointLabel() const { if( !globalPointLabelPtr_ || !pProcsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelLongList& polyMeshGenAddressing::" + "globalPointLabel() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalPointLabels(); - + } + return *globalPointLabelPtr_; } -const labelListPMG& polyMeshGenAddressing::globalFaceLabel() const +const labelLongList& polyMeshGenAddressing::globalFaceLabel() const { if( !globalFaceLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelLongList& polyMeshGenAddressing" + "::globalFaceLabel() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalFaceLabels(); - + } + return *globalFaceLabelPtr_; } -const labelListPMG& polyMeshGenAddressing::globalCellLabel() const +const labelLongList& polyMeshGenAddressing::globalCellLabel() const { if( !globalCellLabelPtr_ ) calcGlobalCellLabels(); - + return *globalCellLabelPtr_; } -const labelListPMG& polyMeshGenAddressing::globalEdgeLabel() const +const labelLongList& polyMeshGenAddressing::globalEdgeLabel() const { if( !globalEdgeLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelLongList& polyMeshGenAddressing" + "::globalEdgeLabel() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalEdgeLabels(); - + } + return *globalEdgeLabelPtr_; } const VRWGraph& polyMeshGenAddressing::pointAtProcs() const { if( !globalPointLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::pointAtProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalPointLabels(); - + } + return *pProcsPtr_; } const DynList<label>& polyMeshGenAddressing::pointNeiProcs() const { if( !pointNeiProcsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const DynList<label>& polyMeshGenAddressing" + "::pointNeiProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalPointLabels(); - + } + return *pointNeiProcsPtr_; } const Map<label>& polyMeshGenAddressing::globalToLocalPointAddressing() const { if( !globalToLocalPointAddressingPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const Map<label>& polyMeshGenAddressing" + "::globalToLocalPointAddressing() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalPointLabels(); - + } + return *globalToLocalPointAddressingPtr_; } const VRWGraph& polyMeshGenAddressing::edgeAtProcs() const { if( !globalEdgeLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::edgeAtProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalEdgeLabels(); - + } + return *eProcsPtr_; } const DynList<label>& polyMeshGenAddressing::edgeNeiProcs() const { if( !edgeNeiProcsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const DynList<label>& polyMeshGenAddressing::edgeNeiProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalEdgeLabels(); - + } + return *edgeNeiProcsPtr_; } const Map<label>& polyMeshGenAddressing::globalToLocalEdgeAddressing() const { if( !globalToLocalEdgeAddressingPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const Map<label>& polyMeshGenAddressing" + "::globalToLocalEdgeAddressing() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcGlobalEdgeLabels(); - + } + return *globalToLocalEdgeAddressingPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointCells.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointCells.C index 3ec1ae05c2e15efddc7ea707e3b4c4b938555b2b..c0d213a4b9593558ac1df0c598d9bd6d0b632df8 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -45,11 +44,11 @@ void polyMeshGenAddressing::calcPointCells() const else { const VRWGraph& cellPoints = this->cellPoints(); - + //- create the storage pcPtr_ = new VRWGraph(); VRWGraph& pointCellAddr = *pcPtr_; - + VRWGraphSMPModifier(pointCellAddr).reverseAddressing(cellPoints); pointCellAddr.setSize(mesh_.points().size()); } @@ -60,7 +59,18 @@ void polyMeshGenAddressing::calcPointCells() const const VRWGraph& polyMeshGenAddressing::pointCells() const { if( !pcPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::pointCells() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcPointCells(); + } return *pcPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointEdges.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointEdges.C index a43b22a3602a0396b2e028f5e51758b84688e3eb..1aa2eac7058cfcd7b6de0fd15487ea2cc094a122 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointEdges.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -61,6 +60,15 @@ const VRWGraph& polyMeshGenAddressing::pointEdges() const { if( !pePtr_ ) { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::pointEdges() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcPointEdges(); } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointFaces.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointFaces.C index 9d2f4741437a5c7cff08b86c5df6aa5b3a40550c..1fb1b518b9807786163e5a0fb303183a83d778d3 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointFaces.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -45,8 +44,8 @@ void polyMeshGenAddressing::calcPointFaces() const else { const faceListPMG& faces = mesh_.faces(); - const label nPoints = mesh_.points().size(); - + const label nPoints = mesh_.points().size(); + //- create the addressing pfPtr_ = new VRWGraph(); VRWGraph& pointFaceAddr = *pfPtr_; @@ -61,7 +60,18 @@ void polyMeshGenAddressing::calcPointFaces() const const VRWGraph& polyMeshGenAddressing::pointFaces() const { if( !pfPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::pointFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcPointFaces(); + } return *pfPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointPoints.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointPoints.C index dead65b4361e866f3dc9af8a68816d2a8a8cbb41..0ab46397b07badb24ce30f2471ad8001812769a0 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointPoints.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingPointPoints.C @@ -1,33 +1,34 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "polyMeshGenAddressing.H" #include "VRWGraphSMPModifier.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -50,23 +51,28 @@ void polyMeshGenAddressing::calcPointPoints() const VRWGraph& pp = *ppPtr_; const faceListPMG& faces = mesh_.faces(); - const VRWGraph& pointFaces = this->pointFaces(); - + const VRWGraph& pointFaces = this->pointFaces(); + labelList nPoints(pointFaces.size()); - - const label nThreads = 3 * omp_get_num_procs(); + # ifdef USE_OMP + const label nThreads = 3 * omp_get_num_procs(); # pragma omp parallel num_threads(nThreads) if( nPoints.size() > 10000 ) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(nPoints, i) nPoints[i] = 0; - + + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(pointFaces, pointI) { DynList<label, 32> helper; - + forAllRow(pointFaces, pointI, pfI) { const face& f = faces[pointFaces(pointI, pfI)]; @@ -75,34 +81,38 @@ void polyMeshGenAddressing::calcPointPoints() const helper.appendIfNotIn(f.prevLabel(pos)); helper.appendIfNotIn(f.nextLabel(pos)); } - + nPoints[pointI] = helper.size(); } - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp master + # endif VRWGraphSMPModifier(pp).setSizeAndRowSize(nPoints); - + + # ifdef USE_OMP # pragma omp barrier - + # pragma omp for schedule(static) + # endif forAll(pointFaces, pointI) { DynList<label, 32> helper; - + forAllRow(pointFaces, pointI, pfI) { const face& f = faces[pointFaces(pointI, pfI)]; - + const label pos = f.which(pointI); const label pLabel = f.prevLabel(pos); const label nLabel = f.nextLabel(pos); - + helper.appendIfNotIn(nLabel); helper.appendIfNotIn(pLabel); } - + pp.setRow(pointI, helper); } } @@ -114,7 +124,18 @@ void polyMeshGenAddressing::calcPointPoints() const const VRWGraph& polyMeshGenAddressing::pointPoints() const { if( !ppPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& polyMeshGenAddressing::pointPoints() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + calcPointPoints(); + } return *ppPtr_; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingUpdateGeometry.C b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingUpdateGeometry.C index 7b4f17fffa5b3eb793e866514016099d37232e0d..ff0f504ae985d877d98242a25d3083417b732554 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingUpdateGeometry.C +++ b/meshLibrary/utilities/meshes/polyMeshGenAddressing/polyMeshGenAddressingUpdateGeometry.C @@ -1,33 +1,34 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ #include "polyMeshGenAddressing.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +#endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -38,157 +39,161 @@ namespace Foam void polyMeshGenAddressing::updateGeometry ( - const boolList& changedFace + const boolList& changedFace ) { - const pointFieldPMG& p = mesh_.points(); - const faceListPMG& faces = mesh_.faces(); - - //- update face centres and face areas - if( faceCentresPtr_ && faceAreasPtr_ ) - { - vectorField& fCtrs = *faceCentresPtr_; - vectorField& fAreas = *faceAreasPtr_; - + const pointFieldPMG& p = mesh_.points(); + const faceListPMG& faces = mesh_.faces(); + + //- update face centres and face areas + if( faceCentresPtr_ && faceAreasPtr_ ) + { + vectorField& fCtrs = *faceCentresPtr_; + vectorField& fAreas = *faceAreasPtr_; + + # ifdef USE_OMP # pragma omp parallel for if( faces.size() > 100 ) \ schedule(dynamic, 10) - forAll(faces, faceI) - if( changedFace[faceI] ) - { - const face& f = faces[faceI]; - const label nPoints = f.size(); - - // If the face is a triangle, do a direct calculation for - // efficiency and to avoid round-off error-related problems - if (nPoints == 3) - { - fCtrs[faceI] = (1.0/3.0)*(p[f[0]] + p[f[1]] + p[f[2]]); - fAreas[faceI] = - 0.5*((p[f[1]] - p[f[0]])^(p[f[2]] - p[f[0]])); - } - else - { - vector sumN = vector::zero; - scalar sumA = 0.0; - vector sumAc = vector::zero; - - point fCentre = p[f[0]]; - for(label pI=1;pI<nPoints;++pI) - { - fCentre += p[f[pI]]; - } - - fCentre /= nPoints; - - for(label pI=0;pI<nPoints;++pI) - { - const point& nextPoint = p[f.nextLabel(pI)]; - - vector c = p[f[pI]] + nextPoint + fCentre; - vector n = (nextPoint - p[f[pI]])^(fCentre - p[f[pI]]); - scalar a = mag(n); - - sumN += n; - sumA += a; - sumAc += a*c; - } - - fCtrs[faceI] = (1.0/3.0)*sumAc/(sumA + VSMALL); - fAreas[faceI] = 0.5*sumN; - } - } - } - - //- update cell centres and cell volumes - if( cellCentresPtr_ && cellVolumesPtr_ && faceCentresPtr_ && faceAreasPtr_ ) - { - const vectorField& fCtrs = *faceCentresPtr_; - const vectorField& fAreas = *faceAreasPtr_; - vectorField& cellCtrs = *cellCentresPtr_; - scalarField& cellVols = *cellVolumesPtr_; - - const labelList& own = mesh_.owner(); - const cellListPMG& cells = mesh_.cells(); - + # endif + forAll(faces, faceI) + if( changedFace[faceI] ) + { + const face& f = faces[faceI]; + const label nPoints = f.size(); + + // If the face is a triangle, do a direct calculation for + // efficiency and to avoid round-off error-related problems + if (nPoints == 3) + { + fCtrs[faceI] = (1.0/3.0)*(p[f[0]] + p[f[1]] + p[f[2]]); + fAreas[faceI] = + 0.5*((p[f[1]] - p[f[0]])^(p[f[2]] - p[f[0]])); + } + else + { + vector sumN = vector::zero; + scalar sumA = 0.0; + vector sumAc = vector::zero; + + point fCentre = p[f[0]]; + for(label pI=1;pI<nPoints;++pI) + { + fCentre += p[f[pI]]; + } + + fCentre /= nPoints; + + for(label pI=0;pI<nPoints;++pI) + { + const point& nextPoint = p[f.nextLabel(pI)]; + + vector c = p[f[pI]] + nextPoint + fCentre; + vector n = (nextPoint - p[f[pI]])^(fCentre - p[f[pI]]); + scalar a = mag(n); + + sumN += n; + sumA += a; + sumAc += a*c; + } + + fCtrs[faceI] = (1.0/3.0)*sumAc/(sumA + VSMALL); + fAreas[faceI] = 0.5*sumN; + } + } + } + + //- update cell centres and cell volumes + if( cellCentresPtr_ && cellVolumesPtr_ && faceCentresPtr_ && faceAreasPtr_ ) + { + const vectorField& fCtrs = *faceCentresPtr_; + const vectorField& fAreas = *faceAreasPtr_; + vectorField& cellCtrs = *cellCentresPtr_; + scalarField& cellVols = *cellVolumesPtr_; + + const labelList& own = mesh_.owner(); + const cellListPMG& cells = mesh_.cells(); + + # ifdef USE_OMP # pragma omp parallel for if( cells.size() > 100 ) \ schedule(dynamic, 10) - forAll(cells, cellI) - { - const cell& c = cells[cellI]; - - bool update(false); - forAll(c, fI) - if( changedFace[c[fI]] ) - { - update = true; - break; - } - - if( update ) - { - cellCtrs[cellI] = vector::zero; - cellVols[cellI] = 0.0; - - //- estimate position of cell centre - vector cEst(vector::zero); - forAll(c, fI) - cEst += fCtrs[c[fI]]; - cEst /= c.size(); - - forAll(c, fI) - if( own[c[fI]] == cellI ) - { - // Calculate 3*face-pyramid volume - const scalar pyr3Vol = - max - ( - fAreas[c[fI]] & - ( - fCtrs[c[fI]] - - cEst - ), - VSMALL - ); - - // Calculate face-pyramid centre - const vector pc = - (3.0/4.0)*fCtrs[c[fI]] + (1.0/4.0)*cEst; - - // Accumulate volume-weighted face-pyramid centre - cellCtrs[cellI] += pyr3Vol*pc; - - // Accumulate face-pyramid volume - cellVols[cellI] += pyr3Vol; - } - else - { - // Calculate 3*face-pyramid volume - const scalar pyr3Vol = - max - ( - fAreas[c[fI]] & - ( - cEst - fCtrs[c[fI]] - ), - VSMALL - ); - - // Calculate face-pyramid centre - const vector pc = - (3.0/4.0)*fCtrs[c[fI]] + (1.0/4.0)*cEst; - - // Accumulate volume-weighted face-pyramid centre - cellCtrs[cellI] += pyr3Vol*pc; - - // Accumulate face-pyramid volume - cellVols[cellI] += pyr3Vol; - } - - cellCtrs[cellI] /= cellVols[cellI]; - cellVols[cellI] /= 3.0; - } - } - } + # endif + forAll(cells, cellI) + { + const cell& c = cells[cellI]; + + bool update(false); + forAll(c, fI) + if( changedFace[c[fI]] ) + { + update = true; + break; + } + + if( update ) + { + cellCtrs[cellI] = vector::zero; + cellVols[cellI] = 0.0; + + //- estimate position of cell centre + vector cEst(vector::zero); + forAll(c, fI) + cEst += fCtrs[c[fI]]; + cEst /= c.size(); + + forAll(c, fI) + if( own[c[fI]] == cellI ) + { + // Calculate 3*face-pyramid volume + const scalar pyr3Vol = + max + ( + fAreas[c[fI]] & + ( + fCtrs[c[fI]] - + cEst + ), + VSMALL + ); + + // Calculate face-pyramid centre + const vector pc = + (3.0/4.0)*fCtrs[c[fI]] + (1.0/4.0)*cEst; + + // Accumulate volume-weighted face-pyramid centre + cellCtrs[cellI] += pyr3Vol*pc; + + // Accumulate face-pyramid volume + cellVols[cellI] += pyr3Vol; + } + else + { + // Calculate 3*face-pyramid volume + const scalar pyr3Vol = + max + ( + fAreas[c[fI]] & + ( + cEst - fCtrs[c[fI]] + ), + VSMALL + ); + + // Calculate face-pyramid centre + const vector pc = + (3.0/4.0)*fCtrs[c[fI]] + (1.0/4.0)*cEst; + + // Accumulate volume-weighted face-pyramid centre + cellCtrs[cellI] += pyr3Vol*pc; + + // Accumulate face-pyramid volume + cellVols[cellI] += pyr3Vol; + } + + cellCtrs[cellI] /= cellVols[cellI]; + cellVols[cellI] /= 3.0; + } + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.C b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.C index b52d63330ad3681d50b7a335145f06f6cad78e8b..3cf3b5ba6358a11e4b23c610a30b087cf8afd8ac 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.C +++ b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -33,7 +32,9 @@ License #include "ListOps.H" #include "Map.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.H b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.H index 4eeade18023ff18881206cf1cf16d23d21d9d412..dc62e673f1eecb769b9e336e5e5e89abe9bffc12 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.H +++ b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecks.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenChecks diff --git a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksGeometry.C b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksGeometry.C index 792ece61a133ba5d0ed63bbe1d1d7c2f13429b74..fd6c06ea7b5adb4816a9112adc7fb79b260723c2 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksGeometry.C +++ b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksGeometry.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the origina author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -28,9 +27,10 @@ License #include "polyMeshGenAddressing.H" #include "pyramidPointFaceRef.H" #include "tetrahedron.H" -#include "mathematicalConstants.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -119,11 +119,13 @@ bool checkClosedCells { // Check that all cells labels are valid const cellListPMG& cells = mesh.cells(); - const label nFaces = mesh.faces().size(); + const label nFaces = mesh.faces().size(); label nErrorClosed = 0; + # ifdef USE_OMP # pragma omp parallel for schedule(guided) reduction(+ : nErrorClosed) + # endif forAll(cells, cI) { const cell& curCell = cells[cI]; @@ -139,7 +141,9 @@ bool checkClosedCells if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(cI); } @@ -174,10 +178,10 @@ bool checkClosedCells // Add to owner sumClosed[own[faceI]] += areas[faceI]; sumMagClosed[own[faceI]] += mag(areas[faceI]); - - if( nei[faceI] == -1 ) - continue; - + + if( nei[faceI] == -1 ) + continue; + // Subtract from neighbour sumClosed[nei[faceI]] -= areas[faceI]; sumMagClosed[nei[faceI]] += mag(areas[faceI]); @@ -333,7 +337,7 @@ bool checkCellVolumes "bool checkCellVolumes(" "const polyMeshGen&, const bool, labelHashSet*)" ) << "Zero or negative cell volume detected. " - << "Minimum negative volume: " + << "Minimum negative volume: " << minVolume << ".\nNumber of negative volume cells: " << nNegVolCells << ". This mesh is invalid" << endl; @@ -371,16 +375,20 @@ bool checkFaceAreas scalar minArea = VGREAT; scalar maxArea = -VGREAT; + # ifdef USE_OMP # pragma omp parallel if( own.size() > 100 ) + # endif { scalar localMaxArea(-VGREAT), localMinArea(VGREAT); - + + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(magFaceAreas, faceI) { if( changedFacePtr && !changedFacePtr->operator[](faceI) ) continue; - + if( magFaceAreas[faceI] < minFaceArea ) { if( report ) @@ -401,19 +409,23 @@ bool checkFaceAreas << magFaceAreas[faceI] << endl; } } - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } } - + localMinArea = Foam::min(localMinArea, magFaceAreas[faceI]); localMaxArea = Foam::max(localMaxArea, magFaceAreas[faceI]); } - + + # ifdef USE_OMP # pragma omp critical + # endif { minArea = Foam::min(minArea, localMinArea); maxArea = Foam::max(maxArea, localMaxArea); @@ -430,7 +442,7 @@ bool checkFaceAreas "bool checkFaceAreas(" "const polyMeshGen&, const bool, const scalar," " labelHashSet*, const boolList*)" - ) << "Zero or negative face area detected. Minimum negative area: " + ) << "Zero or negative face area detected. Minimum negative area: " << minArea << ". This mesh is invalid" << endl; @@ -462,23 +474,25 @@ bool checkCellPartTetrahedra const faceListPMG& faces = mesh.faces(); const labelList& owner = mesh.owner(); const labelList& neighbour = mesh.neighbour(); - + const vectorField& fCentres = mesh.addressingData().faceCentres(); const vectorField& cCentres = mesh.addressingData().cellCentres(); label nNegVolCells = 0; + # ifdef USE_OMP # pragma omp parallel for if( owner.size() > 100 ) \ schedule(guided) reduction(+ : nNegVolCells) + # endif forAll(owner, faceI) { if( changedFacePtr && !(*changedFacePtr)[faceI] ) continue; - + const face& f = faces[faceI]; - + bool badFace(false); - + forAll(f, eI) { const tetrahedron<point, point> tetOwn @@ -488,22 +502,24 @@ bool checkCellPartTetrahedra points[f[eI]], cCentres[owner[faceI]] ); - + if( tetOwn.mag() < minPartTet ) { if( report ) { + # ifdef USE_OMP # pragma omp critical + # endif Pout<< "Zero or negative cell volume detected for cell " << owner[faceI] << "." << endl; } - + badFace = true; } - + if( neighbour[faceI] < 0 ) continue; - + const tetrahedron<point, point> tetNei ( fCentres[faceI], @@ -511,70 +527,74 @@ bool checkCellPartTetrahedra points[f.nextLabel(eI)], cCentres[neighbour[faceI]] ); - + if( tetNei.mag() < minPartTet ) { if( report ) { + # ifdef USE_OMP # pragma omp critical + # endif Pout<< "Zero or negative cell volume detected for cell " << neighbour[faceI] << "." << endl; } - + badFace = true; } } - + if( badFace ) { if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } - + ++nNegVolCells; } } - + if( setPtr ) { //- ensure that faces are selected at both sides - const PtrList<writeProcessorPatch>& procBnd = mesh.procBoundaries(); + const PtrList<processorBoundaryPatch>& procBnd = mesh.procBoundaries(); forAll(procBnd, patchI) { const label start = procBnd[patchI].patchStart(); const label size = procBnd[patchI].patchSize(); - - labelListPMG sendData; + + labelLongList sendData; for(label faceI=0;faceI<size;++faceI) { if( setPtr->found(faceI+start) ) sendData.append(faceI); } - + OPstream toOtherProc ( Pstream::blocking, procBnd[patchI].neiProcNo(), sendData.byteSize() ); - + toOtherProc << sendData; } - + forAll(procBnd, patchI) { labelList receivedData; - + IPstream fromOtherProc ( Pstream::blocking, procBnd[patchI].neiProcNo() ); - + fromOtherProc >> receivedData; - + const label start = procBnd[patchI].patchStart(); forAll(receivedData, i) setPtr->insert(start+receivedData[i]); @@ -619,11 +639,11 @@ bool checkFaceDotProduct const labelList& own = mesh.owner(); const labelList& nei = mesh.neighbour(); - const label nInternalFaces = mesh.nInternalFaces(); + const label nInternalFaces = mesh.nInternalFaces(); // Severe nonorthogonality threshold const scalar severeNonorthogonalityThreshold = - ::cos(nonOrthWarn/180.0*mathematicalConstant::pi); + ::cos(nonOrthWarn/180.0*M_PI); scalar minDDotS = VGREAT; scalar sumDDotS = 0.0; @@ -632,18 +652,25 @@ bool checkFaceDotProduct label errorNonOrth = 0; label counter = 0; + # ifdef USE_OMP # pragma omp parallel if( nInternalFaces > 1000 ) \ reduction(+ : severeNonOrth, errorNonOrth, sumDDotS) + # endif { scalar localMinDDotS(VGREAT); + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif for(label faceI=0;faceI<nInternalFaces;++faceI) { + if( changedFacePtr && !(*changedFacePtr)[faceI] ) + continue; + const vector d = centres[nei[faceI]] - centres[own[faceI]]; const vector& s = areas[faceI]; - + scalar dDotS = (d & s)/(mag(d)*mag(s) + VSMALL); - + if( dDotS < severeNonorthogonalityThreshold ) { if( dDotS > SMALL ) @@ -651,68 +678,76 @@ bool checkFaceDotProduct if( report ) { // Severe non-orthogonality but mesh still OK + # ifdef USE_OMP # pragma omp critical + # endif Pout<< "Severe non-orthogonality for face " << faceI << " between cells " << own[faceI] << " and " << nei[faceI] << ": Angle = " - << ::acos(dDotS)/mathematicalConstant::pi*180.0 + << ::acos(dDotS)/M_PI*180.0 << " deg." << endl; } - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } - + ++severeNonOrth; } else { ++errorNonOrth; - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } } } - + localMinDDotS = Foam::min(dDotS, localMinDDotS); sumDDotS += dDotS; } - + + # ifdef USE_OMP # pragma omp critical + # endif minDDotS = Foam::min(minDDotS, localMinDDotS); } - + counter += nInternalFaces; - + if( Pstream::parRun() ) { - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh.procBoundaries(); - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); - + vectorField cCentres(procBoundaries[patchI].patchSize()); forAll(cCentres, faceI) cCentres[faceI] = centres[own[start+faceI]]; - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), cCentres.byteSize() ); - + toOtherProc << cCentres; } - + forAll(procBoundaries, patchI) { vectorField otherCentres; @@ -721,25 +756,31 @@ bool checkFaceDotProduct Pstream::blocking, procBoundaries[patchI].neiProcNo() ); - + fromOtherProc >> otherCentres; - + //- calculate skewness at processor faces const label start = procBoundaries[patchI].patchStart(); + # ifdef USE_OMP # pragma omp parallel \ reduction(+ : severeNonOrth, errorNonOrth, sumDDotS) + # endif { scalar localMinDDotS(VGREAT); + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(otherCentres, faceI) { + if( changedFacePtr && !(*changedFacePtr)[start+faceI] ) + continue; const point& cOwn = centres[own[start+faceI]]; const point& cNei = otherCentres[faceI]; const vector d = cNei - cOwn; const vector& s = areas[start+faceI]; - + const scalar dDotS = (d & s)/(mag(d)*mag(s) + VSMALL); - + if( dDotS < severeNonorthogonalityThreshold ) { if( dDotS > SMALL ) @@ -747,12 +788,14 @@ bool checkFaceDotProduct if( report ) { // Severe non-orthogonality but mesh still OK + # ifdef USE_OMP # pragma omp critical + # endif { const scalar angle ( Foam::acos(dDotS) / - mathematicalConstant::pi * 180.0 + M_PI * 180.0 ); Pout<< "Severe non-orthogonality for face " << start+faceI @@ -761,40 +804,46 @@ bool checkFaceDotProduct << " deg." << endl; } } - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(start+faceI); } - + ++severeNonOrth; } else { ++errorNonOrth; - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(start+faceI); } } } - + localMinDDotS = Foam::min(dDotS, localMinDDotS); sumDDotS += 0.5 * dDotS; } - + + # ifdef USE_OMP # pragma omp critical + # endif minDDotS = Foam::min(sumDDotS, localMinDDotS); } - + if( procBoundaries[patchI].owner() ) counter += otherCentres.size(); } } - + reduce(minDDotS, minOp<scalar>()); reduce(sumDDotS, sumOp<scalar>()); reduce(severeNonOrth, sumOp<label>()); @@ -818,9 +867,9 @@ bool checkFaceDotProduct if( counter > 0 ) { Info<< "Mesh non-orthogonality Max: " - << ::acos(minDDotS)/mathematicalConstant::pi*180.0 + << ::acos(minDDotS)/M_PI*180.0 << " average: " << - ::acos(sumDDotS/counter)/mathematicalConstant::pi*180.0 + ::acos(sumDDotS/counter)/M_PI*180.0 << endl; } } @@ -865,26 +914,30 @@ bool checkFacePyramids label nErrorPyrs = 0; + # ifdef USE_OMP # pragma omp parallel for schedule(guided) reduction(+ : nErrorPyrs) + # endif forAll(faces, faceI) { - if( changedFacePtr && !(*changedFacePtr)[faceI] ) - continue; - + if( changedFacePtr && !(*changedFacePtr)[faceI] ) + continue; + // Create the owner pyramid - it will have negative volume const scalar pyrVol = pyramidPointFaceRef - ( - faces[faceI], - ctrs[owner[faceI]] - ).mag(points); - + ( + faces[faceI], + ctrs[owner[faceI]] + ).mag(points); + bool badFace(false); if( pyrVol > -minPyrVol ) { if( report ) { + # ifdef USE_OMP # pragma omp critical + # endif Pout<< "bool checkFacePyramids(" << "const bool, const scalar, labelHashSet*) : " << "face " << faceI << " points the wrong way. " << endl @@ -914,7 +967,9 @@ bool checkFacePyramids { if( report ) { + # ifdef USE_OMP # pragma omp critical + # endif Pout<< "bool checkFacePyramids(" << "const bool, const scalar, labelHashSet*) : " << "face " << faceI << " points the wrong way. " << endl @@ -930,50 +985,52 @@ bool checkFacePyramids badFace = true; } } - + if( badFace ) { if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } - + ++nErrorPyrs; } } reduce(nErrorPyrs, sumOp<label>()); - + if( setPtr ) { //- make sure that processor faces are marked on both sides - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh.procBoundaries(); - + //- send and receive data where needed forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label size = procBoundaries[patchI].patchSize(); - - labelListPMG markedFaces; + + labelLongList markedFaces; for(label faceI=0;faceI<size;++faceI) { if( setPtr->found(start+faceI) ) markedFaces.append(faceI); } - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), markedFaces.byteSize() ); - + toOtherProc << markedFaces; } - + forAll(procBoundaries, patchI) { labelList receivedData; @@ -983,7 +1040,7 @@ bool checkFacePyramids procBoundaries[patchI].neiProcNo() ); fromOtheProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); forAll(receivedData, i) setPtr->insert(start+receivedData[i]); @@ -1026,7 +1083,7 @@ bool checkFaceSkewness //- larger than the face area vector const labelList& own = mesh.owner(); const labelList& nei = mesh.neighbour(); - const label nInternalFaces = mesh.nInternalFaces(); + const label nInternalFaces = mesh.nInternalFaces(); const vectorField& centres = mesh.addressingData().cellCentres(); const vectorField& fCentres = mesh.addressingData().faceCentres(); @@ -1037,99 +1094,113 @@ bool checkFaceSkewness label nWarnSkew = 0; //- check internal faces + # ifdef USE_OMP # pragma omp parallel \ reduction(+ : sumSkew, counter, nWarnSkew) + # endif { scalar localMaxSkew(0.0); - - # pragma omp for schedule(guided) + + # ifdef USE_OMP + # pragma omp for schedule(guided) + # endif for(label faceI=0;faceI<nInternalFaces;++faceI) { if( changedFacePtr && !changedFacePtr->operator[](faceI) ) continue; - + const scalar dOwn = mag(fCentres[faceI] - centres[own[faceI]]); const scalar dNei = mag(fCentres[faceI] - centres[nei[faceI]]); - + const point faceIntersection = centres[own[faceI]]*dNei/(dOwn+dNei) + centres[nei[faceI]]*dOwn/(dOwn+dNei); - - const scalar skewness = + + const scalar skewness = mag(fCentres[faceI] - faceIntersection) /(mag(centres[nei[faceI]] - centres[own[faceI]]) + VSMALL); - + // Check if the skewness vector is greater than the PN vector. if( skewness > warnSkew ) { if( report ) { + # ifdef USE_OMP # pragma omp critical + # endif Pout<< " Severe skewness for face " << faceI << " skewness = " << skewness << endl; } - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } - + ++nWarnSkew; } - + localMaxSkew = Foam::max(localMaxSkew, skewness); sumSkew += skewness; ++counter; } - + + # ifdef USE_OMP # pragma omp critical + # endif maxSkew = Foam::max(maxSkew, localMaxSkew); } - + if( Pstream::parRun() ) { //- check parallel boundaries - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh.procBoundaries(); - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); - + vectorField cCentres(procBoundaries[patchI].patchSize()); forAll(cCentres, faceI) cCentres[faceI] = centres[own[start+faceI]]; - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), cCentres.byteSize() ); - + toOtherProc << cCentres; } - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); - + vectorField otherCentres; IPstream fromOtheProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo() ); - + fromOtheProc >> otherCentres; - + //- calculate skewness at processor faces + # ifdef USE_OMP # pragma omp parallel reduction(+ : nWarnSkew, sumSkew) + # endif { scalar localMaxSkew(0.0); - + + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(otherCentres, faceI) { if( @@ -1137,66 +1208,72 @@ bool checkFaceSkewness !changedFacePtr->operator[](start+faceI) ) continue; - + const point& cOwn = centres[own[start+faceI]]; const point& cNei = otherCentres[faceI]; const scalar dOwn = mag(fCentres[start+faceI] - cOwn); const scalar dNei = mag(fCentres[start+faceI] - cNei); - + const point faceIntersection = cOwn*dNei/(dOwn+dNei) + cNei*dOwn/(dOwn+dNei); - - const scalar skewness = + + const scalar skewness = mag(fCentres[start+faceI] - faceIntersection) /(mag(cOwn - cNei) + VSMALL); - + //- Check if the skewness vector is greater //- than the PN vector. if( skewness > warnSkew ) { if( report ) { + # ifdef USE_OMP # pragma omp critical + # endif Pout<< " Severe skewness for face " << start+faceI << " skewness = " << skewness << endl; } - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(start+faceI); } ++nWarnSkew; } - + localMaxSkew = Foam::max(localMaxSkew, skewness); sumSkew += 0.5 * skewness; } - + + # ifdef USE_OMP # pragma omp critical + # endif maxSkew = Foam::max(maxSkew, localMaxSkew); } - + if( procBoundaries[patchI].owner() ) counter += otherCentres.size(); } } - + //- boundary faces const faceListPMG& faces = mesh.faces(); const pointFieldPMG& points = mesh.points(); - const PtrList<writePatch>& boundaries = mesh.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh.boundaries(); forAll(boundaries, patchI) { label faceI = boundaries[patchI].patchStart(); const label end = faceI + boundaries[patchI].patchSize(); - + for(;faceI<end;++faceI) { const vector d = fCentres[faceI] - centres[own[faceI]]; - + vector n = faces[faceI].normal(points); const scalar magn = mag(n); if( magn > VSMALL ) @@ -1207,11 +1284,11 @@ bool checkFaceSkewness { continue; } - + const vector dn = (n & d) * n; - + const scalar skewness = mag(d - dn) / (mag(d) + VSMALL); - + maxSkew = Foam::max(maxSkew, skewness); sumSkew += skewness; ++counter; @@ -1264,7 +1341,7 @@ bool checkFaceUniformity const labelList& owner = mesh.owner(); const labelList& neighbour = mesh.neighbour(); - const label nInternalFaces = mesh.nInternalFaces(); + const label nInternalFaces = mesh.nInternalFaces(); scalar maxUniformity = 0.0; scalar minUniformity = VGREAT; @@ -1273,18 +1350,22 @@ bool checkFaceUniformity label severeNonUniform = 0; + # ifdef USE_OMP # pragma omp parallel \ reduction(+ : sumUniformity, severeNonUniform) + # endif { scalar localMinUniformity(VGREAT); scalar localMaxUniformity(0.0); - + + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif for(label faceI=0;faceI<nInternalFaces;++faceI) { if( changedFacePtr && !changedFacePtr->operator[](faceI) ) continue; - + const scalar dOwn ( Foam::mag(centres[owner[faceI]] - fCentres[faceI]) @@ -1293,73 +1374,77 @@ bool checkFaceUniformity ( Foam::mag(centres[neighbour[faceI]] - fCentres[faceI]) ); - + const scalar uniformity = Foam::min(dOwn, dNei) / (dOwn + dNei); - + if( uniformity < warnUniform ) { if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } - + ++severeNonUniform; } - + localMaxUniformity = Foam::max(localMaxUniformity, uniformity); localMinUniformity = Foam::min(localMinUniformity, uniformity); sumUniformity += uniformity; } - + + # ifdef USE_OMP # pragma omp critical + # endif { maxUniformity = Foam::max(maxUniformity, localMaxUniformity); minUniformity = Foam::min(minUniformity, localMinUniformity); } } - + label counter = nInternalFaces; - + if( Pstream::parRun() ) { - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh.procBoundaries(); - + forAll(procBoundaries, patchI) { scalarField dst(procBoundaries[patchI].patchSize()); const label start = procBoundaries[patchI].patchStart(); - + forAll(dst, faceI) { const label fI = start + faceI; dst[faceI] = Foam::mag(centres[owner[fI]] - fCentres[fI]); } - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), dst.byteSize() ); - + toOtherProc << dst; } - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); - + scalarField otherDst; IPstream fromOtheProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo() ); - + fromOtheProc >> otherDst; - + forAll(otherDst, faceI) { const label fI = start + faceI; @@ -1372,15 +1457,15 @@ bool checkFaceUniformity { if( setPtr) setPtr->insert(start+faceI); - + ++severeNonUniform; } - + maxUniformity = Foam::max(maxUniformity, uniformity); minUniformity = Foam::min(minUniformity, uniformity); sumUniformity += 0.5 * uniformity; } - + if( procBoundaries[patchI].owner() ) counter += otherDst.size(); } @@ -1433,7 +1518,7 @@ bool checkFaceAngles << abort(FatalError); } - const scalar maxSin = Foam::sin(maxDeg/180.0*mathematicalConstant::pi); + const scalar maxSin = Foam::sin(maxDeg/180.0*M_PI); const pointFieldPMG& points = mesh.points(); const faceListPMG& faces = mesh.faces(); @@ -1444,39 +1529,43 @@ bool checkFaceAngles label nConcave = 0; + # ifdef USE_OMP # pragma omp parallel reduction(+ : nConcave) + # endif { scalar localMaxEdgeSin(0.0); label errorFaceI(-1); - + + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(faces, faceI) { if( changedFacePtr && !changedFacePtr->operator[](faceI) ) continue; - + const face& f = faces[faceI]; - + // Get edge from f[0] to f[size-1]; vector ePrev(points[f[0]] - points[f[f.size()-1]]); scalar magEPrev = mag(ePrev); ePrev /= magEPrev + VSMALL; - + forAll(f, fp0) { // Get vertex after fp label fp1 = f.fcIndex(fp0); - + // Normalized vector between two consecutive points vector e10(points[f[fp1]] - points[f[fp0]]); scalar magE10 = mag(e10); e10 /= magE10 + VSMALL; - + if( magEPrev > SMALL && magE10 > SMALL ) { vector edgeNormal = ePrev ^ e10; scalar magEdgeNormal = mag(edgeNormal); - + if( magEdgeNormal < maxSin ) { // Edges (almost) aligned -> face is ok. @@ -1485,10 +1574,12 @@ bool checkFaceAngles { // Check normal edgeNormal /= magEdgeNormal; - + if( (edgeNormal & faceNormals[faceI]) < SMALL ) { + # ifdef USE_OMP # pragma omp critical + # endif { if( faceI != errorFaceI ) { @@ -1496,23 +1587,25 @@ bool checkFaceAngles errorFaceI = faceI; ++nConcave; } - + if( setPtr ) setPtr->insert(faceI); - + localMaxEdgeSin = Foam::max(localMaxEdgeSin, magEdgeNormal); } } } } - + ePrev = e10; magEPrev = magE10; } } - + + # ifdef USE_OMP # pragma omp critical + # endif maxEdgeSin = Foam::max(maxEdgeSin, localMaxEdgeSin); } @@ -1525,7 +1618,7 @@ bool checkFaceAngles { scalar maxConcaveDegr = Foam::asin(Foam::min(1.0, maxEdgeSin)) - * 180.0/mathematicalConstant::pi; + * 180.0/M_PI; Warning<< "There are " << nConcave << " faces with concave angles between consecutive" @@ -1568,7 +1661,7 @@ bool checkFaceFlatness const bool report, const scalar warnFlatness, labelHashSet* setPtr, - const boolList* changedFacePtr + const boolList* changedFacePtr ) { if( warnFlatness < 0 || warnFlatness > 1 ) @@ -1596,81 +1689,89 @@ bool checkFaceFlatness scalar sumFlatness = 0; label nSummed = 0; + # ifdef USE_OMP # pragma omp parallel if( faces.size() > 1000 ) \ reduction(+ : nSummed, nWarped) reduction(+ : sumFlatness) + # endif { scalar minFlatnessProc = VGREAT; - + + # ifdef USE_OMP # pragma omp for schedule(guided) + # endif forAll(faces, faceI) { if( changedFacePtr && !(*changedFacePtr)[faceI] ) continue; - + const face& f = faces[faceI]; - + if( f.size() > 3 && magAreas[faceI] > VSMALL ) { const point& fc = fctrs[faceI]; - + //- Calculate the sum of magnitude of areas and compare //- the magnitude of sum of areas. - + scalar sumA = 0.0; - + forAll(f, fp) { const point& thisPoint = points[f[fp]]; const point& nextPoint = points[f.nextLabel(fp)]; - + // Triangle around fc. vector n = 0.5*((nextPoint - thisPoint)^(fc - thisPoint)); sumA += mag(n); } - + scalar flatness = magAreas[faceI] / (sumA+VSMALL); - + sumFlatness += flatness; ++nSummed; - + minFlatnessProc = Foam::min(minFlatnessProc, flatness); - + if( flatness < warnFlatness ) { ++nWarped; - + if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(faceI); } } } } - + + # ifdef USE_OMP # pragma omp critical + # endif { minFlatness = Foam::min(minFlatness, minFlatnessProc); } } - + if( Pstream::parRun() && setPtr ) { //- make sure that processor faces are marked on both sides - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh.procBoundaries(); - + List<DynList<label> > markedFaces(procBoundaries.size()); forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label size = procBoundaries[patchI].patchSize(); - + for(label i=0;i<size;++i) if( setPtr->found(start+i) ) markedFaces[patchI].append(i); } - + //- exchange list sizes forAll(procBoundaries, patchI) { @@ -1680,10 +1781,10 @@ bool checkFaceFlatness procBoundaries[patchI].neiProcNo(), sizeof(label) ); - + toOtherProc << markedFaces[patchI].size(); } - + labelList nMarkedOnOtherProcs(procBoundaries.size()); forAll(procBoundaries, patchI) { @@ -1693,31 +1794,31 @@ bool checkFaceFlatness procBoundaries[patchI].neiProcNo(), sizeof(label) ); - + fromOtheProc >> nMarkedOnOtherProcs[patchI]; } - + //- exchange data forAll(procBoundaries, patchI) { if( markedFaces[patchI].size() == 0 ) continue; - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), markedFaces[patchI].byteSize() ); - + toOtherProc << markedFaces[patchI]; } - + forAll(procBoundaries, patchI) { if( nMarkedOnOtherProcs[patchI] == 0 ) continue; - + labelList receivedData; IPstream fromOtheProc ( @@ -1726,7 +1827,7 @@ bool checkFaceFlatness nMarkedOnOtherProcs[patchI]*sizeof(label) ); fromOtheProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); forAll(receivedData, i) if( !setPtr->found(start+receivedData[i]) ) diff --git a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksTopology.C b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksTopology.C index c2767cfea45e02db688d990ea0868440710a1050..c58ea1d134757f7248b9d7cf2bb3f9989b976ee4 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksTopology.C +++ b/meshLibrary/utilities/meshes/polyMeshGenChecks/polyMeshGenChecksTopology.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\ / A nd | Copyright held by the original author \\/ M anipulation | ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -29,7 +28,9 @@ License #include "cell.H" #include "Map.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -176,7 +177,7 @@ bool checkUpperTriangular forAllRow(cc, cellI, nbrI) { - const label neiI = cc(cellI, nbrI); + const label neiI = cc(cellI, nbrI); if( (neiI > cellI) && !usedNbr[nbrI] && (neiI < minNei) ) { nextNei = nbrI; @@ -261,7 +262,9 @@ bool checkCellsZipUp const faceListPMG& faces = mesh.faces(); const cellListPMG& cells = mesh.cells(); + # ifdef USE_OMP # pragma omp parallel for schedule(guided) reduction(+ : nOpenCells) + # endif forAll(cells, cellI) { const labelList& c = cells[cellI]; @@ -278,7 +281,7 @@ bool checkCellsZipUp const edge e = f.faceEdge(eI); const label pos = cellEdges.containsAtPosition(e); - + if( pos < 0 ) { cellEdges.append(e); @@ -291,7 +294,7 @@ bool checkCellsZipUp } } - DynList<edge> singleEdges(cellEdges.size()); + DynList<edge> singleEdges; forAll(edgeUsage, edgeI) { @@ -312,7 +315,9 @@ bool checkCellsZipUp if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(cellI); } } @@ -330,7 +335,9 @@ bool checkCellsZipUp if( setPtr ) { + # ifdef USE_OMP # pragma omp critical + # endif setPtr->insert(cellI); } @@ -373,7 +380,7 @@ bool checkFaceVertices const faceListPMG& faces = mesh.faces(); label nErrorFaces = 0; - const label nPoints = mesh.points().size(); + const label nPoints = mesh.points().size(); forAll(faces, fI) { diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifier.H b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifier.H index 5143a405f193dbc67f12ef6cccc806a95b8e9eb1..da22fa2f48be040dd37a2d2f29023eea3a1ec46b 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifier.H +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifier.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenModifier @@ -124,13 +123,13 @@ public: }; //- access to processor boundary data - inline PtrList<writeProcessorPatch>& procBoundariesAccess() + inline PtrList<processorBoundaryPatch>& procBoundariesAccess() { return mesh_.procBoundaries_; } //- access to boundary data - inline PtrList<writePatch>& boundariesAccess() + inline PtrList<boundaryPatch>& boundariesAccess() { return mesh_.boundaries_; } @@ -165,15 +164,15 @@ public: ( const wordList& patchNames, const VRWGraph& boundaryFaces, - const labelListPMG& faceOwners, - const labelListPMG& facePatches + const labelLongList& faceOwners, + const labelLongList& facePatches ); //- add additional faces into processor patches void addProcessorFaces ( const VRWGraph& procFaces, - const labelListPMG& facePatches + const labelLongList& facePatches ); //- add new processor patch and return its label diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddBufferCells.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddBufferCells.C index 61e53a9b0d416c5d6a18c724f2aca50eb8c5f324..13f28d50dbbdc6a91852f4e5ffeed27ac8c2f7c9 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddBufferCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddBufferCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -52,9 +51,9 @@ void polyMeshGenModifier::addBufferCells() pointFieldPMG& points = mesh_.points(); faceListPMG& faces = facesAccess(); const cellListPMG& cells = mesh_.cells(); - const PtrList<writeProcessorPatch>& procBoundaries = mesh_.procBoundaries(); + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); const polyMeshGenAddressing& addressing = mesh_.addressingData(); - const labelListPMG& globalPointLabel = addressing.globalPointLabel(); + const labelLongList& globalPointLabel = addressing.globalPointLabel(); const Map<label>& globalToLocal = addressing.globalToLocalPointAddressing(); //- receive vertices @@ -133,7 +132,7 @@ void polyMeshGenModifier::addBufferCells() for(;faceI<end;++faceI) cellsToSend.insert(owner[faceI]); - labelListPMG flattenedCells; + labelLongList flattenedCells; forAllConstIter(labelHashSet, cellsToSend, it) { const cell& c = cells[it.key()]; diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.C index 5821a78f787b2fa2b0f03369e907e4a35b24bb20..7f20878654a80ee4bcdd03d352cfe1e29a29e277 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,82 +35,82 @@ namespace Foam polyMeshGenModifierAddCellByCell::polyMeshGenModifierAddCellByCell ( - polyMeshGen& mesh + polyMeshGen& mesh ) : - polyMeshGenModifier(mesh), - nFaces_(mesh.faces().size()), - newFaces_(nFaces_), - nCells_(mesh.cells().size()), - newCells_(nCells_) + polyMeshGenModifier(mesh), + nFaces_(mesh.faces().size()), + newFaces_(nFaces_), + nCells_(mesh.cells().size()), + newCells_(nCells_) { this->pointFaces(); - faceListPMG& faces = this->facesAccess(); - forAll(faces, faceI) - newFaces_[faceI].transfer(faces[faceI]); - - cellListPMG& cells = this->cellsAccess(); - forAll(cells, cellI) - newCells_[cellI].transfer(cells[cellI]); + faceListPMG& faces = this->facesAccess(); + forAll(faces, faceI) + newFaces_[faceI].transfer(faces[faceI]); + + cellListPMG& cells = this->cellsAccess(); + forAll(cells, cellI) + newCells_[cellI].transfer(cells[cellI]); }; - + // Destructor polyMeshGenModifierAddCellByCell::~polyMeshGenModifierAddCellByCell() { - faceListPMG& faces = this->facesAccess(); - faces.setSize(nFaces_); - forAll(faces, faceI) - faces[faceI].transfer(newFaces_[faceI]); - - cellListPMG& cells = this->cellsAccess(); - cells.setSize(newCells_.size()); - forAll(cells, cellI) - cells[cellI].transfer(newCells_[cellI]); + faceListPMG& faces = this->facesAccess(); + faces.setSize(nFaces_); + forAll(faces, faceI) + faces[faceI].transfer(newFaces_[faceI]); + + cellListPMG& cells = this->cellsAccess(); + cells.setSize(newCells_.size()); + forAll(cells, cellI) + cells[cellI].transfer(newCells_[cellI]); } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void polyMeshGenModifierAddCellByCell::addCell(const faceList& cellFaces) { - cell c(cellFaces.size()); - - VRWGraph& pointFaces = this->pointFaces(); - - forAll(cellFaces, faceI) - { - const face& f = cellFaces[faceI]; - - const label pointI = f[0]; - - label fLabel(-1); - forAllRow(pointFaces, pointI, pfI) - { - const label faceI = pointFaces(pointI, pfI); - - if( newFaces_[faceI] == f ) - { - fLabel = faceI; - break; - } - } - - if( fLabel == -1 ) - { - newFaces_.append(f); - c[faceI] = nFaces_; - forAll(f, pI) - pointFaces.append(f[pI], nFaces_); - - ++nFaces_; - } - else - { - c[faceI] = fLabel; - } - } - - newCells_.append(c); - ++nCells_; + cell c(cellFaces.size()); + + VRWGraph& pointFaces = this->pointFaces(); + + forAll(cellFaces, faceI) + { + const face& f = cellFaces[faceI]; + + const label pointI = f[0]; + + label fLabel(-1); + forAllRow(pointFaces, pointI, pfI) + { + const label faceI = pointFaces(pointI, pfI); + + if( newFaces_[faceI] == f ) + { + fLabel = faceI; + break; + } + } + + if( fLabel == -1 ) + { + newFaces_.append(f); + c[faceI] = nFaces_; + forAll(f, pI) + pointFaces.append(f[pI], nFaces_); + + ++nFaces_; + } + else + { + c[faceI] = fLabel; + } + } + + newCells_.append(c); + ++nCells_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.H b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.H index fd5bd9e4d914a6bf9a241b6a9b44062a77d3b0f6..4621422b46a4f9d22eafb1b4e3bf591d47188b1a 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.H +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCellByCell.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class polyMeshGenModifierAddCellByCell @@ -48,27 +47,27 @@ namespace Foam class polyMeshGenModifierAddCellByCell : public polyMeshGenModifier { - // Private data - //- number of faces - label nFaces_; - LongList<face> newFaces_; - - //- number of cells - label nCells_; - LongList<cell> newCells_; + // Private data + //- number of faces + label nFaces_; + LongList<face> newFaces_; + + //- number of cells + label nCells_; + LongList<cell> newCells_; public: - // Constructors - //- Construct from the reference to the mesh - polyMeshGenModifierAddCellByCell(polyMeshGen& mesh); - - // Destructor - ~polyMeshGenModifierAddCellByCell(); - - // Member functions - //- add a single cell (vertices must be added); - void addCell(const faceList& cell); + // Constructors + //- Construct from the reference to the mesh + polyMeshGenModifierAddCellByCell(polyMeshGen& mesh); + + // Destructor + ~polyMeshGenModifierAddCellByCell(); + + // Member functions + //- add a single cell (vertices must be added); + void addCell(const faceList& cell); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCells.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCells.C index 48da16dedd0a804218ef2f91472f4d77064bc831..9ede384259e438437e7669e557e1c2b307532f9c 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddProcessorFaces.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddProcessorFaces.C index d4889b9af348a9b30d7f729bc8ea67c8d9fd5574..62f7c38f504e7117e5237678161c390ce624302a 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddProcessorFaces.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierAddProcessorFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,9 @@ Description #include "polyMeshGenModifier.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif namespace Foam { @@ -39,12 +40,12 @@ namespace Foam void polyMeshGenModifier::addProcessorFaces ( const VRWGraph& procFaces, - const labelListPMG& facePatches + const labelLongList& facePatches ) { Info << "Adding processor faces" << endl; - PtrList<writeProcessorPatch>& procBoundaries = mesh_.procBoundaries_; + PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries_; labelList nAddedFaces(procBoundaries.size(), 0); forAll(facePatches, fI) @@ -65,12 +66,12 @@ void polyMeshGenModifier::addProcessorFaces label endProcFaces(0); forAllReverse(procBoundaries, patchI) { - const writeProcessorPatch& wp = procBoundaries[patchI]; + const processorBoundaryPatch& wp = procBoundaries[patchI]; endProcFaces = Foam::max(endProcFaces, wp.patchStart()+wp.patchSize()); } //- move faces to their new positions - labelListPMG newFaceLabel(nFaces, -1); + labelLongList newFaceLabel(nFaces, -1); if( endProcFaces != nFaces ) { @@ -116,7 +117,9 @@ void polyMeshGenModifier::addProcessorFaces //- renumber cells cellListPMG& cells = mesh_.cells_; + # ifdef USE_OMP # pragma omp parallel for schedule(guided) + # endif forAll(cells, cellI) { cell& c = cells[cellI]; @@ -137,7 +140,7 @@ label polyMeshGenModifier::addProcessorPatch(const label otherProcLabel) { const label nProcPatches = mesh_.procBoundaries().size(); - PtrList<writeProcessorPatch>& procBoundaries = + PtrList<processorBoundaryPatch>& procBoundaries = this->procBoundariesAccess(); procBoundaries.setSize(nProcPatches + 1); @@ -151,7 +154,7 @@ label polyMeshGenModifier::addProcessorPatch(const label otherProcLabel) procBoundaries.set ( nProcPatches, - new writeProcessorPatch + new processorBoundaryPatch ( name, "processor", @@ -167,7 +170,7 @@ label polyMeshGenModifier::addProcessorPatch(const label otherProcLabel) bool polyMeshGenModifier::removeEmptyProcessorPatches() { - PtrList<writeProcessorPatch>& procBoundaries = + PtrList<processorBoundaryPatch>& procBoundaries = this->procBoundariesAccess(); label nValidPatches(0); @@ -180,7 +183,7 @@ bool polyMeshGenModifier::removeEmptyProcessorPatches() if( nValidPatches == procBoundaries.size() ) return false; - PtrList<writeProcessorPatch> newProcBoundaries(nValidPatches); + PtrList<processorBoundaryPatch> newProcBoundaries(nValidPatches); nValidPatches = 0; forAll(procBoundaries, patchI) @@ -190,7 +193,7 @@ bool polyMeshGenModifier::removeEmptyProcessorPatches() newProcBoundaries.set ( nValidPatches++, - new writeProcessorPatch(procBoundaries[patchI]) + new processorBoundaryPatch(procBoundaries[patchI]) ); } } diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveCells.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveCells.C index 19bfe2e9447da1a3ee065984e30a012e617365d4..760fc288ff4ed2449f8060d85ebba1e77932e599 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,9 @@ Description #include "polyMeshGenModifier.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif namespace Foam { @@ -42,75 +43,81 @@ void polyMeshGenModifier::removeCells const bool removeProcFaces ) { - Info << "Removing selected cells from the mesh" << endl; + Info << "Removing selected cells from the mesh" << endl; - //mesh_.clearOut(); + //mesh_.clearOut(); - faceListPMG& faces = mesh_.faces_; - cellListPMG& cells = mesh_.cells_; + faceListPMG& faces = mesh_.faces_; + cellListPMG& cells = mesh_.cells_; - if( removeCell.size() != cells.size() ) - { - Info << "Size of cells " << cells.size() << endl; - Info << "Size of list for removal " << removeCell.size() << endl; - FatalErrorIn - ( - "void polyMeshGenModifier::removeCells(const boolList& removeCell)" - ) << "Incorrect number of entries in removeCell list!" - << abort(FatalError); - } + if( removeCell.size() != cells.size() ) + { + Info << "Size of cells " << cells.size() << endl; + Info << "Size of list for removal " << removeCell.size() << endl; + FatalErrorIn + ( + "void polyMeshGenModifier::removeCells(const boolList& removeCell)" + ) << "Incorrect number of entries in removeCell list!" + << abort(FatalError); + } - //- flip internal faces which will become boundary ones - const labelList& owner = mesh_.owner(); - const labelList& neighbour = mesh_.neighbour(); + //- flip internal faces which will become boundary ones + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) - forAll(faces, faceI) - { - if( neighbour[faceI] == -1 ) + # endif + forAll(faces, faceI) + { + if( neighbour[faceI] == -1 ) { faceI = faces.size(); - continue; + continue; } - if( removeCell[owner[faceI]] && !removeCell[neighbour[faceI]] ) - faces[faceI] = faces[faceI].reverseFace(); - } + if( removeCell[owner[faceI]] && !removeCell[neighbour[faceI]] ) + faces[faceI] = faces[faceI].reverseFace(); + } - mesh_.clearOut(); + mesh_.clearOut(); - //- remove unwanted cells - label nCells(0); - labelListPMG newCellLabel(cells.size(), -1); - forAll(newCellLabel, cellI) - if( !removeCell[cellI] ) - newCellLabel[cellI] = nCells++; + //- remove unwanted cells + label nCells(0); + labelLongList newCellLabel(cells.size(), -1); + forAll(newCellLabel, cellI) + if( !removeCell[cellI] ) + newCellLabel[cellI] = nCells++; - forAll(cells, cellI) - if( (newCellLabel[cellI] != -1) && (newCellLabel[cellI] < cellI) ) - { - cells[newCellLabel[cellI]].transfer(cells[cellI]); - } + forAll(cells, cellI) + if( (newCellLabel[cellI] != -1) && (newCellLabel[cellI] < cellI) ) + { + cells[newCellLabel[cellI]].transfer(cells[cellI]); + } - cells.setSize(nCells); + cells.setSize(nCells); //- update cell subsets in the mesh mesh_.updateCellSubsets(newCellLabel); reduce(nCells, sumOp<label>()); - Info << "New cells size " << nCells << endl; + Info << "New cells size " << nCells << endl; - //- reorder positions of boundary faces + //- reorder positions of boundary faces //- this outs the newly-created bnd faces at the end of the list - this->reorderBoundaryFaces(); + this->reorderBoundaryFaces(); mesh_.clearOut(); - //- remove unused faces - boolList removeFace(faces.size(), true); + //- remove unused faces + boolList removeFace(faces.size(), true); + # ifdef USE_OMP # pragma omp parallel if( cells.size() > 1000 ) + # endif { + # ifdef USE_OMP # pragma omp for schedule(dynamic, 40) + # endif forAll(cells, cellI) { const cell& c = cells[cellI]; @@ -121,18 +128,20 @@ void polyMeshGenModifier::removeCells if( Pstream::parRun() && !removeProcFaces ) { - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries_; + # ifdef USE_OMP # pragma omp for + # endif for(label fI=procBoundaries[0].patchStart();fI<faces.size();++fI) removeFace[fI] = false; } } - mesh_.clearOut(); + mesh_.clearOut(); - this->removeFaces(removeFace); + this->removeFaces(removeFace); Info << "Finished removing selected cells from the mesh" << endl; } diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveFaces.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveFaces.C index b15501385fa0fc6bf29436993b2716e8bdde1c3f..be0cc13474eb3b6ce69d38fa44d652f60c41a9a8 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveFaces.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,9 @@ Description #include "polyMeshGenModifier.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif namespace Foam { @@ -38,61 +39,61 @@ namespace Foam void polyMeshGenModifier::removeFaces(const boolList& removeFace) { - //mesh_.clearOut(); + //mesh_.clearOut(); Info << "Removing faces" << endl; - faceListPMG& faces = mesh_.faces_; - cellListPMG& cells = mesh_.cells_; + faceListPMG& faces = mesh_.faces_; + cellListPMG& cells = mesh_.cells_; - label nFaces(0); - labelListPMG newFaceLabel(faces.size(), -1); + label nFaces(0); + labelLongList newFaceLabel(faces.size(), -1); - //- copy internal faces + //- copy internal faces const label nInternalFaces = mesh_.nInternalFaces(); for(label faceI=0;faceI<nInternalFaces;++faceI) if( !removeFace[faceI] ) - { - if( nFaces < faceI ) - faces[nFaces].transfer(faces[faceI]); + { + if( nFaces < faceI ) + faces[nFaces].transfer(faces[faceI]); newFaceLabel[faceI] = nFaces; - ++nFaces; + ++nFaces; } - //- copy boundary faces - PtrList<writePatch>& boundaries = mesh_.boundaries_; - labelList patchStart(boundaries.size()); - labelList nFacesInPatch(boundaries.size()); - label npI(0); - forAll(boundaries, patchI) - { - const label oldStart = boundaries[patchI].patchStart(); - const label oldNumFacesInPatch = boundaries[patchI].patchSize(); - - patchStart[npI] = nFaces; - nFacesInPatch[npI] = 0; - - for(label faceI=0;faceI<oldNumFacesInPatch;++faceI) - if( !removeFace[oldStart+faceI] ) - { - ++nFacesInPatch[npI]; - if( nFaces < (oldStart+faceI) ) - faces[nFaces].transfer(faces[oldStart+faceI]); - newFaceLabel[oldStart+faceI] = nFaces++; - } + //- copy boundary faces + PtrList<boundaryPatch>& boundaries = mesh_.boundaries_; + labelList patchStart(boundaries.size()); + labelList nFacesInPatch(boundaries.size()); + label npI(0); + forAll(boundaries, patchI) + { + const label oldStart = boundaries[patchI].patchStart(); + const label oldNumFacesInPatch = boundaries[patchI].patchSize(); + + patchStart[npI] = nFaces; + nFacesInPatch[npI] = 0; + + for(label faceI=0;faceI<oldNumFacesInPatch;++faceI) + if( !removeFace[oldStart+faceI] ) + { + ++nFacesInPatch[npI]; + if( nFaces < (oldStart+faceI) ) + faces[nFaces].transfer(faces[oldStart+faceI]); + newFaceLabel[oldStart+faceI] = nFaces++; + } ++npI; - } + } - forAll(boundaries, patchI) - { - boundaries[patchI].patchStart() = patchStart[patchI]; - boundaries[patchI].patchSize() = nFacesInPatch[patchI]; - } + forAll(boundaries, patchI) + { + boundaries[patchI].patchStart() = patchStart[patchI]; + boundaries[patchI].patchSize() = nFacesInPatch[patchI]; + } if( Pstream::parRun() ) { - PtrList<writeProcessorPatch>& procBoundaries = + PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries_; label nProcFaces(0); @@ -124,11 +125,11 @@ void polyMeshGenModifier::removeFaces(const boolList& removeFace) removeProcFace[faceI] = true; OPstream toOtherProc - ( + ( Pstream::blocking, - procBoundaries[patchI].neiProcNo(), - removeProcFace.byteSize() - ); + procBoundaries[patchI].neiProcNo(), + removeProcFace.byteSize() + ); toOtherProc << removeProcFace; } @@ -217,8 +218,10 @@ void polyMeshGenModifier::removeFaces(const boolList& removeFace) //- update face subsets in the mesh mesh_.updateFaceSubsets(newFaceLabel); - //- change cells + //- change cells + # ifdef USE_OMP # pragma omp parallel for if( cells.size() > 1000 ) schedule(dynamic, 40) + # endif forAll(cells, cellI) { cell& c = cells[cellI]; @@ -235,7 +238,7 @@ void polyMeshGenModifier::removeFaces(const boolList& removeFace) c[fI] = newC[fI]; } - mesh_.clearOut(); + mesh_.clearOut(); Info << "Finished removing faces" << endl; } @@ -246,7 +249,7 @@ void polyMeshGenModifier::removeDuplicateFaces() faceListPMG& faces = mesh_.faces_; - labelListPMG newFaceLabel(faces.size(), -1); + labelLongList newFaceLabel(faces.size(), -1); label nFaces(0); forAll(faces, faceI) @@ -289,7 +292,7 @@ void polyMeshGenModifier::removeDuplicateFaces() //- update boundary faces (they cannot be duplicated) forAll(mesh_.boundaries_, patchI) { - writePatch& patch = mesh_.boundaries_[patchI]; + boundaryPatch& patch = mesh_.boundaries_[patchI]; const label start = patch.patchStart(); const label end = start + patch.patchSize(); @@ -305,7 +308,7 @@ void polyMeshGenModifier::removeDuplicateFaces() //- update processor faces (they cannot be duplicated) forAll(mesh_.procBoundaries_, patchI) { - writeProcessorPatch& patch = mesh_.procBoundaries_[patchI]; + processorBoundaryPatch& patch = mesh_.procBoundaries_[patchI]; const label start = patch.patchStart(); const label end = start + patch.patchSize(); @@ -323,7 +326,9 @@ void polyMeshGenModifier::removeDuplicateFaces() //- change cells cellListPMG& cells = mesh_.cells_; + # ifdef USE_OMP # pragma omp parallel for if( cells.size() > 1000 ) schedule(dynamic, 40) + # endif forAll(cells, cellI) { cell& c = cells[cellI]; @@ -340,7 +345,7 @@ void polyMeshGenModifier::removeDuplicateFaces() c[fI] = newC[fI]; } - mesh_.clearOut(); + mesh_.clearOut(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveUnusedVertices.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveUnusedVertices.C index a35feae506bed398b2da1bdc1b81bb22aa75e8c4..d24926217f02624c9c81330309c5efe237360210 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveUnusedVertices.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRemoveUnusedVertices.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -49,7 +48,7 @@ void polyMeshGenModifier::removeUnusedVertices() usePoint[f[pI]] = true; } - labelListPMG newLabel(points.size(), -1); + labelLongList newLabel(points.size(), -1); label nPoints(0); forAll(points, pI) if( usePoint[pI] ) @@ -74,7 +73,7 @@ void polyMeshGenModifier::removeUnusedVertices() mesh_.updatePointSubsets(newLabel); - mesh_.clearOut(); + mesh_.clearOut(); this->clearOut(); } diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRenumberMesh.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRenumberMesh.C index 6e11f655076478a45b3038d835f04e9c9a25f8ef..283ae469c1460881694f5f1a370850c62b69f639 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRenumberMesh.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierRenumberMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -51,7 +50,7 @@ void polyMeshGenModifier::renumberMesh() const VRWGraph& cellCells = mesh_.addressingData().cellCells(); //- the business bit of the renumbering - labelListPMG nextCell; + labelLongList nextCell; boolList visited(cellCells.size(), false); @@ -112,7 +111,7 @@ void polyMeshGenModifier::renumberMesh() cellList newCells(oldCells.size()); //- The reverse order list gives the new cell label for every old cell - labelListPMG reverseOrder(newOrder.size()); + labelLongList reverseOrder(newOrder.size()); forAll(newOrder, cellI) { @@ -123,7 +122,7 @@ void polyMeshGenModifier::renumberMesh() //- Renumber the faces. //- Reverse face order gives the new face number for every old face - labelListPMG reverseFaceOrder(oldOwner.size(), 0); + labelLongList reverseFaceOrder(oldOwner.size(), 0); //- Mark the internal faces with -2 so that they are inserted first forAll(newCells, cellI) @@ -225,7 +224,7 @@ void polyMeshGenModifier::renumberMesh() } //- Face order gives the old face label for every new face - labelListPMG faceOrder(reverseFaceOrder.size()); + labelLongList faceOrder(reverseFaceOrder.size()); forAll(faceOrder, faceI) { @@ -243,7 +242,7 @@ void polyMeshGenModifier::renumberMesh() } } - faceListPMG& oldFaces = this->facesAccess(); + faceListPMG& oldFaces = this->facesAccess(); faceList newFaces(oldFaces.size()); forAll(newFaces, faceI) @@ -280,7 +279,7 @@ void polyMeshGenModifier::renumberMesh() this->clearOut(); mesh_.clearOut(); - Info << "Finished renumbering the mesh" << endl; + Info << "Finished renumbering the mesh" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReorderBoundaryFaces.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReorderBoundaryFaces.C index 70e441e762ba23d476a0caa9ae76f0c69f7b2b57..b5d45e85d93d925093c290708bf4f4956269cb44 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReorderBoundaryFaces.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReorderBoundaryFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,9 @@ Description #include "polyMeshGenModifier.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif // #define DEBUGSearch @@ -56,28 +57,40 @@ void polyMeshGenModifier::reorderBoundaryFaces() //- count internal and boundary faces const label numBFaces = faces.size() - nInternalFaces; - labelListPMG newFaceLabel(faces.size(), -1); + labelLongList newFaceLabel(faces.size(), -1); //- find faces which should be repositioned label nReplaced(0); labelList internalToChange; labelList boundaryToChange; + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); + # else + const label nThreads(1); + # endif labelList nInternalToChangeThread(nThreads); labelList nBoundaryToChangeThread(nThreads); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); + # else + const label threadI = 0; + # endif label& nItc = nInternalToChangeThread[threadI]; label& nBtc = nBoundaryToChangeThread[threadI]; - labelListPMG internalToChangeLocal, boundaryToChangeLocal; + labelLongList internalToChangeLocal, boundaryToChangeLocal; //- find the boundary faces within the range of internal faces + # ifdef USE_OMP # pragma omp for schedule(static) + # endif for(label faceI=0;faceI<nInternalFaces;++faceI) { if( neighbour[faceI] == -1 ) @@ -87,7 +100,9 @@ void polyMeshGenModifier::reorderBoundaryFaces() nItc = internalToChangeLocal.size(); //- find the internal faces within the range of boundary faces + # ifdef USE_OMP # pragma omp for schedule(static) + # endif for(label faceI=nInternalFaces;faceI<faces.size();++faceI) { if( neighbour[faceI] != -1 ) @@ -98,18 +113,24 @@ void polyMeshGenModifier::reorderBoundaryFaces() //- perform reduction such that all threads know how many faces //- need to be swapped + # ifdef USE_OMP # pragma omp critical + # endif nReplaced += nBtc; + # ifdef USE_OMP # pragma omp barrier # pragma omp master + # endif { internalToChange.setSize(nReplaced); boundaryToChange.setSize(nReplaced); } + # ifdef USE_OMP # pragma omp barrier + # endif label localStart(0); for(label i=0;i<threadI;++i) @@ -125,10 +146,12 @@ void polyMeshGenModifier::reorderBoundaryFaces() forAll(boundaryToChangeLocal, i) boundaryToChange[localStart++] = boundaryToChangeLocal[i]; + # ifdef USE_OMP # pragma omp barrier //- start moving positions of faces # pragma omp for schedule(static) + # endif forAll(internalToChange, fI) { //- swap with the face at the location the face should be @@ -140,10 +163,12 @@ void polyMeshGenModifier::reorderBoundaryFaces() newFaceLabel[boundaryToChange[fI]] = internalToChange[fI]; } + # ifdef USE_OMP # pragma omp barrier //- renumber cells # pragma omp for schedule(dynamic, 40) + # endif forAll(cells, cellI) { cell& c = cells[cellI]; @@ -155,7 +180,7 @@ void polyMeshGenModifier::reorderBoundaryFaces() } //- re-create boundary data - PtrList<writePatch>& boundaries = mesh_.boundaries_; + PtrList<boundaryPatch>& boundaries = mesh_.boundaries_; if( boundaries.size() != 1 ) { boundaries.clear(); @@ -163,7 +188,7 @@ void polyMeshGenModifier::reorderBoundaryFaces() boundaries.set ( 0, - new writePatch + new boundaryPatch ( "defaultFaces", "patch", @@ -200,7 +225,7 @@ void polyMeshGenModifier::reorderBoundaryFaces() void polyMeshGenModifier::reorderProcBoundaryFaces() { - PtrList<writeProcessorPatch>& procBoundaries = mesh_.procBoundaries_; + PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries_; if( procBoundaries.size() == 0 ) { Warning << "Processor " << Pstream::myProcNo() << " has no " @@ -228,7 +253,7 @@ void polyMeshGenModifier::reorderProcBoundaryFaces() "void polyMeshGenModifier::reorderProcBoundaryFaces()" ) << "Missing some faces!" << abort(FatalError); - labelListPMG newFaceLabel(faces.size(), -1); + labelLongList newFaceLabel(faces.size(), -1); //- faces added after processor boundaries should be moved up front faceList facesAtEnd(shift); @@ -263,7 +288,7 @@ void polyMeshGenModifier::reorderProcBoundaryFaces() } //- set correct patch size - PtrList<writePatch>& boundaries = mesh_.boundaries_; + PtrList<boundaryPatch>& boundaries = mesh_.boundaries_; if( boundaries.size() == 1 ) { boundaries[0].patchSize() = @@ -278,7 +303,7 @@ void polyMeshGenModifier::reorderProcBoundaryFaces() boundaries.set ( 0, - new writePatch + new boundaryPatch ( "defaultFaces", "patch", @@ -289,14 +314,16 @@ void polyMeshGenModifier::reorderProcBoundaryFaces() } //- renumber cells + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(cells, cellI) { cell& c = cells[cellI]; forAll(c, fI) - if( newFaceLabel[c[fI]] != -1 ) - c[fI] = newFaceLabel[c[fI]]; + if( newFaceLabel[c[fI]] != -1 ) + c[fI] = newFaceLabel[c[fI]]; } //- update face subsets diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReplaceBoundary.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReplaceBoundary.C index 254944b5491cf561de206035a8f53c9b1d33f92c..76ec5d9ea54ab4a5c12b3b82e6580848cafb82c4 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReplaceBoundary.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierReplaceBoundary.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,8 +42,8 @@ void polyMeshGenModifier::replaceBoundary ( const wordList& patchNames, const VRWGraph& boundaryFaces, - const labelListPMG& faceOwners, - const labelListPMG& facePatches + const labelLongList& faceOwners, + const labelLongList& facePatches ) { const label nIntFaces = mesh_.nInternalFaces(); @@ -52,14 +51,14 @@ void polyMeshGenModifier::replaceBoundary faceListPMG& faces = this->facesAccess(); cellListPMG& cells = this->cellsAccess(); - labelListPMG newFaceLabel(faces.size(), -1); + labelLongList newFaceLabel(faces.size(), -1); for(label faceI=0;faceI<nIntFaces;++faceI) newFaceLabel[faceI] = faceI; if( Pstream::parRun() ) { //- shift processor faces - PtrList<writeProcessorPatch>& procBoundaries = + PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries_; label nProcFaces(0); @@ -159,7 +158,7 @@ void polyMeshGenModifier::replaceBoundary forAll(cells, cellI) cells[cellI].setSize(nFacesInCell[cellI]); - PtrList<writePatch>& boundaries = mesh_.boundaries_; + PtrList<boundaryPatch>& boundaries = mesh_.boundaries_; if( boundaries.size() == patchNames.size() ) { forAll(boundaries, patchI) @@ -177,7 +176,7 @@ void polyMeshGenModifier::replaceBoundary boundaries.set ( patchI, - new writePatch + new boundaryPatch ( patchNames[patchI], "patch", diff --git a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierZipUpCells.C b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierZipUpCells.C index f9ee23abb6a1602ce2d5dc151788edd078fb1dc0..bde99de060263f7742de5ab9bac28e0956c0ae23 100644 --- a/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierZipUpCells.C +++ b/meshLibrary/utilities/meshes/polyMeshGenModifier/polyMeshGenModifierZipUpCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,14 +41,14 @@ namespace Foam void polyMeshGenModifier::zipUpCells() { - this->clearOut(); - + this->clearOut(); + Info<< "Zipping up topologically open cells" << endl; - - const pointFieldPMG& points = mesh_.points(); - const cellListPMG& cells = mesh_.cells(); - - faceListPMG& faces = mesh_.faces_; + + const pointFieldPMG& points = mesh_.points(); + const cellListPMG& cells = mesh_.cells(); + + faceListPMG& faces = mesh_.faces_; // Algorithm: // Take the original mesh and visit all cells. For every cell @@ -78,34 +77,34 @@ void polyMeshGenModifier::zipUpCells() do { nChangedFacesInMesh = 0; - + //- calculate pointFaces addressing # ifdef DEBUG_ZIPUP Info << "Starting pointFaces addressing " << endl; # endif - List<direction> nUsage(points.size(), direction(0)); - forAll(faces, fI) - { - const face& f = faces[fI]; - forAll(f, pI) - ++nUsage[f[pI]]; - } - - VRWGraph pFaces(points.size()); - forAll(nUsage, pI) - pFaces.setRowSize(pI, nUsage[pI]); - - nUsage = 0; - - forAll(faces, fI) - { - const face& f = faces[fI]; - forAll(f, pI) - pFaces(f[pI], nUsage[f[pI]]++) = fI; - } - - nUsage.clear(); + List<direction> nUsage(points.size(), direction(0)); + forAll(faces, fI) + { + const face& f = faces[fI]; + forAll(f, pI) + ++nUsage[f[pI]]; + } + + VRWGraph pFaces(points.size()); + forAll(nUsage, pI) + pFaces.setRowSize(pI, nUsage[pI]); + + nUsage = 0; + + forAll(faces, fI) + { + const face& f = faces[fI]; + forAll(f, pI) + pFaces(f[pI], nUsage[f[pI]]++) = fI; + } + + nUsage.clear(); # ifdef DEBUG_ZIPUP Info << "Starting zipping cells " << endl; @@ -551,21 +550,21 @@ void polyMeshGenModifier::zipUpCells() // In order to avoid edge-to-edge comparison, get faces using // point-face addressing in two goes. - const label start = testEdge.start(); - const label end = testEdge.end(); - - labelList facesSharingEdge - ( - pFaces.sizeOfRow(start) + - pFaces.sizeOfRow(end) - ); + const label start = testEdge.start(); + const label end = testEdge.end(); + + labelList facesSharingEdge + ( + pFaces.sizeOfRow(start) + + pFaces.sizeOfRow(end) + ); label nfse = 0; - - forAllRow(pFaces, start, pfI) - facesSharingEdge[nfse++] = pFaces(start, pfI); - - forAllRow(pFaces, end, pfI) - facesSharingEdge[nfse++] = pFaces(end, pfI); + + forAllRow(pFaces, start, pfI) + facesSharingEdge[nfse++] = pFaces(start, pfI); + + forAllRow(pFaces, end, pfI) + facesSharingEdge[nfse++] = pFaces(end, pfI); forAll(facesSharingEdge, faceI) { @@ -709,13 +708,13 @@ void polyMeshGenModifier::zipUpCells() nNewFacePoints++; } } - - forAll(newFace, pI) - pFaces.appendIfNotIn - ( - newFace[pI], - currentFaceIndex - ); + + forAll(newFace, pI) + pFaces.appendIfNotIn + ( + newFace[pI], + currentFaceIndex + ); # ifdef DEBUG_ZIPUP Info<< "oldFace: " diff --git a/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubset.H b/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubset.H index fc17c5092981a2ef5c05211d3fe476e01dabc3fc..836d84758f8411c644e22c24c70ddd3b16f007cd 100644 --- a/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubset.H +++ b/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubset.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSubset @@ -54,28 +53,32 @@ class VRWGraph; class meshSubset { - // Private data + // Private data //- name of the given subset word name_; - + //- type of subset label type_; - + //- labels of elements HashSet<label> data_; public: - + // Enumerators enum subsetType_ { + UNKNOWN = 0, CELLSUBSET = 1, FACESUBSET = 2, - POINTSUBSET = 4 + POINTSUBSET = 4, + FEATUREEDGESUBSET = 8 }; // Constructors + //- Null constructor + inline meshSubset(); //- Construct from name. Creates an empty subset inline meshSubset(const word& name, const subsetType_&); @@ -89,8 +92,14 @@ public: const ListType& elements ); - // Destructor - ~meshSubset(); + //- Copy construct + inline meshSubset(const meshSubset&); + + //- Construct from Istream + inline meshSubset(Istream&); + + // Destructor + ~meshSubset(); // Member Functions @@ -99,7 +108,7 @@ public: //- Return name inline const word& name() const; - + //- Type of subset inline label type() const; @@ -108,30 +117,37 @@ public: inline void containedElements(ListType&) const; // Edit - + //- add element label to subset inline void addElement(const label); - + //- remove element from subset inline void removeElement(const label); - + //- update subset after mesh modification //- the list contains new labels of mesh elements //- removed elements have a negative label template<class ListType> inline void updateSubset(const ListType&); - + //- update subset after modification //- this modifier is used in case when elements are decomposed inline void updateSubset(const VRWGraph&); - - // Searches - //- find if the element exists in the subset - inline bool contains(const label) const; + + // Searches + //- find if the element exists in the subset + inline bool contains(const label) const; + + // operators + + inline void operator=(const meshSubset&); + inline bool operator==(const meshSubset&) const; + inline bool operator!=(const meshSubset&) const; // IOstream operators - friend Ostream& operator<<(Ostream&, const meshSubset&); + friend inline Ostream& operator<<(Ostream&, const meshSubset&); + friend inline Istream& operator>>(Istream&, meshSubset&); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubsetI.H b/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubsetI.H index 6a9d987cf1f1bdf89868bfd2b6055d4b00e7f537..630ae2e0c5c00e9152ca43a27d1ea680ddbbc213 100644 --- a/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubsetI.H +++ b/meshLibrary/utilities/meshes/primitives/meshSubsets/meshSubsetI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,6 +35,13 @@ namespace Foam // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // +inline meshSubset::meshSubset() +: + name_(), + type_(UNKNOWN), + data_() +{} + inline meshSubset::meshSubset ( const word& name, @@ -62,11 +68,29 @@ inline meshSubset::meshSubset forAll(elements, i) data_.insert(elements[i]); } - -inline meshSubset::~meshSubset() + +inline meshSubset::meshSubset(const meshSubset& ms) +: + name_(ms.name_), + type_(ms.type_), + data_() +{ + forAllConstIter(HashSet<label>, ms.data_, it) + data_.insert(it.key()); +} + +inline meshSubset::meshSubset(Istream& is) +: + name_(), + type_(UNKNOWN), + data_() { + is >> *this; } +inline meshSubset::~meshSubset() +{} + // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // inline const word& meshSubset::name() const @@ -83,7 +107,7 @@ template<class ListType> inline void meshSubset::containedElements(ListType& l) const { l.setSize(data_.size()); - + label counter(0); forAllConstIter(HashSet<label>, data_, it) l[counter++] = it.key(); @@ -103,31 +127,33 @@ template<class ListType> inline void meshSubset::updateSubset(const ListType& newLabels) { HashSet<label> newData; - + forAllConstIter(HashSet<label>, data_, it) { if( newLabels[it.key()] < 0 ) continue; - + newData.insert(newLabels[it.key()]); } - + data_.clear(); - data_ = newData; + forAllConstIter(HashSet<label>, newData, it) + data_.insert(it.key()); } inline void meshSubset::updateSubset(const VRWGraph& newLabels) { HashSet<label> newData; - + forAllConstIter(HashSet<label>, data_, it) { forAllRow(newLabels, it.key(), i) newData.insert(newLabels(it.key(), i)); } - + data_.clear(); - data_ = newData; + forAllConstIter(HashSet<label>, newData, it) + data_.insert(it.key()); } inline bool meshSubset::contains(const label elmt) const @@ -135,15 +161,57 @@ inline bool meshSubset::contains(const label elmt) const return data_.found(elmt); } +inline void meshSubset::operator=(const meshSubset& ms) +{ + name_ = ms.name_; + type_ = ms.type_; + + data_.clear(); + forAllConstIter(HashSet<label>, ms.data_, it) + data_.insert(it.key()); +} + +inline bool meshSubset::operator==(const meshSubset& ms) const +{ + if( ms.name_ != name_ ) + return false; + if( ms.type_ != ms.type_ ) + return false; + + forAllConstIter(HashSet<label>, data_, it) + if( !ms.data_.found(it.key()) ) + return false; + + return true; +} + +inline bool meshSubset::operator!=(const meshSubset& ms) const +{ + return !operator==(ms); +} + // * * * * * * * * * * * * * * * Ostream Operator * * * * * * * * * * * * * // inline Ostream& operator<<(Ostream& os, const meshSubset& sel) { + os.check("inline Ostream& operator<<(Ostream&, const meshSubset&)"); + os << sel.name_ << nl << sel.type_ << nl << sel.data_; return os; } +inline Istream& operator>>(Istream& is, meshSubset& sel) +{ + is.check("friend Istream& operator>>(Istream&, meshSubset&)"); + + is >> sel.name_ >> sel.type_ >> sel.data_; + + is.check("friend Istream& operator>>(Istream&, meshSubset&)"); + + return is; +} + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/primitives/partTet/partTet.H b/meshLibrary/utilities/meshes/primitives/partTet/partTet.H index ae57a545592adea4f6012bb80c58e30a0414c300..b96aa3131d9aefbbbe082dae6c20aaedda85d3dc 100644 --- a/meshLibrary/utilities/meshes/primitives/partTet/partTet.H +++ b/meshLibrary/utilities/meshes/primitives/partTet/partTet.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class partTet @@ -55,15 +54,15 @@ class Ostream; class partTet { protected: - - // Protected data + + // Protected data label data_[4]; public: // Constructors - //- Null construct - inline partTet(); + //- Null construct + inline partTet(); //- Construct from point labels inline partTet @@ -74,8 +73,8 @@ public: const label d ); - // Destructor - ~partTet(); + // Destructor + ~partTet(); // Member Functions @@ -92,54 +91,54 @@ public: inline label d() const; inline label size() const; - - // Searches - //- find position of the node in the partTet - inline label whichPosition(const label) const; + + // Searches + //- find position of the node in the partTet + inline label whichPosition(const label) const; // Properties //- Return face normal - template<class PointField> + template<class PointField> inline vector Sa(const PointField&) const; - template<class PointField> + template<class PointField> inline vector Sb(const PointField&) const; - template<class PointField> + template<class PointField> inline vector Sc(const PointField&) const; - template<class PointField> + template<class PointField> inline vector Sd(const PointField&) const; //- Return volume - template<class PointField> + template<class PointField> inline scalar mag(const PointField&) const; - - //- Return circum-centre - template<class PointField> - inline point crcmCentre(const PointField&) const; - - template<class PointField> - inline scalar crcmRadius(const PointField&) const; - - //- Return centroid of the tetrahedron - template<class PointField> - inline point centroid(const PointField&) const; - - //- Return edges - edgeList edges() const; - - // Member operators - - inline label operator[](const label) const; - - inline void operator=(const partTet&); + + //- Return circum-centre + template<class PointField> + inline point crcmCentre(const PointField&) const; + + template<class PointField> + inline scalar crcmRadius(const PointField&) const; + + //- Return centroid of the tetrahedron + template<class PointField> + inline point centroid(const PointField&) const; + + //- Return edges + edgeList edges() const; + + // Member operators + + inline label operator[](const label) const; + + inline void operator=(const partTet&); // IOstream operators - friend Ostream& operator<<(Ostream&, const partTet&); + friend Ostream& operator<<(Ostream&, const partTet&); }; diff --git a/meshLibrary/utilities/meshes/primitives/partTet/partTetI.H b/meshLibrary/utilities/meshes/primitives/partTet/partTetI.H index 38ebaf3f7e855bed4b11d5a58f166f520add2224..f147f95d7bbd4e1ccd5b7bcfffa1ab54fa37556f 100644 --- a/meshLibrary/utilities/meshes/primitives/partTet/partTetI.H +++ b/meshLibrary/utilities/meshes/primitives/partTet/partTetI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,7 +39,7 @@ namespace Foam inline partTet::partTet() { } - + inline partTet::partTet ( const label a, @@ -49,10 +48,10 @@ inline partTet::partTet const label d ) { - data_[0] = a; - data_[1] = b; - data_[2] = c; - data_[3] = d; + data_[0] = a; + data_[1] = b; + data_[2] = c; + data_[3] = d; } inline partTet::~partTet() @@ -88,145 +87,145 @@ inline label partTet::size() const inline label partTet::whichPosition(const label pointI) const { - for(label i=0;i<4;++i) - if( data_[i] == pointI ) - return i; - - return -1; + for(label i=0;i<4;++i) + if( data_[i] == pointI ) + return i; + + return -1; } template<class PointField> inline vector partTet::Sa(const PointField& points) const { - triangle<point, point> tria - ( - points[data_[1]], - points[data_[2]], - points[data_[3]] - ); - - return tria.normal(); + triangle<point, point> tria + ( + points[data_[1]], + points[data_[2]], + points[data_[3]] + ); + + return tria.normal(); //return triangle<point, point>(b_, c_, d_).normal(); } template<class PointField> inline vector partTet::Sb(const PointField& points) const { - triangle<point, point> tria - ( - points[data_[0]], - points[data_[3]], - points[data_[2]] - ); - - return tria.normal(); + triangle<point, point> tria + ( + points[data_[0]], + points[data_[3]], + points[data_[2]] + ); + + return tria.normal(); //return triangle<point, point>(a_, d_, c_).normal(); } template<class PointField> inline vector partTet::Sc(const PointField& points) const { - triangle<point, point> tria - ( - points[data_[0]], - points[data_[1]], - points[data_[3]] - ); - - return tria.normal(); + triangle<point, point> tria + ( + points[data_[0]], + points[data_[1]], + points[data_[3]] + ); + + return tria.normal(); //return triangle<point, point>(a_, b_, d_).normal(); } template<class PointField> inline vector partTet::Sd(const PointField& points) const { - triangle<point, point> tria - ( - points[data_[0]], - points[data_[2]], - points[data_[1]] - ); - - return tria.normal(); + triangle<point, point> tria + ( + points[data_[0]], + points[data_[2]], + points[data_[1]] + ); + + return tria.normal(); //return triangle<point, point>(a_, c_, b_).normal(); } template<class PointField> inline scalar partTet::mag(const PointField& points) const { - tetrahedron<point, point> tet - ( - points[data_[0]], - points[data_[1]], - points[data_[2]], - points[data_[3]] - ); - - return tet.mag(); + tetrahedron<point, point> tet + ( + points[data_[0]], + points[data_[1]], + points[data_[2]], + points[data_[3]] + ); + + return tet.mag(); //return (1.0/6.0)*(((b_ - a_) ^ (c_ - a_)) & (d_ - a_)); } template<class PointField> inline point partTet::crcmCentre(const PointField& points) const { - tetrahedron<point, point> tet - ( - points[data_[0]], - points[data_[1]], - points[data_[2]], - points[data_[3]] - ); - - return tet.circumCentre(); + tetrahedron<point, point> tet + ( + points[data_[0]], + points[data_[1]], + points[data_[2]], + points[data_[3]] + ); + + return tet.circumCentre(); } template<class PointField> inline scalar partTet::crcmRadius(const PointField& points) const { - tetrahedron<point, point> tet - ( - points[data_[0]], - points[data_[1]], - points[data_[2]], - points[data_[3]] - ); - - return tet.circumRadius(); + tetrahedron<point, point> tet + ( + points[data_[0]], + points[data_[1]], + points[data_[2]], + points[data_[3]] + ); + + return tet.circumRadius(); } template<class PointField> inline point partTet::centroid(const PointField& points) const { - point p = points[data_[0]]; - for(label i=1;i<4;++i) - p += points[data_[i]]; - - p /= 4; - return p; + point p = points[data_[0]]; + for(label i=1;i<4;++i) + p += points[data_[i]]; + + p /= 4; + return p; } inline edgeList partTet::edges() const { - edgeList edges(6); - edges[0] = edge(data_[0], data_[1]); - edges[1] = edge(data_[0], data_[2]); - edges[2] = edge(data_[0], data_[3]); + edgeList edges(6); + edges[0] = edge(data_[0], data_[1]); + edges[1] = edge(data_[0], data_[2]); + edges[2] = edge(data_[0], data_[3]); edges[3] = edge(data_[3], data_[1]); edges[4] = edge(data_[1], data_[2]); edges[5] = edge(data_[3], data_[2]); - return edges; + return edges; } inline label partTet::operator[](const label i) const { - return data_[i]; + return data_[i]; } inline void partTet::operator=(const partTet& tet) { - for(label i=0;i<4;++i) - data_[i] = tet.data_[i]; + for(label i=0;i<4;++i) + data_[i] = tet.data_[i]; } // * * * * * * * * * * * * * * * Ostream Operator * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurf.C b/meshLibrary/utilities/meshes/triSurf/triSurf.C index 8c5fabba9fa8ac42eb950a652ee84aa47ee151c3..1d2891679440f2660a8a8258ef3405c40a8f9d81 100644 --- a/meshLibrary/utilities/meshes/triSurf/triSurf.C +++ b/meshLibrary/utilities/meshes/triSurf/triSurf.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -32,142 +31,236 @@ Description #include "OFstream.H" #include "Time.H" +#include "gzstream.h" + +#include "triSurface.H" + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void triSurf::calculateFaceGroups() const +void triSurf::readFromFTR(const fileName& fName) { - nFaceGroups_ = 0; - - faceGroupPtr_ = new labelListPMG(triSurface::size(), -1); - labelListPMG& faceGroup = *faceGroupPtr_; - - const labelListList& faceEdges = this->faceEdges(); - const labelListList& edgeFaces = this->edgeFaces(); - - labelListPMG front; - - forAll(faceGroup, fI) - { - if( faceGroup[fI] != -1 ) - continue; - - front.clear(); - front.append(fI); - faceGroup[fI] = nFaceGroups_; - - while( front.size() != 0 ) - { - const label fLabel = front.removeLastElement(); - - const labelList& fEdges = faceEdges[fLabel]; - forAll(fEdges, feI) - { - const label eI = fEdges[feI]; - - if( edgeFaces[eI].size() != 2 ) - continue; - - label nei = edgeFaces[eI][0]; - if( nei == fLabel ) - nei = edgeFaces[eI][1]; - - if( faceGroup[nei] == -1 ) - { - faceGroup[nei] = nFaceGroups_; - front.append(nei); - } - } - } - - ++nFaceGroups_; - } + IFstream fStream(fName); + + fStream >> triSurfFacets::patches_; + + fStream >> triSurfPoints::points_; + + fStream >> triSurfFacets::triangles_; } -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +void triSurf::writeToFTR(const fileName& fName) const +{ + OFstream fStream(fName); -triSurf::triSurf(const fileName& name) -: - triSurface(name), - triSubsets_(), - nFaceGroups_(-1), - faceGroupPtr_(NULL) + fStream << triSurfFacets::patches_; + + fStream << nl; + + fStream << triSurfPoints::points_; + + fStream << nl; + + fStream << triSurfFacets::triangles_; +} + +void triSurf::readFromFMS(const fileName& fName) { + IFstream fStream(fName); + + //- read the list of patches defined on the surface mesh + fStream >> triSurfFacets::patches_; + + //- read points + fStream >> triSurfPoints::points_; + + //- read surface triangles + fStream >> triSurfFacets::triangles_; + + //- read feature edges + fStream >> triSurfFeatureEdges::featureEdges_; + + List<meshSubset> subsets; + + //- read point subsets + fStream >> subsets; + forAll(subsets, subsetI) + triSurfPoints::pointSubsets_.insert(subsetI, subsets[subsetI]); + + subsets.clear(); + + //- read facet subsets + fStream >> subsets; + forAll(subsets, subsetI) + triSurfFacets::facetSubsets_.insert(subsetI, subsets[subsetI]); + + subsets.clear(); + + //- read subsets on feature edges + fStream >> subsets; + forAll(subsets, subsetI) + triSurfFeatureEdges::featureEdgeSubsets_.insert + ( + subsetI, + subsets[subsetI] + ); } +void triSurf::writeToFMS(const fileName& fName) const +{ + OFstream fStream(fName); + + //- write patches + fStream << triSurfFacets::patches_; + + fStream << nl; + + //- write points + fStream << triSurfPoints::points_; + + fStream << nl; + + //- write triangles + fStream << triSurfFacets::triangles_; + + fStream << nl; + + //- write feature edges + fStream << triSurfFeatureEdges::featureEdges_; + + fStream << nl; + + //- write point subsets + List<meshSubset> subsets; + label i(0); + subsets.setSize(pointSubsets_.size()); + forAllConstIter(Map<meshSubset>, pointSubsets_, it) + subsets[i++] = it(); + fStream << subsets; + + fStream << nl; + + //- write subsets of facets + subsets.setSize(triSurfFacets::facetSubsets_.size()); + i = 0; + forAllConstIter(Map<meshSubset>, triSurfFacets::facetSubsets_, it) + subsets[i++] = it(); + fStream << subsets; + + fStream << nl; + + //- write subets of feature edges + subsets.setSize(triSurfFeatureEdges::featureEdgeSubsets_.size()); + i = 0; + forAllConstIter + ( + Map<meshSubset>, + triSurfFeatureEdges::featureEdgeSubsets_, + it + ) + subsets[i++] = it(); + fStream << subsets; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurf::triSurf() +: + triSurfPoints(), + triSurfFacets(), + triSurfFeatureEdges(), + triSurfAddressing(triSurfPoints::points_, triSurfFacets::triangles_) +{} + +//- Construct from parts triSurf::triSurf ( - const List<labelledTri>& triangles, - const geometricSurfacePatchList& patches, - const pointField& points, - std::map<word, labelListPMG>& faceSubsets + const LongList<labelledTri>& triangles, + const geometricSurfacePatchList& patches, + const edgeLongList& featureEdges, + const pointField& points ) : - triSurface(triangles, patches, points), - triSubsets_(), - nFaceGroups_(-1), - faceGroupPtr_(NULL) + triSurfPoints(points), + triSurfFacets(triangles, patches), + triSurfFeatureEdges(featureEdges), + triSurfAddressing(triSurfPoints::points_, triSurfFacets::triangles_) +{} + +//- Read from file +triSurf::triSurf(const fileName& fName) +: + triSurfPoints(), + triSurfFacets(), + triSurfFeatureEdges(), + triSurfAddressing(triSurfPoints::points_, triSurfFacets::triangles_) { - std::map<word, labelListPMG>::const_iterator iter; - for(iter=faceSubsets.begin();iter!=faceSubsets.end();++iter) - { - triSubsets_.insert - ( - std::pair<word, labelListPMG>(iter->first, iter->second) - ); - } + readSurface(fName); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // triSurf::~triSurf() -{ -} - +{} + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void triSurf::readFaceSubsets(const fileName& fName) +void triSurf::readSurface(const fileName& fName) { - IFstream file(fName); - - //- read the number of subsets - label nSubsets; - file >> nSubsets; - - // read subsets - for(label subsetI=0;subsetI<nSubsets;++subsetI) - { - word name; - file >> name; - labelListPMG set; - file >> set; - - this->addFacetsToSubset(name, set); - } + if( fName.ext() == "fms" || fName.ext() == "FMS" ) + { + readFromFMS(fName); + } + else if( fName.ext() == "ftr" || fName.ext() == "FTR" ) + { + readFromFTR(fName); + } + else + { + triSurface copySurface(fName); + + //- copy the points + triSurfPoints::points_.setSize(copySurface.points().size()); + forAll(copySurface.points(), pI) + triSurfPoints::points_[pI] = copySurface.points()[pI]; + + //- copy the triangles + triSurfFacets::triangles_.setSize(copySurface.size()); + forAll(copySurface, tI) + triSurfFacets::triangles_[tI] = copySurface[tI]; + + //- copy patches + triSurfFacets::patches_ = copySurface.patches(); + } } -void triSurf::writeFaceSubsets(const fileName& fName) const +void triSurf::writeSurface(const fileName& fName) const { - OFstream file(fName); - - label nSubsets(0); - - //- find the number of subsets - std::map<word, labelListPMG>::const_iterator iter; - for(iter = triSubsets_.begin();iter != triSubsets_.end();++iter) - ++nSubsets; - file << nSubsets << nl; - - //- write subsets - for(iter = triSubsets_.begin();iter != triSubsets_.end();++iter) - { - file << iter->first << nl; - file << iter->second << nl; - } + if( fName.ext() == "fms" || fName.ext() == "FMS" ) + { + writeToFMS(fName); + } + else if( fName.ext() == "ftr" || fName.ext() == "FTR" ) + { + writeToFTR(fName); + } + else + { + const pointField& pts = this->points(); + const LongList<labelledTri>& facets = this->facets(); + const geometricSurfacePatchList& patches = this->patches(); + + List<labelledTri> newTrias(facets.size()); + forAll(facets, tI) + newTrias[tI] = facets[tI]; + + triSurface newSurf(newTrias, patches, pts); + newSurf.write(fName); + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurf.H b/meshLibrary/utilities/meshes/triSurf/triSurf.H index 4b2ff7325f83f1db8f0cdc2e437d9f3c5ad0241d..1e542553c894b7ba7f6cc260d94cae4301e5bc2a 100644 --- a/meshLibrary/utilities/meshes/triSurf/triSurf.H +++ b/meshLibrary/utilities/meshes/triSurf/triSurf.H @@ -1,34 +1,33 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triSurf Description A class for triangulated surface used in the meshing process. - It is derived from triSurface with some additional subsets. - Subsets are vert useful for local mesh refinement. + It is derived from points and facets with some additional subsets. + Subsets are vert useful for local mesh refinement. SourceFiles triSurf.C @@ -38,84 +37,77 @@ SourceFiles #ifndef triSurf_H #define triSurf_H -#include "triSurface.H" +#include "triSurfPoints.H" +#include "triSurfFacets.H" +#include "triSurfFeatureEdges.H" +#include "triSurfAddressing.H" #include <map> #include "DynList.H" -#include "labelListPMG.H" +#include "labelLongList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { +// Froward declarations +class triSurfModifier; + /*---------------------------------------------------------------------------*\ - Class triSurf Declaration + Class triSurf Declaration \*---------------------------------------------------------------------------*/ class triSurf -: public triSurface +: + public triSurfPoints, + public triSurfFacets, + public triSurfFeatureEdges, + public triSurfAddressing { - // Private data - //- subsets of facets in the triangulation - std::map<word, labelListPMG> triSubsets_; + // Private member functions + void readFromFTR(const fileName&); + void writeToFTR(const fileName&) const; - //- groups of facets - //- which can be visited over manifold edges - mutable label nFaceGroups_; - mutable labelListPMG* faceGroupPtr_; + void readFromFMS(const fileName&); + void writeToFMS(const fileName&) const; - // Private member functions - //- calculate groups of facets - void calculateFaceGroups() const; + inline LongList<labelledTri>& accessToFacets(); + inline geometricSurfacePatchList& accessToPatches(); //- Disallow default bitwise assignment void operator=(const triSurf&); public: + // Friend classes + friend class triSurfModifer; + // Constructors - //- Construct from file name (uses extension to determine type) - triSurf(const fileName&); + //- Default construct + triSurf(); //- Construct from parts triSurf ( - const List<labelledTri>& triangles, + const LongList<labelledTri>& triangles, const geometricSurfacePatchList& patches, - const pointField& points, - std::map<word, labelListPMG>& faceSubsets + const edgeLongList& featureEdges_, + const pointField& points ); + //- Read from file + triSurf(const fileName& fName); + // Destructor ~triSurf(); // Member Functions - //- read and write subset data - void readFaceSubsets(const fileName&); - void writeFaceSubsets(const fileName&) const; - - //- returns the names of the existing subsets - inline void existingFaceSubsets(DynList<word>&) const; - - //- return facets in subset - inline bool doesFaceSubsetExist(const word&) const; - inline const labelListPMG& facesInSubset(const word&) const; - - //- creates a new subset if it does not yet exist - //- adds elements which are not yet in the subset - inline void addFacetsToSubset(const word&, const labelListPMG&); - - //- remove subset of facets - inline void removeFaceSubset(const word&); - - //- number of groups of facets that are connected over manifold edges - inline label numberOfFaceGroups() const; - - //- groups assigned to the surface facets - inline const labelListPMG& faceGroups() const; + //- read and write the surface + void readSurface(const fileName&); + void writeSurface(const fileName&) const; }; diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfAddressing.C b/meshLibrary/utilities/meshes/triSurf/triSurfAddressing.C new file mode 100644 index 0000000000000000000000000000000000000000..88a704b6cad751457a73f2cb3b20000f562a43e1 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfAddressing.C @@ -0,0 +1,371 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfAddressing.H" +#include "VRWGraphSMPModifier.H" +#include "demandDrivenData.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +namespace Foam +{ + +void triSurfAddressing::calculatePointFacets() const +{ + pointFacetsPtr_ = new VRWGraph(); + + VRWGraphSMPModifier(*pointFacetsPtr_).reverseAddressing(facets_); +} + +void triSurfAddressing::calculateEdges() const +{ + edgesPtr_ = new edgeLongList(); + + const VRWGraph& pFacets = pointFacets(); + + # ifdef USE_OMP + label nThreads = 3 * omp_get_num_procs(); + if( pFacets.size() < 1000 ) + nThreads = 1; + # else + const label nThreads(1); + # endif + + labelList nEdgesForThread(nThreads); + + label edgeI(0); + + # ifdef USE_OMP + # pragma omp parallel num_threads(nThreads) + # endif + { + edgeLongList edgesHelper; + + # ifdef USE_OMP + # pragma omp for schedule(static) + # endif + forAll(facets_, fI) + { + const labelledTri& tri = facets_[fI]; + + forAll(tri, pI) + { + const edge fe(tri[pI], tri[(pI+1)%3]); + const label s = fe.start(); + const label e = fe.end(); + + DynList<label> edgeFaces; + + bool store(true); + + //- find all faces attached to this edge + //- store the edge in case the face faceI is the face + //- with the smallest label + forAllRow(pFacets, s, pfI) + { + const label ofI = pFacets(s, pfI); + const labelledTri& of = facets_[ofI]; + + label pos(-1); + for(label i=0;i<3;++i) + if( of[i] == e ) + { + pos = i; + break; + } + if( pos < 0 ) + continue; + if( ofI < fI ) + { + store = false; + break; + } + + edgeFaces.append(ofI); + } + + if( store ) + edgesHelper.append(fe); + } + } + + //- this enables other threads to see the number of edges + //- generated by each thread + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif + nEdgesForThread[threadI] = edgesHelper.size(); + + + # ifdef USE_OMP + # pragma omp critical + # endif + edgeI += edgesHelper.size(); + + # ifdef USE_OMP + # pragma omp barrier + + # pragma omp master + # endif + edgesPtr_->setSize(edgeI); + + # ifdef USE_OMP + # pragma omp barrier + # endif + + //- find the starting position of the edges generated by this thread + //- in the global list of edges + label localStart(0); + for(label i=0;i<threadI;++i) + localStart += nEdgesForThread[i]; + + //- store edges into the global list + forAll(edgesHelper, i) + edgesPtr_->operator[](localStart+i) = edgesHelper[i]; + } +} + +void triSurfAddressing::calculateFacetEdges() const +{ + const edgeLongList& edges = this->edges(); + const VRWGraph& pointFaces = this->pointFacets(); + + facetEdgesPtr_ = new VRWGraph(facets_.size()); + VRWGraph& faceEdges = *facetEdgesPtr_; + + labelList nfe(facets_.size()); + + # ifdef USE_OMP + const label nThreads = 3 * omp_get_num_procs(); + # pragma omp parallel num_threads(nThreads) + # endif + { + # ifdef USE_OMP + # pragma omp for schedule(static) + # endif + forAll(facets_, fI) + nfe[fI] = 3; + + # ifdef USE_OMP + # pragma omp barrier + + # pragma omp master + # endif + VRWGraphSMPModifier(faceEdges).setSizeAndRowSize(nfe); + + # ifdef USE_OMP + # pragma omp barrier + + # pragma omp for schedule(static) + # endif + forAll(edges, edgeI) + { + const edge ee = edges[edgeI]; + const label pI = ee.start(); + + forAllRow(pointFaces, pI, pfI) + { + const label fI = pointFaces(pI, pfI); + + const labelledTri& tri = facets_[fI]; + forAll(tri, eI) + { + const edge e(tri[eI], tri[(eI+1)%3]); + if( e == ee ) + { + faceEdges(fI, eI) = edgeI; + break; + } + } + } + } + } +} + +void triSurfAddressing::calculateEdgeFacets() const +{ + const edgeLongList& edges = this->edges(); + const VRWGraph& faceEdges = this->facetEdges(); + + edgeFacetsPtr_ = new VRWGraph(edges.size()); + + VRWGraphSMPModifier(*edgeFacetsPtr_).reverseAddressing(faceEdges); +} + +void triSurfAddressing::calculatePointEdges() const +{ + const edgeLongList& edges = this->edges(); + + pointEdgesPtr_ = new VRWGraph(points_.size()); + + pointEdgesPtr_->reverseAddressing(edges); +} + +void triSurfAddressing::calculateFacetFacetsEdges() const +{ + facetFacetsEdgesPtr_ = new VRWGraph(); + + const VRWGraph& facetEdges = this->facetEdges(); + const VRWGraph& edgeFacets = this->edgeFacets(); + + facetFacetsEdgesPtr_->setSize(facets_.size()); + + forAll(facetEdges, facetI) + { + labelHashSet fLabels; + + forAllRow(facetEdges, facetI, feI) + { + const label edgeI = facetEdges(facetI, feI); + + forAllRow(edgeFacets, edgeI, efI) + fLabels.insert(edgeFacets(edgeI, efI)); + } + + facetFacetsEdgesPtr_->setRowSize(facetI, fLabels.size()); + + label counter(0); + forAllConstIter(labelHashSet, fLabels, iter) + facetFacetsEdgesPtr_->operator()(facetI, counter++) = iter.key(); + } +} + +void triSurfAddressing::calculatePointNormals() const +{ + const VRWGraph& pFacets = pointFacets(); + const vectorField& fNormals = facetNormals(); + + pointNormalsPtr_ = new vectorField(pFacets.size()); + + const label size = pFacets.size(); + # ifdef USE_OMP + # pragma omp parallel for if( size > 1000 ) + # endif + for(label pI=0;pI<size;++pI) + { + vector normal(vector::zero); + + forAllRow(pFacets, pI, pfI) + normal += fNormals[pFacets(pI, pfI)]; + + const scalar d = mag(normal); + if( d > VSMALL ) + { + normal /= d; + } + else + { + normal = vector::zero; + } + + (*pointNormalsPtr_)[pI] = normal; + } +} + +void triSurfAddressing::calculateFacetNormals() const +{ + facetNormalsPtr_ = new vectorField(facets_.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(facets_, fI) + { + vector v = facets_[fI].normal(points_); + v /= (mag(v) + VSMALL); + (*facetNormalsPtr_)[fI] = v; + } +} + +void triSurfAddressing::calculateFacetCentres() const +{ + facetCentresPtr_ = new vectorField(facets_.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(facets_, fI) + (*facetCentresPtr_)[fI] = facets_[fI].centre(points_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfAddressing::triSurfAddressing +( + const pointField& points, + const LongList<labelledTri>& triangles) +: + points_(points), + facets_(triangles), + pointFacetsPtr_(NULL), + edgesPtr_(NULL), + facetEdgesPtr_(NULL), + edgeFacetsPtr_(NULL), + pointEdgesPtr_(NULL), + facetFacetsEdgesPtr_(NULL), + pointNormalsPtr_(NULL), + facetNormalsPtr_(NULL), + facetCentresPtr_(NULL) + +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfAddressing::~triSurfAddressing() +{ + clearAddressing(); + clearGeometry(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfAddressing::clearAddressing() +{ + deleteDemandDrivenData(pointFacetsPtr_); + deleteDemandDrivenData(edgesPtr_); + deleteDemandDrivenData(facetEdgesPtr_); + deleteDemandDrivenData(edgeFacetsPtr_); + deleteDemandDrivenData(pointEdgesPtr_); + deleteDemandDrivenData(facetFacetsEdgesPtr_); +} + +void triSurfAddressing::clearGeometry() +{ + deleteDemandDrivenData(pointNormalsPtr_); + deleteDemandDrivenData(facetNormalsPtr_); + deleteDemandDrivenData(facetCentresPtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfAddressing.H b/meshLibrary/utilities/meshes/triSurf/triSurfAddressing.H new file mode 100644 index 0000000000000000000000000000000000000000..0fdbde13109106565a563493a8031af469e9d66f --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfAddressing.H @@ -0,0 +1,184 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfAddressing + +Description + Provides topology addressing of the triangulated surface + +SourceFiles + triSurfAddressing.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfAddressing_H +#define triSurfAddressing_H + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "VRWGraph.H" +#include "edgeLongList.H" +#include "triSurfFacets.H" +#include "labelledTri.H" +#include "DynList.H" + +#include <map> + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +class triSurfAddressing +{ + // Private data + //- const reference to the points + const pointField& points_; + + // Topology addressing + //- const reference to the facets + const LongList<labelledTri>& facets_; + + //- facets connected to a point + mutable VRWGraph* pointFacetsPtr_; + + //- edges in the triangulation + mutable edgeLongList* edgesPtr_; + + //- labels of edges in the triangles + mutable VRWGraph* facetEdgesPtr_; + + //- labels of triangles connected to an edge + mutable VRWGraph* edgeFacetsPtr_; + + //- labels of edges connected to a point + mutable VRWGraph* pointEdgesPtr_; + + //- facets connected tp a facet via edges + mutable VRWGraph* facetFacetsEdgesPtr_; + + // Geometry data + //- point normals + mutable vectorField* pointNormalsPtr_; + + //- face normals + mutable vectorField* facetNormalsPtr_; + + //- face centres + mutable vectorField* facetCentresPtr_; + + // Private member functions + //- calculate point-facets addressing + void calculatePointFacets() const; + + //- calculate edges, facet-edges and edge-facets addressing + void calculateEdges() const; + + //- calculate facet-edges addresing + void calculateFacetEdges() const; + + //- calculate edge-facets addressing + void calculateEdgeFacets() const; + + //- calculate point-edges addressing + void calculatePointEdges() const; + + //- calculate facet-faceys addressing + void calculateFacetFacetsEdges() const; + + //- calculate point normals + void calculatePointNormals() const; + + //- calculate normals of facets + void calculateFacetNormals() const; + + //- calculate centres of facets + void calculateFacetCentres() const; + + // Disallow bitwise assignment + void operator=(const triSurfAddressing&); + + triSurfAddressing(const triSurfAddressing&); + +public: + + // Constructors + //- Construct from surface triangles + triSurfAddressing + ( + const pointField& points, + const LongList<labelledTri>& triangles + ); + + // Destructor + ~triSurfAddressing(); + + // Member functions + //- return point-facets addressing + inline const VRWGraph& pointFacets() const; + + //- return edges + inline const LongList<edge>& edges() const; + + //- return facet-edges addressing + inline const VRWGraph& facetEdges() const; + + //- return edge-facets addressing + inline const VRWGraph& edgeFacets() const; + + //- return point-edges addressing + inline const VRWGraph& pointEdges() const; + + //- return facet-facets addressing + inline const VRWGraph& facetFacets() const; + + //- return point normals + inline const pointField& pointNormals() const; + + //- return normals of facets + inline const vectorField& facetNormals() const; + + //- return centres of facets + inline const vectorField& facetCentres() const; + + //- delete all data + void clearAddressing(); + + //- delete geometry data + void clearGeometry(); +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfAddressingI.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfAddressingI.H b/meshLibrary/utilities/meshes/triSurf/triSurfAddressingI.H new file mode 100644 index 0000000000000000000000000000000000000000..5dc2563570c80a58c561e6e216773604c4040be6 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfAddressingI.H @@ -0,0 +1,212 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + + +\*---------------------------------------------------------------------------*/ + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfAddressing.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +inline const VRWGraph& triSurfAddressing::pointFacets() const +{ + if( !pointFacetsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const VRWGraph& triSurfAddressing::pointFacets() const" + ) << "Cannot calculate pointFacets" << abort(FatalError); + # endif + + calculatePointFacets(); + } + + return *pointFacetsPtr_; +} + +inline const edgeLongList& triSurfAddressing::edges() const +{ + if( !edgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const edgeLongList& triSurfAddressing::edges() const" + ) << "Cannot calculate edges" << abort(FatalError); + # endif + + calculateEdges(); + } + + return *edgesPtr_; +} + +inline const VRWGraph& triSurfAddressing::facetEdges() const +{ + if( !facetEdgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const VRWGraph& triSurfAddressing::facetEdges() const" + ) << "Cannot calculate facetEdges" << abort(FatalError); + # endif + + calculateFacetEdges(); + } + + return *facetEdgesPtr_; +} + +inline const VRWGraph& triSurfAddressing::edgeFacets() const +{ + if( !edgeFacetsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const VRWGraph& triSurfAddressing::edgeFacets() const" + ) << "Cannot calculate edgeFacets" << abort(FatalError); + # endif + + calculateEdgeFacets(); + } + + return *edgeFacetsPtr_; +} + +inline const VRWGraph& triSurfAddressing::pointEdges() const +{ + if( !pointEdgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const VRWGraph& triSurfAddressing::pointEdges() const" + ) << "Cannot calculate pointEdges" << abort(FatalError); + # endif + + calculatePointEdges(); + } + + return *pointEdgesPtr_; +} + +inline const VRWGraph& triSurfAddressing::facetFacets() const +{ + if( !facetFacetsEdgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const VRWGraph& triSurfAddressing::facetFacets() const" + ) << "Cannot calculate facetFacets" << abort(FatalError); + # endif + + calculateFacetFacetsEdges(); + } + + return *facetFacetsEdgesPtr_; +} + +inline const vectorField& triSurfAddressing::pointNormals() const +{ + if( !pointNormalsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const vectorField&" + " triSurfAddressing::pointNormals() const" + ) << "Cannot calculate pointNormals" << abort(FatalError); + # endif + + calculatePointNormals(); + } + + return *pointNormalsPtr_; +} + +inline const vectorField& triSurfAddressing::facetNormals() const +{ + if( !facetNormalsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const vectorField&" + " triSurfAddressing::facetNormals() const" + ) << "Cannot calculate facetNormals" << abort(FatalError); + # endif + + calculateFacetNormals(); + } + + return *facetNormalsPtr_; +} + +inline const vectorField& triSurfAddressing::facetCentres() const +{ + if( !facetCentresPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "inline const vectorField&" + " triSurfAddressing::facetCentres() const" + ) << "Cannot calculate facetCentres" << abort(FatalError); + # endif + + calculateFacetCentres(); + } + + return *facetCentresPtr_; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfFacets.C b/meshLibrary/utilities/meshes/triSurf/triSurfFacets.C new file mode 100644 index 0000000000000000000000000000000000000000..24777599cd54caa41a9388895e0c8a99184d94a1 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfFacets.C @@ -0,0 +1,132 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfFacets.H" +#include "pointIOField.H" +#include "IOobjectList.H" +#include "pointSet.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfFacets::triSurfFacets() +: + triangles_(), + patches_(), + facetSubsets_() +{} + +triSurfFacets::triSurfFacets(const LongList<labelledTri>& triangles) +: + triangles_(triangles), + patches_(1), + facetSubsets_() +{ + forAll(triangles_, triI) + triangles_[triI].region() = 0; + + patches_[0].name() = "patch"; +} + +triSurfFacets::triSurfFacets +( + const LongList<labelledTri>& triangles, + const geometricSurfacePatchList& patches +) +: + triangles_(triangles), + patches_(patches), + facetSubsets_() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +// Destructor +triSurfFacets::~triSurfFacets() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +label triSurfFacets::addFacetSubset(const word& subsetName) +{ + label id = facetSubsetIndex(subsetName); + if( id >= 0 ) + { + Warning << "Point subset " << subsetName << " already exists!" << endl; + return id; + } + + id = 0; + forAllConstIter(Map<meshSubset>, facetSubsets_, it) + id = Foam::max(id, it.key()+1); + + facetSubsets_.insert + ( + id, + meshSubset(subsetName, meshSubset::FACESUBSET) + ); + + return id; +} + +void triSurfFacets::removeFacetSubset(const label subsetID) +{ + if( facetSubsets_.find(subsetID) == facetSubsets_.end() ) + return; + + facetSubsets_.erase(subsetID); +} + +word triSurfFacets::facetSubsetName(const label subsetID) const +{ + Map<meshSubset>::const_iterator it = facetSubsets_.find(subsetID); + if( it == facetSubsets_.end() ) + { + Warning << "Subset " << subsetID << " is not a facet subset" << endl; + return word(); + } + + return it().name(); +} + +label triSurfFacets::facetSubsetIndex(const word& subsetName) const +{ + forAllConstIter(Map<meshSubset>, facetSubsets_, it) + { + if( it().name() == subsetName ) + return it.key(); + } + + return -1; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfFacets.H b/meshLibrary/utilities/meshes/triSurf/triSurfFacets.H new file mode 100644 index 0000000000000000000000000000000000000000..a36ba99003c36397b24a483b40aabf9b204bbfc4 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfFacets.H @@ -0,0 +1,136 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfFacets + +Description + Facets for the triangulated surface + +SourceFiles + triSurfFacets.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfFacets_H +#define triSurfFacets_H + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfAddressing.H" +#include "meshSubset.H" +#include "geometricSurfacePatchList.H" +#include "LongList.H" +#include "labelledTri.H" +#include "DynList.H" +#include "Map.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +class triSurfFacets +{ +protected: + + // Protected data + //- list of triangles + LongList<labelledTri> triangles_; + + //- list of boundary patches and their properties + geometricSurfacePatchList patches_; + + //- map of point subsets + Map<meshSubset> facetSubsets_; + + // Disallow bitwise assignment + void operator=(const triSurfFacets&); + + triSurfFacets(const triSurfFacets&); + +public: + + // Constructors + //- Null constructor + triSurfFacets(); + + //- Construct from components without the boundary + triSurfFacets(const LongList<labelledTri>& triangles); + + //- Construct from components + triSurfFacets + ( + const LongList<labelledTri>& triangles, + const geometricSurfacePatchList& patches + ); + + // Destructor + ~triSurfFacets(); + + // Member functions + //- return the number of triangles + inline label size() const; + + //- access to facets + inline const LongList<labelledTri>& facets() const; + + //- access to patches + inline const geometricSurfacePatchList& patches() const; + + //- append a triangle to the end of the list + inline void appendTriangle(const labelledTri& tria); + + //- point subsets + label addFacetSubset(const word&); + void removeFacetSubset(const label); + word facetSubsetName(const label) const; + label facetSubsetIndex(const word&) const; + inline void addFacetToSubset(const label, const label); + inline void removeFacetFromSubset(const label, const label); + inline void facetInSubsets(const label, DynList<label>&) const; + inline void facetSubsetIndices(DynList<label>&) const; + template<class ListType> + inline void facetsInSubset(const label, ListType&) const; + template<class ListType> + inline void updateFacetsSubsets(const ListType&); + + // Operators + + //- access to a triangle + inline const labelledTri& operator[](const label) const; +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfFacetsI.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfFacetsI.H b/meshLibrary/utilities/meshes/triSurf/triSurfFacetsI.H new file mode 100644 index 0000000000000000000000000000000000000000..ef6d1fce20bbf5349157f8399bd634ba40a0b5f2 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfFacetsI.H @@ -0,0 +1,155 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + + +\*---------------------------------------------------------------------------*/ + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfFacets.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +inline label triSurfFacets::size() const +{ + return triangles_.size(); +} + +inline const LongList<labelledTri>& triSurfFacets::facets() const +{ + return triangles_; +} + +inline const geometricSurfacePatchList& triSurfFacets::patches() const +{ + return patches_; +} + +inline void triSurfFacets::appendTriangle(const labelledTri& tri) +{ + triangles_.append(tri); +} + +inline void triSurfFacets::addFacetToSubset +( + const label setI, + const label triI +) +{ + Map<meshSubset>::iterator it = facetSubsets_.find(setI); + if( it == facetSubsets_.end() ) + return; + + it().addElement(triI); +} + +inline void triSurfFacets::removeFacetFromSubset +( + const label setI, + const label triI +) +{ + Map<meshSubset>::iterator it = facetSubsets_.find(setI); + if( it == facetSubsets_.end() ) + return; + + it().removeElement(triI); +} + +inline void triSurfFacets::facetInSubsets +( + const label triI, + DynList<label>& facetSubsets +) const +{ + facetSubsets.clear(); + + forAllConstIter + ( + Map<meshSubset>, + facetSubsets_, + it + ) + { + if( it().contains(triI) ) + facetSubsets.append(it.key()); + } +} + +inline void triSurfFacets::facetSubsetIndices(DynList<label>& indices) const +{ + indices.clear(); + + forAllConstIter + ( + Map<meshSubset>, + facetSubsets_, + it + ) + indices.append(it.key()); +} + +template<class ListType> +inline void triSurfFacets::facetsInSubset +( + const label setI, + ListType& facetsLabels +) const +{ + facetsLabels.clear(); + + Map<meshSubset>::const_iterator it = facetSubsets_.find(setI); + if( it == facetSubsets_.end() ) + return; + + it().containedElements(facetsLabels); +} + +template<class ListType> +inline void triSurfFacets::updateFacetsSubsets(const ListType& newFacetsLabels) +{ + for + ( + Map<meshSubset>::iterator it=facetSubsets_.begin(); + it!=facetSubsets_.end(); + ++it + ) + it().updateSubset(newFacetsLabels); +} + +inline const labelledTri& triSurfFacets::operator[](const label triI) const +{ + return triangles_[triI]; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdges.C b/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdges.C new file mode 100644 index 0000000000000000000000000000000000000000..3a3649c97bda0fec8686819a3218757241634060 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdges.C @@ -0,0 +1,111 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfFeatureEdges.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfFeatureEdges::triSurfFeatureEdges() +: + featureEdges_(), + featureEdgeSubsets_() +{} + +triSurfFeatureEdges::triSurfFeatureEdges(const edgeLongList& featureEdges) +: + featureEdges_(featureEdges), + featureEdgeSubsets_() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +// Destructor +triSurfFeatureEdges::~triSurfFeatureEdges() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +label triSurfFeatureEdges::addEdgeSubset(const word& subsetName) +{ + label id = edgeSubsetIndex(subsetName); + if( id >= 0 ) + { + Warning << "Edge subset " << subsetName << " already exists!" << endl; + return id; + } + + id = 0; + forAllConstIter(Map<meshSubset>, featureEdgeSubsets_, it) + id = Foam::max(id, it.key()+1); + + featureEdgeSubsets_.insert + ( + id, + meshSubset(subsetName, meshSubset::FEATUREEDGESUBSET) + ); + + return id; +} + +void triSurfFeatureEdges::removeEdgeSubset(const label subsetID) +{ + if( featureEdgeSubsets_.find(subsetID) == featureEdgeSubsets_.end() ) + return; + + featureEdgeSubsets_.erase(subsetID); +} + +word triSurfFeatureEdges::edgeSubsetName(const label subsetID) const +{ + Map<meshSubset>::const_iterator it = featureEdgeSubsets_.find(subsetID); + if( it == featureEdgeSubsets_.end() ) + { + Warning << "Subset " << subsetID << " is not an edge subset" << endl; + return word(); + } + + return it().name(); +} + +label triSurfFeatureEdges::edgeSubsetIndex(const word& subsetName) const +{ + forAllConstIter(Map<meshSubset>, featureEdgeSubsets_, it) + { + if( it().name() == subsetName ) + return it.key(); + } + + return -1; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdges.H b/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdges.H new file mode 100644 index 0000000000000000000000000000000000000000..da8aea1cd9f5f2582a3c6d339d13b1a638cc2d4c --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdges.H @@ -0,0 +1,116 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfFeatureEdges + +Description + User-selected list of feature edges used in the meshing process + +SourceFiles + triSurfFeatureEdges.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfFeatureEdges_H +#define triSurfFeatureEdges_H + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "edgeLongList.H" +#include "meshSubset.H" +#include "Map.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +class triSurfFeatureEdges +{ +protected: + + // Protected data + //- list of feature edges + edgeLongList featureEdges_; + + //- map of edge subsets + Map<meshSubset> featureEdgeSubsets_; + + // Disallow bitwise assignment + void operator=(const triSurfFeatureEdges&); + + triSurfFeatureEdges(const triSurfFeatureEdges&); + +public: + + // Constructors + //- Null constructor + triSurfFeatureEdges(); + + //- Construct from feature edges + triSurfFeatureEdges(const edgeLongList& triangles); + + // Destructor + ~triSurfFeatureEdges(); + + // Member functions + //- return the number of feature edges + inline label nFeatureEdges() const; + + //- access to feature edges + inline const edgeLongList& featureEdges() const; + + //- append an edge to the end of the list + inline void appendFeatureEdge(const edge& e); + + //- point subsets + label addEdgeSubset(const word&); + void removeEdgeSubset(const label); + word edgeSubsetName(const label) const; + label edgeSubsetIndex(const word&) const; + inline void addEdgeToSubset(const label, const label); + inline void removeEdgeFromSubset(const label, const label); + inline void edgeInSubsets(const label, DynList<label>&) const; + inline void edgeSubsetIndices(DynList<label>&) const; + template<class ListType> + inline void edgesInSubset(const label, ListType&) const; + template<class ListType> + inline void updateEdgeSubsets(const ListType&); + + // Operators +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfFeatureEdgesI.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdgesI.H b/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdgesI.H new file mode 100644 index 0000000000000000000000000000000000000000..d2ce00c25c7fad538fa456e639f7522aa9bd1b0b --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfFeatureEdgesI.H @@ -0,0 +1,152 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + + +\*---------------------------------------------------------------------------*/ + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfFeatureEdges.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +inline label triSurfFeatureEdges::nFeatureEdges() const +{ + return featureEdges_.size(); +} + +inline const edgeLongList& triSurfFeatureEdges::featureEdges() const +{ + return featureEdges_; +} + +inline void triSurfFeatureEdges::appendFeatureEdge(const edge& e) +{ + featureEdges_.append(e); +} + +inline void triSurfFeatureEdges::addEdgeToSubset +( + const label setI, + const label eI +) +{ + Map<meshSubset>::iterator it = featureEdgeSubsets_.find(setI); + if( it == featureEdgeSubsets_.end() ) + return; + + it().addElement(eI); +} + +inline void triSurfFeatureEdges::removeEdgeFromSubset +( + const label setI, + const label eI +) +{ + Map<meshSubset>::iterator it = featureEdgeSubsets_.find(setI); + if( it == featureEdgeSubsets_.end() ) + return; + + it().removeElement(eI); +} + +inline void triSurfFeatureEdges::edgeInSubsets +( + const label eI, + DynList<label>& edgeSubsets +) const +{ + edgeSubsets.clear(); + + forAllConstIter + ( + Map<meshSubset>, + featureEdgeSubsets_, + it + ) + { + if( it().contains(eI) ) + edgeSubsets.append(it.key()); + } +} + +inline void triSurfFeatureEdges::edgeSubsetIndices +( + DynList<label>& indices +) const +{ + indices.clear(); + + forAllConstIter + ( + Map<meshSubset>, + featureEdgeSubsets_, + it + ) + indices.append(it.key()); +} + +template<class ListType> +inline void triSurfFeatureEdges::edgesInSubset +( + const label setI, + ListType& edgeLabels +) const +{ + edgeLabels.clear(); + + Map<meshSubset>::const_iterator it = featureEdgeSubsets_.find(setI); + if( it == featureEdgeSubsets_.end() ) + return; + + it().containedElements(edgeLabels); +} + +template<class ListType> +inline void triSurfFeatureEdges::updateEdgeSubsets +( + const ListType& newEdgeLabels +) +{ + for + ( + Map<meshSubset>::iterator it=featureEdgeSubsets_.begin(); + it!=featureEdgeSubsets_.end(); + ++it + ) + it().updateSubset(newEdgeLabels); +} + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfI.H b/meshLibrary/utilities/meshes/triSurf/triSurfI.H index 45420d447c975b0c3c23dd923954b8b4ad61e3f2..830c057d2a491438d2a863d8eadfb439a3887574 100644 --- a/meshLibrary/utilities/meshes/triSurf/triSurfI.H +++ b/meshLibrary/utilities/meshes/triSurf/triSurfI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,75 +34,17 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -inline void triSurf::existingFaceSubsets(DynList<word>& names) const +inline LongList<labelledTri>& triSurf::accessToFacets() { - names.clear(); - - std::map<word, labelListPMG>::const_iterator iter; - for(iter=triSubsets_.begin();iter!=triSubsets_.end();++iter) - names.append(iter->first); -} - -inline bool triSurf::doesFaceSubsetExist(const word& name) const -{ - if( triSubsets_.find(name) != triSubsets_.end() ) - return true; - - return false; -} - -inline const labelListPMG& triSurf::facesInSubset(const word& name) const -{ - if( !doesFaceSubsetExist(name) ) - FatalErrorIn - ( - "inline const labelListPMG& triSurf::" - "facesInSubset(const word& name) const" - ) << "Subset " << name << " does not exist!" << exit(FatalError); - - std::map<word, labelListPMG>::const_iterator iter = triSubsets_.find(name); - - return iter->second; -} - -inline void triSurf::addFacetsToSubset -( - const word& name, - const labelListPMG& newElements -) -{ - if( doesFaceSubsetExist(name) ) - { - std::map<word, labelListPMG>::iterator iter = triSubsets_.find(name); - - labelListPMG& elmts = iter->second; - boolList alreadyInside(this->size(), false); - forAll(elmts, elI) - alreadyInside[elmts[elI]] = true; - - forAll(newElements, elI) - if( - (newElements[elI] >= 0) && - (newElements[elI] < this->size()) && - !alreadyInside[newElements[elI]] - ) - { - elmts.append(newElements[elI]); - alreadyInside[newElements[elI]] = true; - } - } - else - { - triSubsets_.insert(std::pair<word, labelListPMG>(name, newElements)); - } + return triSurfFacets::triangles_; } -inline void triSurf::removeFaceSubset(const word& name) +inline geometricSurfacePatchList& triSurf::accessToPatches() { - if( doesFaceSubsetExist(name) ) - triSubsets_.erase(name); + return triSurfFacets::patches_; } +/* inline label triSurf::numberOfFaceGroups() const { if( !faceGroupPtr_ ) @@ -112,13 +53,14 @@ inline label triSurf::numberOfFaceGroups() const return nFaceGroups_; } -inline const labelListPMG& triSurf::faceGroups() const +inline const labelLongList& triSurf::faceGroups() const { if( !faceGroupPtr_ ) calculateFaceGroups(); return *faceGroupPtr_; } +*/ // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/dataConversion/foamToFLMA/writeMeshFLMA.H b/meshLibrary/utilities/meshes/triSurf/triSurfModifier.C similarity index 54% rename from meshLibrary/utilities/dataConversion/foamToFLMA/writeMeshFLMA.H rename to meshLibrary/utilities/meshes/triSurf/triSurfModifier.C index 3b8cd2a9e5a98bb585370d4ce2a1d3bd1d642557..41299f5430d1ea8147a9da58cc933890e8705f98 100644 --- a/meshLibrary/utilities/dataConversion/foamToFLMA/writeMeshFLMA.H +++ b/meshLibrary/utilities/meshes/triSurf/triSurfModifier.C @@ -1,59 +1,55 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -Class - writeMeshFLMA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Write mesh into flma format - -SourceFiles - writeMeshFLMA.C \*---------------------------------------------------------------------------*/ -#ifndef writeMeshFLMA_H -#define writeMeshFLMA_H - -#include "OFstream.H" -#include "word.H" - +#include "triSurfModifier.H" +#include "demandDrivenData.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { -class polyMeshGen; - -void writeMeshFLMA(const polyMeshGen& mesh, const word& fName); +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +//- Construct from parts +triSurfModifier::triSurfModifier(triSurf& surface) +: + surface_(surface) +{} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +triSurfModifier::~triSurfModifier() +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -} // End namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -#endif +} // End namespace Foam // ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfModifier.H b/meshLibrary/utilities/meshes/triSurf/triSurfModifier.H new file mode 100644 index 0000000000000000000000000000000000000000..16c39373e47c61d0f54e290100f3d50728e3c2f1 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfModifier.H @@ -0,0 +1,101 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfModifier + +Description + A class allowing non-const access to the member of the surface mesh + +SourceFiles + triSurfModifier.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfModifier_H +#define triSurfModifier_H + +#include "triSurf.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +/*---------------------------------------------------------------------------*\ + Class triSurfModifier Declaration +\*---------------------------------------------------------------------------*/ + +class triSurfModifier +{ + // Private data + //- reference to the surface mesh + triSurf& surface_; + + // Disallow bitwise assignment + //- Default construct + triSurfModifier(); + + //- Disallow default bitwise assignment + void operator=(const triSurfModifier&); + +public: + + // Constructors + + //- Construct from surface mesh + triSurfModifier(triSurf& surface); + + // Destructor + + ~triSurfModifier(); + + + // Member Functions + //- non-const access to points + inline pointField& pointsAccess(); + + //- access to facets + inline LongList<labelledTri>& facetsAccess(); + + //- non-const access to feature edges + inline edgeLongList& featureEdgesAccess(); + + //- access to patches + inline geometricSurfacePatchList& patchesAccess(); +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfModifierI.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfModifierI.H b/meshLibrary/utilities/meshes/triSurf/triSurfModifierI.H new file mode 100644 index 0000000000000000000000000000000000000000..26e16b9fad3fd90476e2702021670083b8e9e7d1 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfModifierI.H @@ -0,0 +1,61 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + + +\*---------------------------------------------------------------------------*/ + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +inline pointField& triSurfModifier::pointsAccess() +{ + return const_cast<pointField&>(surface_.points()); +} + +inline LongList<labelledTri>& triSurfModifier::facetsAccess() +{ + return const_cast<LongList<labelledTri>&>(surface_.facets()); +} + +inline edgeLongList& triSurfModifier::featureEdgesAccess() +{ + return const_cast<edgeLongList&>(surface_.featureEdges()); +} + +inline geometricSurfacePatchList& triSurfModifier::patchesAccess() +{ + return const_cast<geometricSurfacePatchList&>(surface_.patches()); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfPoints.C b/meshLibrary/utilities/meshes/triSurf/triSurfPoints.C new file mode 100644 index 0000000000000000000000000000000000000000..45b652f94ca1726eb3121cbccaa4eb6b23c17ccb --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfPoints.C @@ -0,0 +1,111 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfPoints.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfPoints::triSurfPoints() +: + points_(), + pointSubsets_() +{} + +triSurfPoints::triSurfPoints(const pointField& points) +: + points_(points), + pointSubsets_() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +// Destructor +triSurfPoints::~triSurfPoints() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +label triSurfPoints::addPointSubset(const word& subsetName) +{ + label id = pointSubsetIndex(subsetName); + if( id >= 0 ) + { + Warning << "Point subset " << subsetName << " already exists!" << endl; + return id; + } + + id = 0; + forAllConstIter(Map<meshSubset>, pointSubsets_, it) + id = Foam::max(id, it.key()+1); + + pointSubsets_.insert + ( + id, + meshSubset(subsetName, meshSubset::POINTSUBSET) + ); + + return id; +} + +void triSurfPoints::removePointSubset(const label subsetID) +{ + if( pointSubsets_.find(subsetID) == pointSubsets_.end() ) + return; + + pointSubsets_.erase(subsetID); +} + +word triSurfPoints::pointSubsetName(const label subsetID) const +{ + Map<meshSubset>::const_iterator it = pointSubsets_.find(subsetID); + if( it == pointSubsets_.end() ) + { + Warning << "Subset " << subsetID << " is not a point subset" << endl; + return word(); + } + + return it().name(); +} + +label triSurfPoints::pointSubsetIndex(const word& subsetName) const +{ + forAllConstIter(Map<meshSubset>, pointSubsets_, it) + { + if( it().name() == subsetName ) + return it.key(); + } + + return -1; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfPoints.H b/meshLibrary/utilities/meshes/triSurf/triSurfPoints.H new file mode 100644 index 0000000000000000000000000000000000000000..5df65e591421ccfa7d00994a8bbd92cbebf3f3bc --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfPoints.H @@ -0,0 +1,115 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfPoints + +Description + Point coordinates information for triangulated surface + +SourceFiles + triSurfPoints.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfPoints_H +#define triSurfPoints_H + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "meshSubset.H" +#include "pointField.H" +#include "DynList.H" +#include "Map.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +class triSurfPoints +{ +protected: + + // Protected data + //- list of vertices + pointField points_; + + //- map of point subsets + Map<meshSubset> pointSubsets_; + + // Disallow bitwise assignment + void operator=(const triSurfPoints&); + + triSurfPoints(const triSurfPoints&); + +public: + + // Constructors + //- Null constructor + triSurfPoints(); + + //- Construct from vertices + triSurfPoints(const pointField& points); + + // Destructor + ~triSurfPoints(); + + // Member functions + //- return the number of points + inline label nPoints() const; + + //- access to points + inline const pointField& points() const; + + //- append a vertex to the end of the list + inline void appendVertex(const point& p); + + //- point subsets + label addPointSubset(const word&); + void removePointSubset(const label); + word pointSubsetName(const label) const; + label pointSubsetIndex(const word&) const; + inline void addPointToSubset(const label, const label); + inline void removePointFromSubset(const label, const label); + inline void pointInSubsets(const label, DynList<label>&) const; + inline void pointSubsetIndices(DynList<label>&) const; + template<class ListType> + inline void pointsInSubset(const label, ListType&) const; + template<class ListType> + inline void updatePointSubsets(const ListType&); +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfPointsI.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/meshes/triSurf/triSurfPointsI.H b/meshLibrary/utilities/meshes/triSurf/triSurfPointsI.H new file mode 100644 index 0000000000000000000000000000000000000000..720c534b4505752065e7b4dc1cbc8394ab5eeb35 --- /dev/null +++ b/meshLibrary/utilities/meshes/triSurf/triSurfPointsI.H @@ -0,0 +1,148 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + + +\*---------------------------------------------------------------------------*/ + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "triSurfPoints.H" + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +inline label triSurfPoints::nPoints() const +{ + return points_.size(); +} + +inline const pointField& triSurfPoints::points() const +{ + return points_; +} + +inline void triSurfPoints::appendVertex(const point& p) +{ + const label s = points_.size(); + points_.setSize(s+1); + points_[s] = p; +} + +inline void triSurfPoints::addPointToSubset +( + const label setI, + const label pointI +) +{ + Map<meshSubset>::iterator it = pointSubsets_.find(setI); + if( it == pointSubsets_.end() ) + return; + + it().addElement(pointI); +} + +inline void triSurfPoints::removePointFromSubset +( + const label setI, + const label pointI +) +{ + Map<meshSubset>::iterator it = pointSubsets_.find(setI); + if( it == pointSubsets_.end() ) + return; + + it().removeElement(pointI); +} + +inline void triSurfPoints::pointInSubsets +( + const label pointI, + DynList<label>& pointSubsets +) const +{ + pointSubsets.clear(); + + forAllConstIter + ( + Map<meshSubset>, + pointSubsets_, + it + ) + { + if( it().contains(pointI) ) + pointSubsets.append(it.key()); + } +} + +inline void triSurfPoints::pointSubsetIndices(DynList<label>& indices) const +{ + indices.clear(); + + forAllConstIter + ( + Map<meshSubset>, + pointSubsets_, + it + ) + indices.append(it.key()); +} + +template<class ListType> +inline void triSurfPoints::pointsInSubset +( + const label setI, + ListType& pointLabels +) const +{ + pointLabels.clear(); + + Map<meshSubset>::const_iterator it = + pointSubsets_.find(setI); + if( it == pointSubsets_.end() ) + return; + + it().containedElements(pointLabels); +} + +template<class ListType> +inline void triSurfPoints::updatePointSubsets(const ListType& newNodeLabels) +{ + for + ( + Map<meshSubset>::iterator it=pointSubsets_.begin(); + it!=pointSubsets_.end(); + ++it + ) + it().updateSubset(newNodeLabels); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/nonManifoldMeshing/findNonManifoldInterfaces/findNonManifoldInterfaces.C b/meshLibrary/utilities/nonManifoldMeshing/findNonManifoldInterfaces/findNonManifoldInterfaces.C new file mode 100644 index 0000000000000000000000000000000000000000..15c92206aec541a693180c196293e1976a4da9a0 --- /dev/null +++ b/meshLibrary/utilities/nonManifoldMeshing/findNonManifoldInterfaces/findNonManifoldInterfaces.C @@ -0,0 +1,298 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "findNonManifoldInterfaces.H" +#include "meshOctree.H" +#include "findCellsIntersectingSurface.H" +#include "triSurf.H" +#include "demandDrivenData.H" + +#define DEBUGNonManifoldInterfaces + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void findNonManifoldInterfaces::findIntersectedCells() +{ + Info << "Starting finding cells intersected by the surface" << endl; + + findCellsIntersectingSurface cis(mesh_, octree_); + + const VRWGraph& facetsIntersectedCells = cis.facetsIntersectingCells(); + + //- find which surface patches intersect a cell + const triSurf& surface = octree_.surface(); + patchesIntersectingCells_.clear(); + patchesIntersectingCells_.setSize(facetsIntersectedCells.size()); + + forAll(facetsIntersectedCells, cellI) + { + forAllRow(facetsIntersectedCells, cellI, i) + { + const label triI = facetsIntersectedCells(cellI, i); + patchesIntersectingCells_.appendIfNotIn + ( + cellI, + surface[triI].region() + ); + } + } + + # ifdef DEBUGNonManifoldInterfaces + Map<label> regionToID; + forAll(patchesIntersectingCells_, cellI) + { + forAllRow(patchesIntersectingCells_, cellI, i) + { + const label regionI = patchesIntersectingCells_(cellI, i); + Map<label>::iterator iter = regionToID.find(regionI); + if( iter == regionToID.end() ) + { + const word sName = + "intersected_"+mesh_.boundaries()[regionI].patchName(); + regionToID.insert + ( + regionI, + mesh_.addCellSubset(sName) + ); + + iter = regionToID.find(regionI); + } + + mesh_.addCellToSubset(iter(), cellI); + } + } + # endif + + Info << "Finished finding cells intersected by the surface" << endl; +} + +void findNonManifoldInterfaces::findNeighbouringGroups() +{ + //- start assigning neighbouring cells of the intersected cells into groups + neiGroups_.setSize(0); + neiGroups_.setSize(patchesIntersectingCells_.size()); + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + + for(label fI=0;fI<mesh_.nInternalFaces();++fI) + { + const label own = owner[fI]; + const label nei = neighbour[fI]; + + if( patchesIntersectingCells_.sizeOfRow(own) ) + { + forAllRow(patchesIntersectingCells_, own, i) + { + const label patchI = patchesIntersectingCells_(own, i); + + if( !patchesIntersectingCells_.contains(nei, patchI) ) + neiGroups_.append(nei, patchI); + } + } + else if( patchesIntersectingCells_.sizeOfRow(nei) ) + { + forAllRow(patchesIntersectingCells_, nei, i) + { + const label patchI = patchesIntersectingCells_(nei, i); + + if( !patchesIntersectingCells_.contains(own, patchI) ) + neiGroups_.append(own, patchI); + } + } + } + + # ifdef DEBUGNonManifoldInterfaces + Map<label> regionToID; + forAll(neiGroups_, cellI) + { + forAllRow(neiGroups_, cellI, i) + { + const label regionI = neiGroups_(cellI, i); + Map<label>::iterator iter = regionToID.find(regionI); + if( iter == regionToID.end() ) + { + const word sName = + "neighboursOfPatch_" + + mesh_.boundaries()[regionI].patchName(); + + regionToID.insert + ( + regionI, + mesh_.addCellSubset(sName) + ); + + iter = regionToID.find(regionI); + } + + mesh_.addCellToSubset(iter(), cellI); + } + } + # endif +} + +bool findNonManifoldInterfaces::findFaceCandidates() +{ + internalFacePatches_.clear(); + internalFacePatches_.setSize(mesh_.nInternalFaces()); + + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + + forAll(internalFacePatches_, faceI) + { + const label own = owner[faceI]; + const label nei = neighbour[faceI]; + + forAllRow(patchesIntersectingCells_, own , i) + { + const label patchI = patchesIntersectingCells_(own, i); + + if( + !patchesIntersectingCells_.contains(nei, patchI) && + neiGroups_.contains(nei, patchI) + ) + internalFacePatches_.appendIfNotIn(faceI, patchI); + } + + forAllRow(patchesIntersectingCells_, nei , i) + { + const label patchI = patchesIntersectingCells_(nei, i); + + if( + !patchesIntersectingCells_.contains(own, patchI) && + neiGroups_.contains(own, patchI) + ) + internalFacePatches_.appendIfNotIn(faceI, patchI); + } + } + + # ifdef DEBUGNonManifoldInterfaces + Map<label> regionToID; + forAll(internalFacePatches_, faceI) + { + forAllRow(internalFacePatches_, faceI, i) + { + const label regionI = internalFacePatches_(faceI, i); + Map<label>::iterator iter = regionToID.find(regionI); + if( iter == regionToID.end() ) + { + const word sName = + "interfaceFaceToPatch_" + + mesh_.boundaries()[regionI].patchName(); + + regionToID.insert + ( + regionI, + mesh_.addFaceSubset(sName) + ); + + iter = regionToID.find(regionI); + } + + mesh_.addFaceToSubset(iter(), faceI); + } + } + + const label problemFacesID = mesh_.addFaceSubset("problematicFaces"); + # endif + + //- check if there exist any proximity problems + forAll(internalFacePatches_, faceI) + { + if( internalFacePatches_.sizeOfRow(faceI) < 2 ) + continue; + + //- check if it is a proximity problem + Info << "More than one internal interface assigned to face " + << faceI << endl; + + # ifdef DEBUGNonManifoldInterfaces + mesh_.addFaceToSubset(problemFacesID, faceI); + # endif + } + + return false; +} + +bool findNonManifoldInterfaces::extractInterfaces() +{ + + //- the procedure ended without any problems + return false; +} + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +// Construct from mesh and octree +findNonManifoldInterfaces::findNonManifoldInterfaces +( + polyMeshGen& mesh, + const meshOctree& octree +) +: + mesh_(mesh), + octree_(octree), + patchesIntersectingCells_(), + neiGroups_(), + internalFacePatches_() +{} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +findNonManifoldInterfaces::~findNonManifoldInterfaces() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void findNonManifoldInterfaces::createNonManifoldInterfaces() +{ + do + { + //- find cells intersected by the surface + findIntersectedCells(); + + //- find cells near the intersected cells + findNeighbouringGroups(); + } while( findFaceCandidates() ); + + if( extractInterfaces() ) + WarningIn + ( + "void findNonManifoldInterfaces::createNonManifoldInterfaces()" + ) << "Could not generate all internal interfaces" << endl; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/nonManifoldMeshing/findNonManifoldInterfaces/findNonManifoldInterfaces.H b/meshLibrary/utilities/nonManifoldMeshing/findNonManifoldInterfaces/findNonManifoldInterfaces.H new file mode 100644 index 0000000000000000000000000000000000000000..1a2d6a24ed086541a038757c7c9b244c24fce844 --- /dev/null +++ b/meshLibrary/utilities/nonManifoldMeshing/findNonManifoldInterfaces/findNonManifoldInterfaces.H @@ -0,0 +1,119 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + findNonManifoldInterfaces + +Description + Aclass for detecting non-manifold interfaces in the mesh + +SourceFiles + findNonManifoldInterfaces.C + +\*---------------------------------------------------------------------------*/ + +#ifndef findNonManifoldInterfaces_H +#define findNonManifoldInterfaces_H + +#include "polyMeshGenModifier.H" +#include "VRWGraph.H" +#include "boolList.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class meshOctree; +class meshSurfaceEngine; + +/*---------------------------------------------------------------------------*\ + Class findNonManifoldInterfaces Declaration +\*---------------------------------------------------------------------------*/ + +class findNonManifoldInterfaces +{ + //- reference to mesh + polyMeshGen& mesh_; + + //- const reference to meshOctree + const meshOctree& octree_; + + //- graph of mesh cells intesected by surface facets + VRWGraph patchesIntersectingCells_; + + //- cell groups assigned to neighbouring cells + //- of the intersected cells + VRWGraph neiGroups_; + + //- store information about face candidates + //- and the patches they may be mapped to + VRWGraph internalFacePatches_; + + // Private member functions + //- find intersected cells + void findIntersectedCells(); + + //- find neighbouring groups + void findNeighbouringGroups(); + + //- find faces which are candidates to be constrained + //- to the internal interfaces + bool findFaceCandidates(); + + //- extract non-manifold interfaces + bool extractInterfaces(); + + //- Disallow default bitwise copy construct + findNonManifoldInterfaces(const findNonManifoldInterfaces&); + + //- Disallow default bitwise assignment + void operator=(const findNonManifoldInterfaces&); + +public: + + // Constructors + + //- Construct from mesh and octree + findNonManifoldInterfaces(polyMeshGen& mesh, const meshOctree& octree); + + // Destructor + + ~findNonManifoldInterfaces(); + + // Public member functions + //- create interfaces + void createNonManifoldInterfaces(); +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/nonManifoldMeshing/removeCellsInSelectedDomains/removeCellsInSelectedDomains.C b/meshLibrary/utilities/nonManifoldMeshing/removeCellsInSelectedDomains/removeCellsInSelectedDomains.C new file mode 100644 index 0000000000000000000000000000000000000000..f1d6ab7c01ccea49823bed80a210e6eba22a36cb --- /dev/null +++ b/meshLibrary/utilities/nonManifoldMeshing/removeCellsInSelectedDomains/removeCellsInSelectedDomains.C @@ -0,0 +1,596 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "removeCellsInSelectedDomains.H" +#include "meshOctree.H" +#include "findCellsIntersectingSurface.H" +#include "triSurf.H" +#include "demandDrivenData.H" + +#include "helperFunctions.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGRemoveDomains + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +class meshNeighbourOperator +{ + const polyMeshGen& mesh_; + +public: + + meshNeighbourOperator(const polyMeshGen& mesh) + : + mesh_(mesh) + {} + + label size() const + { + return mesh_.cells().size(); + } + + void operator()(const label cellI, DynList<label>& neighbourCells) const + { + neighbourCells.clear(); + + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + + const cell& c = mesh_.cells()[cellI]; + + forAll(c, fI) + { + label nei = owner[c[fI]]; + + if( nei == cellI ) + nei = neighbour[c[fI]]; + + if( nei >= 0 ) + neighbourCells.append(nei); + } + } + + template<class labelListType> + void collectGroups + ( + std::map<label, DynList<label> >& neiGroups, + const labelListType& elementInGroup, + const DynList<label>& localGroupLabel + ) const + { + const PtrList<processorBoundaryPatch>& procBoundaries = + mesh_.procBoundaries(); + const labelList& owner = mesh_.owner(); + + //- send the data to other processors + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + labelList groupOwner(procBoundaries[patchI].patchSize()); + for(label faceI=0;faceI<size;++faceI) + { + const label groupI = elementInGroup[owner[start+faceI]]; + + if( groupI < 0 ) + { + groupOwner[faceI] = -1; + continue; + } + + groupOwner[faceI] = localGroupLabel[groupI]; + } + + OPstream toOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo(), + groupOwner.byteSize() + ); + + toOtherProc << groupOwner; + } + + //- receive data from other processors + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + + labelList receivedData; + + IPstream fromOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo() + ); + + fromOtherProc >> receivedData; + + forAll(receivedData, faceI) + { + if( receivedData[faceI] < 0 ) + continue; + + const label groupI = elementInGroup[owner[start+faceI]]; + + if( groupI < 0 ) + continue; + + DynList<label>& ng = neiGroups[localGroupLabel[groupI]]; + + //- store the connection over the inter-processor boundary + ng.appendIfNotIn(receivedData[faceI]); + } + } + } +}; + +class meshSelectorOperator +{ + const LongList<DynList<label, 2> >& intersectedCells_; + +public: + + meshSelectorOperator(const LongList<DynList<label, 2> >& intersectedCells) + : + intersectedCells_(intersectedCells) + {} + + bool operator()(const label cellI) const + { + if( intersectedCells_[cellI].size() ) + return false; + + return true; + } +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +const VRWGraph& removeCellsInSelectedDomains::cellsIntersectedBySurfaceFacets() +{ + if( !surfIntersectionPtr_ ) + surfIntersectionPtr_ = new findCellsIntersectingSurface(mesh_, octree_); + + return surfIntersectionPtr_->facetsIntersectingCells(); +} + +void removeCellsInSelectedDomains::markSelectedFacets() +{ + const triSurf& surf = octree_.surface(); + const geometricSurfacePatchList& patches = surf.patches(); + + VRWGraph usedPatch(patches.size(), 0); + + selectedFacets_.setSize(surf.size()); + forAll(selectedFacets_, rowI) + selectedFacets_.setRowSize(rowI, 0); + + forAll(domains_, domainI) + { + const DynList<word, 4>& domain = domains_[domainI]; + + forAll(domain, subsetI) + { + const word& sName = domain[subsetI]; + + label index = surf.facetSubsetIndex(sName); + + if( index >= 0 ) + { + //- it is a subset + labelLongList facetsInSubset; + surf.facetsInSubset(index, facetsInSubset); + + forAll(facetsInSubset, i) + selectedFacets_[facetsInSubset[i]].append(domainI); + } + else + { + //- check if it is a patch + forAll(patches, i) + { + if( patches[i].name() == sName ) + { + usedPatch.append(i, domainI); + } + } + } + } + } + + //- selected facets in used patches + forAll(surf, triI) + { + const labelledTri& tri = surf[triI]; + + forAllRow(usedPatch, tri.region(), i) + selectedFacets_[triI].append(usedPatch(tri.region(), i)); + } +} + +void removeCellsInSelectedDomains::findLeavesInsideRegions() +{ + insideLeaves_.setSize(octree_.numberOfLeaves()); + insideLeaves_ = false; + + //- find octree leaves intersected by the selected domains + boolList intersectedLeaves(insideLeaves_.size(), false); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(intersectedLeaves, leafI) + { + DynList<label> trianglesInLeaf; + octree_.containedTriangles(leafI, trianglesInLeaf); + + forAll(trianglesInLeaf, i) + { + if( selectedFacets_[trianglesInLeaf[i]].size() ) + { + intersectedLeaves[leafI] = true; + break; + } + } + } + + //- find islands of octree leaves which are not intersected by + //- the selected domains + + //- select the islands which do not have contact with the outer bondary +} + +void removeCellsInSelectedDomains::findAndRemoveCells() +{ + //- find the cells which are intersected by the selected domains + LongList<DynList<label, 2> > intersectedCells(mesh_.cells().size()); + + const VRWGraph& facetsIntersectingCell = cellsIntersectedBySurfaceFacets(); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(facetsIntersectingCell, cellI) + { + forAllRow(facetsIntersectingCell, cellI, triI) + { + const label fI = facetsIntersectingCell(cellI, triI); + + forAllRow(selectedFacets_, fI, domainI) + intersectedCells[cellI].append(selectedFacets_(fI, domainI)); + } + } + + # ifdef DEBUGRemoveDomains + labelList domainIds(domains_.size()); + forAll(domainIds, i) + { + domainIds[i] = + mesh_.addCellSubset("intersectingDomain_"+help::scalarToText(i)); + } + + forAll(intersectedCells, i) + { + const DynList<label, 2>& doms = intersectedCells[i]; + + forAll(doms, ii) + mesh_.addCellToSubset(domainIds[doms[i]], i); + }; + # endif + + //- find islands of cells which are not intersected by the selected domains + //const cellListPMG& cells = mesh_.cells(); + labelLongList findCellGroups; + + const label nGroups = + help::groupMarking + ( + findCellGroups, + meshNeighbourOperator(mesh_), + meshSelectorOperator(intersectedCells) + ); + + # ifdef DEBUGRemoveDomains + Info << "Number of groups " << nGroups << endl; + Info << "2.1 Here" << endl; + labelList groupToId(nGroups); + for(label i=0;i<nGroups;++i) + groupToId[i] = mesh_.addCellSubset("group_"+help::scalarToText(i)); + + forAll(findCellGroups, i) + { + if( findCellGroups[i] != -1 ) + mesh_.addCellToSubset(groupToId[findCellGroups[i]], i); + } + # endif + + //- collect which domains are assigned to facets neighbouring + //- groups + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + + List<DynList<label> > neiDomains(nGroups); + for(label faceI=0;faceI<mesh_.nInternalFaces();++faceI) + { + const label own = owner[faceI]; + const label nei = neighbour[faceI]; + + if( intersectedCells[own].size() && (findCellGroups[nei] != -1) ) + { + forAll(intersectedCells[own], domainI) + neiDomains[findCellGroups[nei]].appendIfNotIn + ( + intersectedCells[own][domainI] + ); + } + else if( intersectedCells[nei].size() && (findCellGroups[own] != -1) ) + { + forAll(intersectedCells[nei], domainI) + neiDomains[findCellGroups[own]].appendIfNotIn + ( + intersectedCells[nei][domainI] + ); + } + } + + if( Pstream::parRun() ) + { + const PtrList<processorBoundaryPatch>& procBoundaries = + mesh_.procBoundaries(); + + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + labelList sendGroup(size); + for(label fI=0;fI<size;++fI) + sendGroup[fI] = findCellGroups[owner[start+fI]]; + + OPstream toOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo(), + sendGroup.byteSize() + ); + + toOtherProc << sendGroup; + } + + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + + labelList receivedGroup; + + IPstream fromOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo() + ); + + fromOtherProc >> receivedGroup; + + forAll(receivedGroup, fI) + { + const label own = owner[start+fI]; + + if( intersectedCells[own].size() && (receivedGroup[fI] != -1) ) + { + forAll(intersectedCells[own], domainI) + neiDomains[receivedGroup[fI]].appendIfNotIn + ( + intersectedCells[own][domainI] + ); + } + } + } + } + + # ifdef DEBUGRemoveDomains + Info << "1. Nei domains " << neiDomains << endl; + # endif + + //- find a common group for all cell neighbours of a group + for(label faceI=0;faceI<mesh_.nInternalFaces();++faceI) + { + const label own = owner[faceI]; + const label nei = neighbour[faceI]; + + if( intersectedCells[own].size() && (findCellGroups[nei] != -1) ) + { + const label groupI = findCellGroups[nei]; + forAllReverse(neiDomains[groupI], domainI) + { + const label neiDomain = neiDomains[groupI][domainI]; + if( !intersectedCells[own].contains(neiDomain) ) + neiDomains[groupI].removeElement(domainI); + } + } + else if( intersectedCells[nei].size() && (findCellGroups[own] != -1) ) + { + const label groupI = findCellGroups[own]; + forAllReverse(neiDomains[groupI], domainI) + { + const label neiDomain = neiDomains[groupI][domainI]; + if( !intersectedCells[nei].contains(neiDomain) ) + neiDomains[groupI].removeElement(domainI); + } + } + } + + if( Pstream::parRun() ) + { + const PtrList<processorBoundaryPatch>& procBoundaries = + mesh_.procBoundaries(); + + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + labelList sendGroup(size); + for(label fI=0;fI<size;++fI) + sendGroup[fI] = findCellGroups[owner[start+fI]]; + + OPstream toOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo(), + sendGroup.byteSize() + ); + + toOtherProc << sendGroup; + } + + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + + labelList receivedGroup; + + IPstream fromOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo() + ); + + fromOtherProc >> receivedGroup; + + forAll(receivedGroup, fI) + { + const label own = owner[start+fI]; + + const label groupI = receivedGroup[fI]; + if( intersectedCells[own].size() && (groupI != -1) ) + { + forAllReverse(neiDomains[groupI], domainI) + { + const label neiDomain = neiDomains[groupI][domainI]; + if( !intersectedCells[own].contains(neiDomain) ) + neiDomains[groupI].removeElement(domainI); + } + } + } + } + } + + # ifdef DEBUGRemoveDomains + Info << "2. Nei domains " << neiDomains << endl; + # endif + + //- check which islands of cells correspond to octree boxes + //- marked as internal boxes + boolList internalCells(intersectedCells.size(), false); + + forAll(findCellGroups, cellI) + { + const label groupI = findCellGroups[cellI]; + + //- do not remove cells which are not assigned to a domain + if( groupI < 0 ) + continue; + + //- do not remove cells intersected by the selected surface elements + if( intersectedCells[cellI].size() ) + continue; + + //- remove domains surrounded by facets in a single user-selected domain + if( neiDomains[groupI].size() != 1 ) + continue; + + //- mark cell for removal + internalCells[cellI] = true; + } + + //- remove cells inside the selected domains + polyMeshGenModifier(mesh_).removeCells(internalCells); +} + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +removeCellsInSelectedDomains::removeCellsInSelectedDomains +( + polyMeshGen& mesh, + const meshOctree& octree +) +: + mesh_(mesh), + octree_(octree), + domains_(), + selectedFacets_(), + surfIntersectionPtr_(NULL), + insideLeaves_(octree_.numberOfLeaves(), false) +{} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +removeCellsInSelectedDomains::~removeCellsInSelectedDomains() +{ + deleteDemandDrivenData(surfIntersectionPtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void removeCellsInSelectedDomains::selectCellsInDomain(const wordList& domain) +{ + const label s = domains_.size(); + + domains_.setSize(s+1); + + domains_[s] = domain; +} + +void removeCellsInSelectedDomains::removeCells() +{ + Info << "Starting removing cells in user-selected domains" << endl; + + markSelectedFacets(); + + //findLeavesInsideRegions(); + + findAndRemoveCells(); + + Info << "Finished removing cells in user-selected domains" << endl; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/nonManifoldMeshing/removeCellsInSelectedDomains/removeCellsInSelectedDomains.H b/meshLibrary/utilities/nonManifoldMeshing/removeCellsInSelectedDomains/removeCellsInSelectedDomains.H new file mode 100644 index 0000000000000000000000000000000000000000..843220850bd3a77b88d2eb918870a0379edfff32 --- /dev/null +++ b/meshLibrary/utilities/nonManifoldMeshing/removeCellsInSelectedDomains/removeCellsInSelectedDomains.H @@ -0,0 +1,128 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + removeCellsInSelectedDomains + +Description + Removes cells inside the domains in the multi-domains mesh + which are specified by the user + +SourceFiles + removeCellsInSelectedDomains.C + +\*---------------------------------------------------------------------------*/ + +#ifndef removeCellsInSelectedDomains_H +#define removeCellsInSelectedDomains_H + +#include "polyMeshGenModifier.H" +#include "boolList.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class meshOctree; +class findCellsIntersectingSurface; + +/*---------------------------------------------------------------------------*\ + Class removeCellsInSelectedDomains Declaration +\*---------------------------------------------------------------------------*/ + +class removeCellsInSelectedDomains +{ + // Private data + //- reference to mesh + polyMeshGen& mesh_; + + //- const reference to meshOctree + const meshOctree& octree_; + + //- regions which shall not be meshed + DynList<DynList<word, 4> > domains_; + + //- facets which are part of the selected domains + VRWGraph selectedFacets_; + + //- intersect cells with the surface mesh + findCellsIntersectingSurface* surfIntersectionPtr_; + + //- octree leaves inside the domains which shall be removed + boolList insideLeaves_; + + // Private member functions + //- return a graph containing information which surface facets + //- intersect each cell in the mesh + const VRWGraph& cellsIntersectedBySurfaceFacets(); + + //- find facets contained in user-selected patches/subsets + void markSelectedFacets(); + + //- find octree boxed inside the given regions + void findLeavesInsideRegions(); + + //- perform removal of cells + void findAndRemoveCells(); + + //- Disallow default bitwise copy construct + removeCellsInSelectedDomains(const removeCellsInSelectedDomains&); + + //- Disallow default bitwise assignment + void operator=(const removeCellsInSelectedDomains&); + +public: + + // Constructors + + //- Construct from mesh and octree + removeCellsInSelectedDomains + ( + polyMeshGen& mesh, + const meshOctree& octree + ); + + // Destructor + + ~removeCellsInSelectedDomains(); + + // Public member functions + //- assing a domain by giving a list of patches/subsets bounding it + //- shall be called prior to removeCells + void selectCellsInDomain(const wordList&); + + //- perform removal of cells + void removeCells(); +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctree.C b/meshLibrary/utilities/octrees/meshOctree/meshOctree.C index 9a03ab2134c156446fa3947745558143d6fcd5d9..9e58a6a212568e42f22fd5b41e906ded932f030b 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctree.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctree.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -28,11 +27,12 @@ Description #include "meshOctree.H" #include "triSurf.H" -#include "IOdictionary.H" #include "boundBox.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGSearch @@ -43,8 +43,8 @@ namespace Foam // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // -// Construct from surface and IOdictionary -meshOctree::meshOctree(const triSurf& ts) +// Construct from surface +meshOctree::meshOctree(const triSurf& ts, const bool isQuadtree) : surface_(ts), neiProcs_(), @@ -58,7 +58,8 @@ meshOctree::meshOctree(const triSurf& ts) vrtLeavesPos_(), regularityPositions_(), dataSlots_(), - leaves_() + leaves_(), + isQuadtree_(isQuadtree) { Info << "Constructing octree" << endl; @@ -188,7 +189,7 @@ void meshOctree::setOctantVectorsAndPositions() void meshOctree::createInitialOctreeBox() { //- create initial octree box - boundBox bb(surface_.localPoints()); + boundBox bb(surface_.points()); const point& min_ = bb.min(); const point& max_ = bb.max(); @@ -213,6 +214,7 @@ void meshOctree::createInitialOctreeBox() } //- allocate data slots + # ifdef USE_OMP if( omp_get_num_procs() > 0 ) { dataSlots_.setSize(omp_get_num_procs()); @@ -221,18 +223,36 @@ void meshOctree::createInitialOctreeBox() { dataSlots_.setSize(1); } + # else + dataSlots_.setSize(1); + # endif meshOctreeSlot* slotPtr = &dataSlots_[0]; - slotPtr->cubes_.append - ( - meshOctreeCube + if( !isQuadtree_ ) + { + slotPtr->cubes_.append ( - meshOctreeCubeCoordinates(0, 0, 0, 0), - surface_.size(), - slotPtr - ) - ); + meshOctreeCube + ( + meshOctreeCubeCoordinates(0, 0, 0, 0), + surface_.size(), + slotPtr + ) + ); + } + else + { + slotPtr->cubes_.append + ( + meshOctreeCube + ( + meshOctreeCubeCoordinates(0, 0, -10, 0), + surface_.size(), + slotPtr + ) + ); + } initialCubePtr_ = &slotPtr->cubes_[0]; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctree.H b/meshLibrary/utilities/octrees/meshOctree/meshOctree.H index 2073b0290c153d66629e2b56dcbacf92ee69ce95..650dfc277b4cf9c4154a7572acbefa5b39fb3dee 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctree.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctree.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctree @@ -49,7 +48,6 @@ namespace Foam // Forward declarations class triSurf; -class IOdictionary; /*---------------------------------------------------------------------------*\ Class meshOctree Declaration @@ -91,6 +89,9 @@ class meshOctree //- list of cubes which are leaves of the octree LongList<meshOctreeCube*> leaves_; + //- a flag whether is true if is it a quadtree + const bool isQuadtree_; + // Private member functions //- set data needed for finding neighbours void setOctantVectorsAndPositions(); @@ -125,7 +126,7 @@ public: // Constructors //- Construct from surface - meshOctree(const triSurf&); + meshOctree(const triSurf&, const bool isQuadtree = false); // Destructor @@ -137,6 +138,9 @@ public: //- find a cube containing the vertex label findLeafContainingVertex(const point&) const; + //- is octree a quadtree or an octree + inline bool isQuadtree() const; + //- return octant vectors inline const FixedList<Vector<label>, 8>& octantVectors() const; @@ -159,6 +163,7 @@ public: ( point& nearest, scalar& distSq, + label& nearestTriangle, label& region, const point& p ) const; @@ -168,25 +173,48 @@ public: ( point& nearest, scalar& distSq, + label& nearestTriangle, const label region, const point& p ) const; - //- find nearest surface edges vertex to the given vertex + //- find nearest feature-edges vertex to a given vertex bool findNearestEdgePoint ( - const point& p, - const DynList<label>& regions, point& edgePoint, - scalar& distSq + scalar& distSq, + label& nearestEdge, + const point& p, + const DynList<label>& regions ) const; - bool findNearestVertexToTheEdge + bool findNearestPointToEdge ( + point& nearest, + scalar& distSq, + label& nearestEdge, const FixedList<point, 2>& edgePoints, - const FixedList<label, 2>& edgePointRegions, + const FixedList<label, 2>& edgePointRegions + ) const; + + //- find nearest corner point + bool findNearestCorner + ( point& nearest, - scalar& distSq + scalar& distSq, + label& nearestPoint, + const point& p, + const DynList<label>& patches + ) const; + + //- find the nearest vertex to the given patches + bool findNearestPointToPatches + ( + point& nearest, + scalar& distSq, + const point& p, + const DynList<label>& patches, + const scalar tol = 1e-4 ) const; //- return a reference to the surface diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.C index f7bfb4afc17fafc15ae2faba4b756326221860ce..c6f007b51370460c2abc3d19e3d69779ead820bc 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -51,12 +50,12 @@ void meshOctreeAddressing::clearOut() void meshOctreeAddressing::clearNodeAddressing() { - nNodes_ = 0; + nNodes_ = 0; deleteDemandDrivenData(octreePointsPtr_); - deleteDemandDrivenData(nodeLabelsPtr_); - deleteDemandDrivenData(nodeLeavesPtr_); - - deleteDemandDrivenData(nodeTypePtr_); + deleteDemandDrivenData(nodeLabelsPtr_); + deleteDemandDrivenData(nodeLeavesPtr_); + + deleteDemandDrivenData(nodeTypePtr_); } void meshOctreeAddressing::clearBoxTypes() @@ -104,18 +103,18 @@ meshOctreeAddressing::meshOctreeAddressing ( const meshOctree& mo, const dictionary& dict, - bool useDATABoxes + bool useDATABoxes ) : - octree_(mo), - meshDict_(dict), - useDATABoxes_(useDATABoxes), - nNodes_(0), + octree_(mo), + meshDict_(dict), + useDATABoxes_(useDATABoxes), + nNodes_(0), octreePointsPtr_(NULL), - nodeLabelsPtr_(NULL), - nodeLeavesPtr_(NULL), - boxTypePtr_(NULL), - nodeTypePtr_(NULL), + nodeLabelsPtr_(NULL), + nodeLeavesPtr_(NULL), + boxTypePtr_(NULL), + nodeTypePtr_(NULL), octreeFacesPtr_(NULL), octreeFacesOwnersPtr_(NULL), octreeFacesNeighboursPtr_(NULL), @@ -138,40 +137,51 @@ meshOctreeAddressing::meshOctreeAddressing globalLeafToLocalPtr_(NULL), leafAtProcsPtr_(NULL) { - if( !useDATABoxes && dict.found("keepCellsIntersectingBoundary") ) - { - useDATABoxes_ = readBool(dict.lookup("keepCellsIntersectingBoundary")); - } - + if( !useDATABoxes && dict.found("keepCellsIntersectingBoundary") ) + { + useDATABoxes_ = readBool(dict.lookup("keepCellsIntersectingBoundary")); + } + + if( dict.found("nonManifoldMeshing") ) + { + const bool nonManifoldMesh + ( + readBool(dict.lookup("nonManifoldMeshing")) + ); + + if( nonManifoldMesh ) + useDATABoxes_ = true; + } + if( Pstream::parRun() ) { meshOctreeModifier om(const_cast<meshOctree&>(octree_)); om.addLayerFromNeighbouringProcessors(); } - - //- check for glued regions - checkGluedRegions(); + + //- check for glued regions + checkGluedRegions(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // meshOctreeAddressing::~meshOctreeAddressing() { - clearOut(); + clearOut(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // bool meshOctreeAddressing::isIntersectedFace(const label fI) const { - const labelListPMG& owner = octreeFaceOwner(); - const labelListPMG& neighbour = octreeFaceNeighbour(); - + const labelLongList& owner = octreeFaceOwner(); + const labelLongList& neighbour = octreeFaceNeighbour(); + if( neighbour[fI] < 0 ) return false; - + Map<label> nAppearances; - DynList<label> triangles(100); + DynList<label> triangles; octree_.containedTriangles(owner[fI], triangles); forAll(triangles, triI) { @@ -184,7 +194,7 @@ bool meshOctreeAddressing::isIntersectedFace(const label fI) const nAppearances.insert(triangles[triI], 1); } } - + triangles.clear(); octree_.containedTriangles(neighbour[fI], triangles); forAll(triangles, triI) @@ -198,7 +208,7 @@ bool meshOctreeAddressing::isIntersectedFace(const label fI) const nAppearances.insert(triangles[triI], 1); } } - + forAllConstIter(Map<label>, nAppearances, iter) { if( iter() == 2 ) @@ -209,16 +219,16 @@ bool meshOctreeAddressing::isIntersectedFace(const label fI) const octree_.returnLeaf(neighbour[fI]).level() ) return true; - + //- check intersection by geometric testing const triSurf& surf = octree_.surface(); const pointField& points = this->octreePoints(); const VRWGraph& faces = this->octreeFaces(); - + face f(faces.sizeOfRow(fI)); forAll(f, pI) f[pI] = faces(fI, pI); - + if( help::doFaceAndTriangleIntersect ( @@ -231,31 +241,31 @@ bool meshOctreeAddressing::isIntersectedFace(const label fI) const return true; } } - + return false; } bool meshOctreeAddressing::isIntersectedEdge(const label eI) const { const VRWGraph& edgeCubes = this->edgeLeaves(); - + Map<label> nAppearances; - DynList<label> triangles(100); + DynList<label> triangles; bool sameLevel(true); - + forAllRow(edgeCubes, eI, i) { const label leafI = edgeCubes(eI, i); if( !octree_.hasContainedTriangles(leafI) ) return false; - + if ( octree_.returnLeaf(leafI).level() != octree_.returnLeaf(edgeCubes(eI, 0)).level() ) sameLevel = false; - + triangles.clear(); octree_.containedTriangles(leafI, triangles); forAll(triangles, triI) @@ -270,19 +280,19 @@ bool meshOctreeAddressing::isIntersectedEdge(const label eI) const } } } - + forAllConstIter(Map<label>, nAppearances, iter) { if( iter() == edgeCubes.sizeOfRow(eI) ) { if( sameLevel ) return true; - + //- check for geometric intersection const LongList<edge>& edges = this->octreeEdges(); const pointField& points = this->octreePoints(); - point intersection; - + point intersection(vector::zero); + if( help::triLineIntersection ( @@ -296,7 +306,7 @@ bool meshOctreeAddressing::isIntersectedEdge(const label eI) const return true; } } - + return false; } @@ -307,22 +317,22 @@ void meshOctreeAddressing::edgeIntersections ) const { intersections.clear(); - + const LongList<edge>& edges = this->octreeEdges(); const pointField& points = this->octreePoints(); const VRWGraph& edgeCubes = this->edgeLeaves(); const scalar tol = SMALL * mag(points[edges[eI].start()] - points[edges[eI].end()]); - + Map<label> nAppearances; - DynList<label> triangles(100); - + DynList<label> triangles; + forAllRow(edgeCubes, eI, i) { const label leafI = edgeCubes(eI, i); if( !octree_.hasContainedTriangles(leafI) ) return; - + triangles.clear(); octree_.containedTriangles(leafI, triangles); forAll(triangles, triI) @@ -337,15 +347,15 @@ void meshOctreeAddressing::edgeIntersections } } } - + + point intersection(vector::zero); + forAllConstIter(Map<label>, nAppearances, iter) { if( iter() == edgeCubes.sizeOfRow(eI) ) { //- check for geometric intersection - point intersection; - - if( + const bool intersectionExists = help::triLineIntersection ( octree_.surface(), @@ -353,14 +363,15 @@ void meshOctreeAddressing::edgeIntersections points[edges[eI].start()], points[edges[eI].end()], intersection - ) - ) + ); + + if( intersectionExists ) { bool store(true); forAll(intersections, i) if( mag(intersections[i] - intersection) <= tol ) store = false; - + if( store ) intersections.append(intersection); } @@ -370,103 +381,106 @@ void meshOctreeAddressing::edgeIntersections void meshOctreeAddressing::cubesAroundEdge ( - const label leafI, - const direction eI, - FixedList<label, 4>& edgeCubes + const label leafI, + const direction eI, + FixedList<label, 4>& edgeCubes ) const { - const VRWGraph& nl = this->nodeLabels(); - const label nodeI = nl(leafI, meshOctreeCubeCoordinates::edgeNodes_[eI][0]); - const FRWGraph<label, 8>& pLeaves = this->nodeLeaves(); - - switch( eI ) - { - case 0: case 1: case 2: case 3: - { - edgeCubes[0] = pLeaves(nodeI, 1); - edgeCubes[1] = pLeaves(nodeI, 3); - edgeCubes[2] = pLeaves(nodeI, 5); - edgeCubes[3] = pLeaves(nodeI, 7); - } break; - case 4: case 5: case 6: case 7: - { - edgeCubes[0] = pLeaves(nodeI, 2); - edgeCubes[1] = pLeaves(nodeI, 3); - edgeCubes[2] = pLeaves(nodeI, 6); - edgeCubes[3] = pLeaves(nodeI, 7); - } break; - case 8: case 9: case 10: case 11: - { - edgeCubes[0] = pLeaves(nodeI, 4); - edgeCubes[1] = pLeaves(nodeI, 5); - edgeCubes[2] = pLeaves(nodeI, 6); - edgeCubes[3] = pLeaves(nodeI, 7); - } break; - default: - { - FatalErrorIn - ( - "void tetMeshExtractorOctree::cubesAroundEdge(const label," - "const direction, FixedList<label, 4>&)" - ) << "Invalid edge specified!!" << abort(FatalError); - } break; - }; + const VRWGraph& nl = this->nodeLabels(); + const label nodeI = nl(leafI, meshOctreeCubeCoordinates::edgeNodes_[eI][0]); + const FRWGraph<label, 8>& pLeaves = this->nodeLeaves(); + + switch( eI ) + { + case 0: case 1: case 2: case 3: + { + edgeCubes[0] = pLeaves(nodeI, 1); + edgeCubes[1] = pLeaves(nodeI, 3); + edgeCubes[2] = pLeaves(nodeI, 5); + edgeCubes[3] = pLeaves(nodeI, 7); + } break; + case 4: case 5: case 6: case 7: + { + edgeCubes[0] = pLeaves(nodeI, 2); + edgeCubes[1] = pLeaves(nodeI, 3); + edgeCubes[2] = pLeaves(nodeI, 6); + edgeCubes[3] = pLeaves(nodeI, 7); + } break; + case 8: case 9: case 10: case 11: + { + edgeCubes[0] = pLeaves(nodeI, 4); + edgeCubes[1] = pLeaves(nodeI, 5); + edgeCubes[2] = pLeaves(nodeI, 6); + edgeCubes[3] = pLeaves(nodeI, 7); + } break; + default: + { + FatalErrorIn + ( + "void tetMeshExtractorOctree::cubesAroundEdge(const label," + "const direction, FixedList<label, 4>&)" + ) << "Invalid edge specified!!" << abort(FatalError); + } break; + }; } label meshOctreeAddressing::findEdgeCentre ( - const label leafI, - const direction eI + const label leafI, + const direction eI ) const { - const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); - const VRWGraph& nl = this->nodeLabels(); - const label nodeI = nl(leafI, meshOctreeCubeCoordinates::edgeNodes_[eI][0]); - const FRWGraph<label, 8>& pLeaves = this->nodeLeaves(); - - const direction level = oc.level(); - - label fI(-1); - switch( eI ) - { - case 0: case 1: case 2: case 3: - { - fI = 1; - } break; - case 4: case 5: case 6: case 7: - { - fI = 3; - } break; - case 8: case 9: case 10: case 11: - { - fI = 5; - } break; - default: - { - FatalErrorIn - ( - "label meshOctreeAddressing::findEdgeCentre" + if( octree_.isQuadtree() && eI >= 8 ) + return -1; + + const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); + const VRWGraph& nl = this->nodeLabels(); + const label nodeI = nl(leafI, meshOctreeCubeCoordinates::edgeNodes_[eI][0]); + const FRWGraph<label, 8>& pLeaves = this->nodeLeaves(); + + const direction level = oc.level(); + + label fI(-1); + switch( eI ) + { + case 0: case 1: case 2: case 3: + { + fI = 1; + } break; + case 4: case 5: case 6: case 7: + { + fI = 3; + } break; + case 8: case 9: case 10: case 11: + { + fI = 5; + } break; + default: + { + FatalErrorIn + ( + "label meshOctreeAddressing::findEdgeCentre" "(const label leafI, const direction eI) const" - ) << "Invalid edge specified!!" << abort(FatalError); - } break; - }; - - for(label i=0;i<4;++i) - { + ) << "Invalid edge specified!!" << abort(FatalError); + } break; + }; + + for(label i=0;i<4;++i) + { const label fNode = meshOctreeCubeCoordinates::faceNodes_[fI][i]; - - if( pLeaves(nodeI, fNode) < 0 ) - continue; - - const label leafJ = pLeaves(nodeI, fNode); - if( octree_.returnLeaf(leafJ).level() > level ) + + if( pLeaves(nodeI, fNode) < 0 ) + continue; + + const label leafJ = pLeaves(nodeI, fNode); + if( octree_.returnLeaf(leafJ).level() > level ) { const label shift = (i+2)%4; - return nl(leafJ, meshOctreeCubeCoordinates::faceNodes_[fI][shift]); + return nl(leafJ, meshOctreeCubeCoordinates::faceNodes_[fI][shift]); } - } - - return -1; + } + + return -1; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.H index 02f08be83d079e347459529b8c9db83e85882230..f7e314a9b2649871c40e9932c4ed54698173cb4a 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressing.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeAddressing Description Automatic octree for mesh generation. This class checks if the current - octree resolution is enough to resolve all surface features + octree resolution is enough to resolve all surface features SourceFiles meshOctreeAddressing.C @@ -61,38 +60,38 @@ class IOdictionary; class meshOctreeAddressing { // Private data - //- reference to the octree - const meshOctree& octree_; - - //- reference to the dictionary - const dictionary& meshDict_; - - //- use DATA boxes - bool useDATABoxes_; - - //- number of created octree nodes - mutable label nNodes_; + //- reference to the octree + const meshOctree& octree_; + + //- reference to the dictionary + const dictionary& meshDict_; + + //- use DATA boxes + bool useDATABoxes_; + + //- number of created octree nodes + mutable label nNodes_; //- coordinates of octree nodes mutable pointField* octreePointsPtr_; - - //- node labels - mutable VRWGraph* nodeLabelsPtr_; + + //- node labels + mutable VRWGraph* nodeLabelsPtr_; //- node leaves - mutable FRWGraph<label, 8>* nodeLeavesPtr_; + mutable FRWGraph<label, 8>* nodeLeavesPtr_; - //- identify which boxes should be used as mesh cells - mutable List<direction>* boxTypePtr_; + //- identify which boxes should be used as mesh cells + mutable List<direction>* boxTypePtr_; //- identify created nodes as OUTERNODE or INNERNODE - mutable List<direction>* nodeTypePtr_; + mutable List<direction>* nodeTypePtr_; // Additional addressing useful for some algorithms //- faces of the octree mutable VRWGraph* octreeFacesPtr_; - mutable labelListPMG* octreeFacesOwnersPtr_; - mutable labelListPMG* octreeFacesNeighboursPtr_; + mutable labelLongList* octreeFacesOwnersPtr_; + mutable labelLongList* octreeFacesNeighboursPtr_; //- octree box-faces addressing mutable VRWGraph* leafFacesPtr_; @@ -122,7 +121,7 @@ class meshOctreeAddressing mutable VRWGraph* edgeFacesPtr_; //- global octree point label - mutable labelListPMG* globalPointLabelPtr_; + mutable labelLongList* globalPointLabelPtr_; //- global point to local label addressing mutable Map<label>* globalPointToLocalPtr_; @@ -131,7 +130,7 @@ class meshOctreeAddressing mutable VRWGraph* pointProcsPtr_; //- global octree face label - mutable labelListPMG* globalFaceLabelPtr_; + mutable labelLongList* globalFaceLabelPtr_; //- global face label to local label addressing mutable Map<label>* globalFaceToLocalPtr_; @@ -140,29 +139,29 @@ class meshOctreeAddressing mutable VRWGraph* faceProcsPtr_; //- global leaf label - mutable labelListPMG* globalLeafLabelPtr_; + mutable labelLongList* globalLeafLabelPtr_; //- global leaf label to local label addressing for octree leaves mutable Map<label>* globalLeafToLocalPtr_; //- leaf at procs mutable VRWGraph* leafAtProcsPtr_; - - // Private member functions + + // Private member functions //- calculate octreePointsPtr_ void createOctreePoints() const; - //- calculate nodeLabelsPtr_ - void createNodeLabels() const; - - //- calculate nodeLeavesPtr_ - void createNodeLeaves() const; - - //- assemble boxTypePtr_ list - void findUsedBoxes() const; - - //- calculate nodeTypePtr_ - void calculateNodeType() const; + //- calculate nodeLabelsPtr_ + void createNodeLabels() const; + + //- calculate nodeLeavesPtr_ + void createNodeLeaves() const; + + //- assemble boxTypePtr_ list + void findUsedBoxes() const; + + //- calculate nodeTypePtr_ + void calculateNodeType() const; //- calculate faces void createOctreeFaces() const; @@ -187,17 +186,17 @@ class meshOctreeAddressing //- calculate edge-faces void calculateEdgeFaces() const; - - //- Clear allocated data - void clearOut(); + + //- Clear allocated data + void clearOut(); void clearBoxTypes(); void clearNodeAddressing(); void clearOctreeFaces(); void clearAddressing(); void clearParallelAddressing(); - - //- check if distinct parts are glued together - void checkGluedRegions(); + + //- check if distinct parts are glued together + void checkGluedRegions(); // Private member functions for parallel runs @@ -218,29 +217,29 @@ public: //- Construct from surface and dictionary meshOctreeAddressing - ( - const meshOctree& mo, - const dictionary& dict, - bool useDATABoxes = false - ); + ( + const meshOctree& mo, + const dictionary& dict, + bool useDATABoxes = false + ); // Destructor ~meshOctreeAddressing(); - // Enumerators - - enum octreeCubeTypes - { - NONE = 0, - MESHCELL = 1, - BOUNDARY = 2, - SPLITHEX = 4, - INNERNODE = 8, - OUTERNODE = 16, - BOUNDARYNODE = 32 - }; - + // Enumerators + + enum octreeCubeTypes + { + NONE = 0, + MESHCELL = 1, + BOUNDARY = 2, + SPLITHEX = 4, + INNERNODE = 8, + OUTERNODE = 16, + BOUNDARYNODE = 32 + }; + // Member Functions //- check if there exist any non-signly connected edges and vertices @@ -248,35 +247,35 @@ public: //- for the cartesian template void checkAndFixIrregularConnections(); - //- return number of octree nodes - inline label numberOfNodes() const; + //- return number of octree nodes + inline label numberOfNodes() const; //- return coordinates of octree vertices inline const pointField& octreePoints() const; - //- return nodeLabels - inline const VRWGraph& nodeLabels() const; + //- return nodeLabels + inline const VRWGraph& nodeLabels() const; - //- return nodeLeaves - inline const FRWGraph<label, 8>& nodeLeaves() const; - - //- return which octree boxes are used for mesh creation - inline const List<direction>& boxType() const; + //- return nodeLeaves + inline const FRWGraph<label, 8>& nodeLeaves() const; + + //- return which octree boxes are used for mesh creation + inline const List<direction>& boxType() const; //- return type of node (INNERNODE,or OUTERNODE) inline const List<direction>& nodeType() const; - - //- set box type - inline void setBoxType(const label boxI, const direction type); + + //- set box type + inline void setBoxType(const label boxI, const direction type); //- return octree faces, created for MESHCELL boxes inline const VRWGraph& octreeFaces() const; //- return owners of octree faces - inline const labelListPMG& octreeFaceOwner() const; + inline const labelLongList& octreeFaceOwner() const; //- return neighbours of octree faces - inline const labelListPMG& octreeFaceNeighbour() const; + inline const labelLongList& octreeFaceNeighbour() const; //- return octree box-faces addressing inline const VRWGraph& leafFaces() const; @@ -315,25 +314,25 @@ public: //- return edge-faces addressing inline const VRWGraph& edgeFaces() const; - - //- return const reference to meshOctree - inline const meshOctree& octree() const; - - //- find cubes around an edge (cubes must be at the same level) - void cubesAroundEdge - ( - const label leafI, - const direction eI, - FixedList<label, 4>& edgeCubes - ) const; - - //- find edge centre if it exists - label findEdgeCentre(const label leafI, const direction eI) const; + + //- return const reference to meshOctree + inline const meshOctree& octree() const; + + //- find cubes around an edge (cubes must be at the same level) + void cubesAroundEdge + ( + const label leafI, + const direction eI, + FixedList<label, 4>& edgeCubes + ) const; + + //- find edge centre if it exists + label findEdgeCentre(const label leafI, const direction eI) const; // Access to data needed for parallel execution //- return global point labels - inline const labelListPMG& globalPointLabel() const; + inline const labelLongList& globalPointLabel() const; //- global point label to local label. Only for processors points inline const Map<label>& globalToLocalPointAddressing() const; @@ -342,7 +341,7 @@ public: inline const VRWGraph& pointAtProcs() const; //- return global labels of octree faces - inline const labelListPMG& globalFaceLabel() const; + inline const labelLongList& globalFaceLabel() const; //- return global face label to face label. Only for processor faces inline const Map<label>& globalToLocalFaceAddressing() const; @@ -351,7 +350,7 @@ public: inline const VRWGraph& faceAtProcs() const; //- return global labels of octree leaves - inline const labelListPMG& globalLeafLabel() const; + inline const labelLongList& globalLeafLabel() const; //- return processors which contain each octree leaf inline const VRWGraph& leafAtProcs() const; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingCreation.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingCreation.C index bf48d09275a1d48097aff644f923051a2816f8d3..8f3dda3aee794eb9b70a54524b45a5917e613de4 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingCreation.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingCreation.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,11 +30,12 @@ Description #include "VRWGraphSMPModifier.H" #include "demandDrivenData.H" #include "meshOctree.H" -#include "labelListPMG.H" -#include "IOdictionary.H" +#include "labelLongList.H" #include "triSurf.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGVrt @@ -43,79 +43,97 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshOctreeAddressing::createOctreePoints() const { const VRWGraph& nodeLabels = this->nodeLabels(); const boundBox& rootBox = octree_.rootBox(); - + octreePointsPtr_ = new pointField(nNodes_); pointField& octreePoints = *octreePointsPtr_; - + const label nLeaves = nodeLabels.size(); + # ifdef USE_OMP # pragma omp parallel for schedule(guided) + # endif for(label cubeI=0;cubeI<nLeaves;++cubeI) { if( nodeLabels.sizeOfRow(cubeI) == 0 ) continue; - + FixedList<point, 8> vertices; const meshOctreeCubeBasic& oc = octree_.returnLeaf(cubeI); oc.vertices(rootBox, vertices); forAllRow(nodeLabels, cubeI, pI) { forAllRow(nodeLabels, cubeI, nI) - octreePoints[nodeLabels(cubeI, nI)] = vertices[nI]; + octreePoints[nodeLabels(cubeI, nI)] = vertices[nI]; } } } - + void meshOctreeAddressing::createNodeLabels() const { - const List<direction>& boxType = this->boxType(); - - nodeLabelsPtr_ = new VRWGraph(octree_.numberOfLeaves()); - VRWGraph& nodeLabels = *nodeLabelsPtr_; - + const List<direction>& boxType = this->boxType(); + + nodeLabelsPtr_ = new VRWGraph(octree_.numberOfLeaves()); + VRWGraph& nodeLabels = *nodeLabelsPtr_; + //- allocate storage for node labels forAll(nodeLabels, leafI) { if( boxType[leafI] ) { nodeLabels.setRowSize(leafI, 8); - + forAllRow(nodeLabels, leafI, i) nodeLabels(leafI, i) = -1; } } - + //- start creating node labels nNodes_ = 0; DynList<label> numLocalNodes; + # ifdef USE_OMP # pragma omp parallel //num_threads(Foam::max(nodeLabels.size() / 1000, 1)) + # endif { + # ifdef USE_OMP + const label nThreads = omp_get_num_threads(); + const label threadI = omp_get_thread_num(); + # else + const label nThreads = 1; + const label threadI = 0; + # endif + + # ifdef USE_OMP # pragma omp master - numLocalNodes.setSize(omp_get_num_threads()); - + # endif + numLocalNodes.setSize(nThreads); + + # ifdef USE_OMP # pragma omp barrier - + # endif + //- count the number of nodes local to each process - label& nLocalNodes = numLocalNodes[omp_get_thread_num()]; + label& nLocalNodes = numLocalNodes[threadI]; nLocalNodes = 0; - + + # ifdef USE_OMP # pragma omp for schedule(static, 100) + # endif forAll(nodeLabels, leafI) { forAllRow(nodeLabels, leafI, nI) { if( nodeLabels(leafI, nI) != -1 ) continue; - + FixedList<label, 8> pLeaves; octree_.findLeavesForCubeVertex(leafI, nI, pLeaves); - + FixedList<bool, 8> validLeaf(true); label minLeaf(leafI); forAll(pLeaves, plI) @@ -128,13 +146,13 @@ void meshOctreeAddressing::createNodeLabels() const validLeaf[plI] = false; validLeaf[i] = false; } - + if( !boxType[pLeaves[plI]] ) { validLeaf[plI] = false; pLeaves[plI] = -1; } - + if( validLeaf[plI] ) minLeaf = Foam::min(minLeaf, pLeaves[plI]); } @@ -143,7 +161,7 @@ void meshOctreeAddressing::createNodeLabels() const validLeaf[plI] = false; } } - + if( minLeaf == leafI && validLeaf[7-nI] ) { forAll(pLeaves, plI) @@ -152,31 +170,35 @@ void meshOctreeAddressing::createNodeLabels() const //- set node labels to -2 not to repeat searches nodeLabels(pLeaves[plI], (7-plI)) = -2; } - + ++nLocalNodes; } } } - + //- set start node for each process + # ifdef USE_OMP # pragma omp barrier - + # endif + label startNode(0); - for(label i=0;i<omp_get_thread_num();++i) + for(label i=0;i<threadI;++i) startNode += numLocalNodes[i]; - + //- start creating node labels + # ifdef USE_OMP # pragma omp for schedule(static, 100) + # endif forAll(nodeLabels, leafI) { forAllRow(nodeLabels, leafI, nI) { if( nodeLabels(leafI, nI) >= 0 ) continue; - + FixedList<label, 8> pLeaves; octree_.findLeavesForCubeVertex(leafI, nI, pLeaves); - + FixedList<bool, 8> validLeaf(true); label minLeaf(leafI); forAll(pLeaves, plI) @@ -189,13 +211,13 @@ void meshOctreeAddressing::createNodeLabels() const validLeaf[plI] = false; validLeaf[i] = false; } - + if( !boxType[pLeaves[plI]] ) { validLeaf[plI] = false; pLeaves[plI] = -1; } - + if( validLeaf[plI] ) minLeaf = Foam::min(minLeaf, pLeaves[plI]); } @@ -204,7 +226,7 @@ void meshOctreeAddressing::createNodeLabels() const validLeaf[plI] = false; } } - + if( (minLeaf == leafI) && validLeaf[7-nI] ) { forAll(pLeaves, plI) @@ -214,15 +236,17 @@ void meshOctreeAddressing::createNodeLabels() const //- location in the cube nodeLabels(pLeaves[plI], (7-plI)) = startNode; } - + //- store vertex label ++startNode; } } } - + //- set the number of nodes + # ifdef USE_OMP # pragma omp critical + # endif { nNodes_ = Foam::max(nNodes_, startNode); } @@ -232,33 +256,35 @@ void meshOctreeAddressing::createNodeLabels() const void meshOctreeAddressing::createNodeLeaves() const { const List<direction>& boxType = this->boxType(); - const VRWGraph& nodeLabels = this->nodeLabels(); - - //- allocate nodeLeavesPtr_ - nodeLeavesPtr_ = new FRWGraph<label, 8>(nNodes_); - FRWGraph<label, 8>& nodeLeaves = *nodeLeavesPtr_; + const VRWGraph& nodeLabels = this->nodeLabels(); + + //- allocate nodeLeavesPtr_ + nodeLeavesPtr_ = new FRWGraph<label, 8>(nNodes_); + FRWGraph<label, 8>& nodeLeaves = *nodeLeavesPtr_; boolList storedNode(nNodes_, false); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 100) + # endif forAll(nodeLabels, leafI) { forAllRow(nodeLabels, leafI, nI) { const label nodeI = nodeLabels(leafI, nI); - + if( storedNode[nodeI] ) continue; - + storedNode[nodeI] = true; - + FixedList<label, 8> pLeaves; octree_.findLeavesForCubeVertex(leafI, nI, pLeaves); - + forAll(pLeaves, plI) { if( pLeaves[plI] < 0 ) continue; - + if( !boxType[pLeaves[plI]] ) pLeaves[plI] = -1; } @@ -270,42 +296,83 @@ void meshOctreeAddressing::createNodeLeaves() const void meshOctreeAddressing::findUsedBoxes() const { - boxTypePtr_ = new List<direction>(octree_.numberOfLeaves(), NONE); - List<direction>& boxType = *boxTypePtr_; - - # pragma omp parallel for schedule(guided) + boxTypePtr_ = new List<direction>(octree_.numberOfLeaves(), NONE); + List<direction>& boxType = *boxTypePtr_; + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(boxType, leafI) - { - const meshOctreeCubeBasic& leaf = octree_.returnLeaf(leafI); - - if( - !octree_.hasContainedTriangles(leafI) && - (leaf.cubeType() & meshOctreeCubeBasic::INSIDE) - ) - boxType[leafI] |= MESHCELL; - } - - if( useDATABoxes_ ) - { - Info << "Using DATA boxes" << endl; - + { + const meshOctreeCubeBasic& leaf = octree_.returnLeaf(leafI); + + if( + !octree_.hasContainedTriangles(leafI) && + !octree_.hasContainedEdges(leafI) && + (leaf.cubeType() & meshOctreeCubeBasic::INSIDE) + ) + boxType[leafI] |= MESHCELL; + } + + if( meshDict_.found("nonManifoldMeshing") ) + { + const bool nonManifoldMesh + ( + readBool(meshDict_.lookup("nonManifoldMeshing")) + ); + + if( nonManifoldMesh ) + { + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(boxType, leafI) + { + const meshOctreeCubeBasic& leaf = octree_.returnLeaf(leafI); + if( leaf.cubeType() & meshOctreeCubeBasic::UNKNOWN ) + boxType[leafI] |= MESHCELL; + } + } + } + + if( useDATABoxes_ ) + { + Info << "Using DATA boxes" << endl; + forAll(boxType, leafI) { - if( octree_.hasContainedTriangles(leafI) ) - boxType[leafI] |= MESHCELL; + if( + octree_.hasContainedTriangles(leafI) || + octree_.hasContainedEdges(leafI) + ) + boxType[leafI] |= MESHCELL; } - + //- do not use boxes intersecting given patches if( meshDict_.found("removeCellsIntersectingPatches") ) { - wordHashSet patchesToRemove - ( - meshDict_.lookup("removeCellsIntersectingPatches") - ); - + wordHashSet patchesToRemove; + + if( meshDict_.isDict("removeCellsIntersectingPatches") ) + { + const dictionary& dict = + meshDict_.subDict("removeCellsIntersectingPatches"); + const wordList patchNames = dict.toc(); + forAll(patchNames, patchI) + patchesToRemove.insert(patchNames[patchI]); + } + else + { + wordHashSet patchesToRemoveCopy + ( + meshDict_.lookup("removeCellsIntersectingPatches") + ); + patchesToRemove.transfer(patchesToRemoveCopy); + } + const triSurf& ts = octree_.surface(); boolList removeFacets(ts.size(), false); - + //- remove facets in patches forAll(ts.patches(), patchI) { @@ -318,25 +385,27 @@ void meshOctreeAddressing::findUsedBoxes() const } } } - + //- remove facets in subsets forAllConstIter(HashSet<word>, patchesToRemove, it) { - if( ts.doesFaceSubsetExist(it.key()) ) + const label subsetID = ts.facetSubsetIndex(it.key()); + if( subsetID >= 0 ) { - const labelListPMG& facets = ts.facesInSubset(it.key()); - + labelLongList facets; + ts.facetsInSubset(subsetID, facets); + forAll(facets, i) removeFacets[facets[i]] = true; } } - + //- set BOUNDARY flag to boxes intersected by the given facets DynList<label> containedTriangles; forAll(boxType, leafI) { octree_.containedTriangles(leafI, containedTriangles); - + forAll(containedTriangles, i) { if( removeFacets[containedTriangles[i]] ) @@ -346,17 +415,32 @@ void meshOctreeAddressing::findUsedBoxes() const } } } - } - else if( meshDict_.found("keepCellsIntersectingPatches") ) - { - const wordHashSet patchesToKeep - ( - meshDict_.lookup("keepCellsIntersectingPatches") - ); - + } + else if( meshDict_.found("keepCellsIntersectingPatches") ) + { + wordHashSet patchesToKeep; + + if( meshDict_.isDict("keepCellsIntersectingPatches") ) + { + const dictionary& dict = + meshDict_.subDict("keepCellsIntersectingPatches"); + const wordList patchNames = dict.toc(); + + forAll(patchNames, patchI) + patchesToKeep.insert(patchNames[patchI]); + } + else + { + wordHashSet patchesToKeepCopy + ( + meshDict_.lookup("keepCellsIntersectingPatches") + ); + patchesToKeep.transfer(patchesToKeepCopy); + } + const triSurf& ts = octree_.surface(); boolList keepFacets(ts.size(), false); - + //- remove facets in patches forAll(ts.patches(), patchI) { @@ -369,25 +453,28 @@ void meshOctreeAddressing::findUsedBoxes() const } } } - + //- remove facets in subsets forAllConstIter(wordHashSet, patchesToKeep, it) { - if( ts.doesFaceSubsetExist(it.key()) ) + const label subsetID = ts.facetSubsetIndex(it.key()); + + if( subsetID >= 0 ) { - const labelListPMG& facets = ts.facesInSubset(it.key()); - + labelLongList facets; + ts.facetsInSubset(subsetID, facets); + forAll(facets, i) keepFacets[facets[i]] = true; } } - + //- set MESHCELL flag to boxes intersected by the given facets DynList<label> containedTriangles; forAll(boxType, leafI) { octree_.containedTriangles(leafI, containedTriangles); - + forAll(containedTriangles, i) { if( keepFacets[containedTriangles[i]] ) @@ -396,88 +483,78 @@ void meshOctreeAddressing::findUsedBoxes() const } } } - } - -/* if( Pstream::parRun() ) - { - //- set BOUNDARY flag to boxes which do not belong to this processor - forAll(boxType, leafI) - { - const meshOctreeCubeBasic& leaf = octree_.returnLeaf(leafI); - - if( leaf.procNo() != Pstream::myProcNo() ) - boxType[leafI] = NONE; - } } - */ - //- set BOUNDARY flag to boxes which do not have a MESHCELL flag - DynList<label> neighs; - # pragma omp parallel for if( boxType.size() > 1000 ) \ + + //- set BOUNDARY flag to boxes which do not have a MESHCELL flag + DynList<label> neighs; + # ifdef USE_OMP + # pragma omp parallel for if( boxType.size() > 1000 ) \ private(neighs) schedule(dynamic, 20) - forAll(boxType, leafI) - { - if( boxType[leafI] & MESHCELL ) - { - for(label i=0;i<6;++i) - { - neighs.clear(); - octree_.findNeighboursInDirection(leafI, i, neighs); - - forAll(neighs, neiI) - { - const label neiLabel = neighs[neiI]; - + # endif + forAll(boxType, leafI) + { + if( boxType[leafI] & MESHCELL ) + { + for(label i=0;i<6;++i) + { + neighs.clear(); + octree_.findNeighboursInDirection(leafI, i, neighs); + + forAll(neighs, neiI) + { + const label neiLabel = neighs[neiI]; + if( neiLabel < 0 ) continue; - if( !(boxType[neiLabel] & MESHCELL) ) - boxType[neiLabel] = BOUNDARY; - } - } - } - } - + if( !(boxType[neiLabel] & MESHCELL) ) + boxType[neiLabel] = BOUNDARY; + } + } + } + } + if( Pstream::parRun() ) { //- make sure that all processors have the same information //- about BOUNDARY boxes - const labelListPMG& globalLeafLabel = this->globalLeafLabel(); + const labelLongList& globalLeafLabel = this->globalLeafLabel(); const VRWGraph& leafAtProcs = this->leafAtProcs(); const Map<label>& globalLeafToLocal = this->globalToLocalLeafAddressing(); - - std::map<label, labelListPMG> exchangeData; + + std::map<label, labelLongList> exchangeData; forAll(octree_.neiProcs(), procI) exchangeData.insert ( std::make_pair ( octree_.neiProcs()[procI], - labelListPMG() + labelLongList() ) ); - + forAllConstIter(Map<label>, globalLeafToLocal, iter) { const label leafI = iter(); - + if( boxType[leafI] & BOUNDARY ) { forAllRow(leafAtProcs, leafI, procI) { const label neiProc = leafAtProcs(leafI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append(globalLeafLabel[leafI]); } } } - - labelListPMG receivedData; + + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); - + forAll(receivedData, i) boxType[globalLeafToLocal[receivedData[i]]] = BOUNDARY; } @@ -485,298 +562,325 @@ void meshOctreeAddressing::findUsedBoxes() const void meshOctreeAddressing::calculateNodeType() const { - const FRWGraph<label, 8>& nodeLeaves = this->nodeLeaves(); - - nodeTypePtr_ = new List<direction>(nNodes_, NONE); - List<direction>& nodeType = *nodeTypePtr_; - - # pragma omp parallel for schedule(static, 1) - forAll(nodeLeaves, nodeI) - { - forAllRow(nodeLeaves, nodeI, nlI) - { - const label leafI = nodeLeaves(nodeI, nlI); - - if( leafI == -1 ) - continue; - - const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); - - if( + const FRWGraph<label, 8>& nodeLeaves = this->nodeLeaves(); + + nodeTypePtr_ = new List<direction>(nNodes_, NONE); + List<direction>& nodeType = *nodeTypePtr_; + + # ifdef USE_OMP + # pragma omp parallel for schedule(static, 1) + # endif + forAll(nodeLeaves, nodeI) + { + forAllRow(nodeLeaves, nodeI, nlI) + { + const label leafI = nodeLeaves(nodeI, nlI); + + if( leafI == -1 ) + continue; + + const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); + + if( (oc.cubeType() & meshOctreeCubeBasic::OUTSIDE) || (oc.cubeType() & meshOctreeCubeBasic::UNKNOWN) ) - { - nodeType[nodeI] |= OUTERNODE; - break; - } - else if( - !octree_.hasContainedTriangles(leafI) && - (oc.cubeType() & meshOctreeCubeBasic::INSIDE) - ) - { - nodeType[nodeI] |= INNERNODE; - break; - } - } - } + { + nodeType[nodeI] |= OUTERNODE; + break; + } + else if( + !octree_.hasContainedTriangles(leafI) && + (oc.cubeType() & meshOctreeCubeBasic::INSIDE) + ) + { + nodeType[nodeI] |= INNERNODE; + break; + } + } + } } void meshOctreeAddressing::createOctreeFaces() const { octreeFacesPtr_ = new VRWGraph(); - octreeFacesOwnersPtr_ = new labelListPMG(); - octreeFacesNeighboursPtr_ = new labelListPMG(); - + octreeFacesOwnersPtr_ = new labelLongList(); + octreeFacesNeighboursPtr_ = new labelLongList(); + const VRWGraph& nodeLabels = this->nodeLabels(); const List<direction>& boxType = this->boxType(); - this->nodeLeaves(); - - label nFaces(0); - labelList rowSizes, chunkSizes; - - # pragma omp parallel - { - //- faces are created and stored into helper arrays, and each thread - //- allocates its own graph for storing faces. The faces are generated - //- by dividing the octree leaves into chunks, and distributing these - //- chunks over the threads. There are four chunks per each thread to - //- improve load balancing. The number of faces generated in each chunk - //- is stored and later in used to store the faces into the octree faces - //- graph in the correct order - VRWGraph helperFaces; - labelListPMG helperOwner, helperNeighbour; - - const label nChunks = 4 * omp_get_num_threads(); - const label chunkSize = boxType.size() / nChunks + 1; - - # pragma omp master - { - chunkSizes.setSize(nChunks); - chunkSizes = 0; - } - - # pragma omp barrier - - for - ( - label chunkI=omp_get_thread_num(); - chunkI<nChunks; - chunkI+=omp_get_num_threads() - ) - { - const label start = chunkSize * chunkI; - const label end = Foam::min(start+chunkSize, boxType.size()); - - const label nBefore = helperFaces.size(); - - for(label leafI=start;leafI<end;++leafI) - { - const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); - - if( boxType[leafI] & MESHCELL ) - { - FixedList<label, 12> edgeCentreLabel; - for(label i=0;i<12;++i) - edgeCentreLabel[i] = findEdgeCentre(leafI, i); - - for(label fI=0;fI<6;++fI) - { - DynList<label> neighbours; - octree_.findNeighboursInDirection - ( - leafI, - fI, - neighbours - ); - - if( neighbours.size() != 1 ) - continue; - - const label nei = neighbours[0]; - - //- stop if the neighbour is on other processor - if( nei == meshOctreeCubeBasic::OTHERPROC ) - continue; - - //- create face - DynList<label, 8> f; - for(label pI=0;pI<4;++pI) - { - const label nI = - meshOctreeCubeCoordinates::faceNodes_[fI][pI]; - const label feI = - meshOctreeCubeCoordinates::faceEdges_[fI][pI]; - - f.append(nodeLabels(leafI, nI)); - - if( edgeCentreLabel[feI] != -1 ) - f.append(edgeCentreLabel[feI]); - } - - if( nei < 0 ) - { - //- face is at the boundary of the octree - helperFaces.appendList(f); - helperOwner.append(leafI); - helperNeighbour.append(-1); - } - else if( boxType[nei] & MESHCELL ) - { - //- face is an internal face - if( nei > leafI ) - { - helperFaces.appendList(f); - helperOwner.append(leafI); - helperNeighbour.append(nei); - } - else if - ( - octree_.returnLeaf(nei).level() < oc.level() - ) - { - //- append a reversed face - label i(1); - for(label j=f.size()-1;j>i;--j) - { - const label add = f[j]; - f[j] = f[i]; - f[i] = add; - ++i; - } - - helperFaces.appendList(f); - helperOwner.append(nei); - helperNeighbour.append(leafI); - } - } - else if( boxType[nei] & BOUNDARY ) - { - //- face is at the boundary of the mesh cells - helperFaces.appendList(f); - helperOwner.append(leafI); - helperNeighbour.append(nei); - } - } - } - else if( boxType[leafI] & BOUNDARY ) - { - for(label fI=0;fI<6;++fI) - { - DynList<label> neighbours; - octree_.findNeighboursInDirection - ( - leafI, - fI, - neighbours - ); - - if( neighbours.size() != 1 ) - continue; - const label nei = neighbours[0]; - if( nei < 0 ) - continue; - if( - (boxType[nei] & MESHCELL) && - (octree_.returnLeaf(nei).level() < oc.level()) - ) - { - //- add a boundary face - const label* fNodes = - meshOctreeCubeCoordinates::faceNodes_[fI]; - face cf(4); - for(label i=0;i<4;++i) - { - cf[i] = nodeLabels(leafI, fNodes[i]); - } - - helperFaces.appendList(cf.reverseFace()); - helperOwner.append(nei); - helperNeighbour.append(leafI); - } - } - } - } - - //- store the size of this chunk - chunkSizes[chunkI] = helperFaces.size() - nBefore; - } - - //- set the sizes of faces graph - # pragma omp critical - nFaces += helperFaces.size(); - - # pragma omp barrier - - # pragma omp master - { - rowSizes.setSize(nFaces); - octreeFacesPtr_->setSize(nFaces); - octreeFacesOwnersPtr_->setSize(nFaces); - octreeFacesNeighboursPtr_->setSize(nFaces); - } - - # pragma omp barrier - - //- set the size of face graph rows and copy owners and neighbours - for - ( - label chunkI=omp_get_thread_num(); - chunkI<nChunks; - chunkI+=omp_get_num_threads() - ) - { - label start(0), localStart(0); - for(label i=0;i<chunkI;++i) - start += chunkSizes[i]; - for(label i=omp_get_thread_num();i<chunkI;i+=omp_get_num_threads()) - localStart += chunkSizes[i]; - - for(label faceI=0;faceI<chunkSizes[chunkI];++faceI) - { - octreeFacesOwnersPtr_->operator[](start) = - helperOwner[localStart]; - octreeFacesNeighboursPtr_->operator[](start) = - helperNeighbour[localStart]; - rowSizes[start++] = helperFaces.sizeOfRow(localStart++); - } - } - - # pragma omp barrier - - //- set the size of octree faces - # pragma omp master - VRWGraphSMPModifier(*octreeFacesPtr_).setSizeAndRowSize(rowSizes); - - # pragma omp barrier - - //- copy the data into octree faces - for - ( - label chunkI=omp_get_thread_num(); - chunkI<nChunks; - chunkI+=omp_get_num_threads() - ) - { - label start(0), localStart(0); - - for(label i=0;i<chunkI;++i) - start += chunkSizes[i]; - for(label i=omp_get_thread_num();i<chunkI;i+=omp_get_num_threads()) - localStart += chunkSizes[i]; - - for(label faceI=0;faceI<chunkSizes[chunkI];++faceI) - { - for(label i=0;i<helperFaces.sizeOfRow(localStart);++i) - octreeFacesPtr_->operator()(start, i) = - helperFaces(localStart, i); - - ++start; - ++localStart; - } - } - } - + this->nodeLeaves(); + + label nFaces(0); + labelList rowSizes, chunkSizes; + + # ifdef USE_OMP + # pragma omp parallel + # endif + { + //- faces are created and stored into helper arrays, and each thread + //- allocates its own graph for storing faces. The faces are generated + //- by dividing the octree leaves into chunks, and distributing these + //- chunks over the threads. There are four chunks per each thread to + //- improve load balancing. The number of faces generated in each chunk + //- is stored and later in used to store the faces into the octree faces + //- graph in the correct order + VRWGraph helperFaces; + labelLongList helperOwner, helperNeighbour; + + # ifdef USE_OMP + const label nThreads = omp_get_num_threads(); + const label threadI = omp_get_thread_num(); + const label nChunks = 4 * omp_get_num_threads(); + const label chunkSize = boxType.size() / nChunks + 1; + # else + const label nThreads(1); + const label threadI(0); + const label nChunks(1); + const label chunkSize = boxType.size(); + # endif + + # ifdef USE_OMP + # pragma omp master + # endif + { + chunkSizes.setSize(nChunks); + chunkSizes = 0; + } + + # ifdef USE_OMP + # pragma omp barrier + # endif + + for + ( + label chunkI=threadI; + chunkI<nChunks; + chunkI+=nThreads + ) + { + const label start = chunkSize * chunkI; + const label end = Foam::min(start+chunkSize, boxType.size()); + + const label nBefore = helperFaces.size(); + + for(label leafI=start;leafI<end;++leafI) + { + const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); + + if( boxType[leafI] & MESHCELL ) + { + FixedList<label, 12> edgeCentreLabel(-1); + for(label i=0;i<12;++i) + edgeCentreLabel[i] = findEdgeCentre(leafI, i); + + for(label fI=0;fI<6;++fI) + { + DynList<label> neighbours; + octree_.findNeighboursInDirection + ( + leafI, + fI, + neighbours + ); + + if( neighbours.size() != 1 ) + continue; + + const label nei = neighbours[0]; + + //- stop if the neighbour is on other processor + if( nei == meshOctreeCubeBasic::OTHERPROC ) + continue; + + //- create face + DynList<label, 8> f; + for(label pI=0;pI<4;++pI) + { + const label nI = + meshOctreeCubeCoordinates::faceNodes_[fI][pI]; + const label feI = + meshOctreeCubeCoordinates::faceEdges_[fI][pI]; + + f.append(nodeLabels(leafI, nI)); + + if( edgeCentreLabel[feI] != -1 ) + f.append(edgeCentreLabel[feI]); + } + + if( nei < 0 ) + { + //- face is at the boundary of the octree + helperFaces.appendList(f); + helperOwner.append(leafI); + helperNeighbour.append(-1); + } + else if( boxType[nei] & MESHCELL ) + { + //- face is an internal face + if( nei > leafI ) + { + helperFaces.appendList(f); + helperOwner.append(leafI); + helperNeighbour.append(nei); + } + else if + ( + octree_.returnLeaf(nei).level() < oc.level() + ) + { + //- append a reversed face + label i(1); + for(label j=f.size()-1;j>i;--j) + { + const label add = f[j]; + f[j] = f[i]; + f[i] = add; + ++i; + } + + helperFaces.appendList(f); + helperOwner.append(nei); + helperNeighbour.append(leafI); + } + } + else if( boxType[nei] & BOUNDARY ) + { + //- face is at the boundary of the mesh cells + helperFaces.appendList(f); + helperOwner.append(leafI); + helperNeighbour.append(nei); + } + } + } + else if( boxType[leafI] & BOUNDARY ) + { + for(label fI=0;fI<6;++fI) + { + DynList<label> neighbours; + octree_.findNeighboursInDirection + ( + leafI, + fI, + neighbours + ); + + if( neighbours.size() != 1 ) + continue; + const label nei = neighbours[0]; + if( nei < 0 ) + continue; + if( + (boxType[nei] & MESHCELL) && + (octree_.returnLeaf(nei).level() < oc.level()) + ) + { + //- add a boundary face + const label* fNodes = + meshOctreeCubeCoordinates::faceNodes_[fI]; + face cf(4); + for(label i=0;i<4;++i) + { + cf[i] = nodeLabels(leafI, fNodes[i]); + } + + helperFaces.appendList(cf.reverseFace()); + helperOwner.append(nei); + helperNeighbour.append(leafI); + } + } + } + } + + //- store the size of this chunk + chunkSizes[chunkI] = helperFaces.size() - nBefore; + } + + //- set the sizes of faces graph + # ifdef USE_OMP + # pragma omp critical + # endif + nFaces += helperFaces.size(); + + # ifdef USE_OMP + # pragma omp barrier + + # pragma omp master + # endif + { + rowSizes.setSize(nFaces); + octreeFacesPtr_->setSize(nFaces); + octreeFacesOwnersPtr_->setSize(nFaces); + octreeFacesNeighboursPtr_->setSize(nFaces); + } + + # ifdef USE_OMP + # pragma omp barrier + # endif + + //- set the size of face graph rows and copy owners and neighbours + for + ( + label chunkI=threadI; + chunkI<nChunks; + chunkI+=nThreads + ) + { + label start(0), localStart(0); + for(label i=0;i<chunkI;++i) + start += chunkSizes[i]; + for(label i=threadI;i<chunkI;i+=nThreads) + localStart += chunkSizes[i]; + + for(label faceI=0;faceI<chunkSizes[chunkI];++faceI) + { + octreeFacesOwnersPtr_->operator[](start) = + helperOwner[localStart]; + octreeFacesNeighboursPtr_->operator[](start) = + helperNeighbour[localStart]; + rowSizes[start++] = helperFaces.sizeOfRow(localStart++); + } + } + + # ifdef USE_OMP + # pragma omp barrier + + //- set the size of octree faces + # pragma omp master + # endif + VRWGraphSMPModifier(*octreeFacesPtr_).setSizeAndRowSize(rowSizes); + + # ifdef USE_OMP + # pragma omp barrier + # endif + + //- copy the data into octree faces + for + ( + label chunkI=threadI; + chunkI<nChunks; + chunkI+=nThreads + ) + { + label start(0), localStart(0); + + for(label i=0;i<chunkI;++i) + start += chunkSizes[i]; + for(label i=threadI;i<chunkI;i+=nThreads) + localStart += chunkSizes[i]; + + for(label faceI=0;faceI<chunkSizes[chunkI];++faceI) + { + for(label i=0;i<helperFaces.sizeOfRow(localStart);++i) + octreeFacesPtr_->operator()(start, i) = + helperFaces(localStart, i); + + ++start; + ++localStart; + } + } + } + # ifdef DEBUGVrt List<vector> sum(octree_.numberOfLeaves(), vector::zero); for(label faceI=0;faceI<octreeFacesPtr_->size();++faceI) @@ -788,12 +892,12 @@ void meshOctreeAddressing::createOctreeFaces() const sum[(*octreeFacesOwnersPtr_)[faceI]] += n; const label nei = (*octreeFacesNeighboursPtr_)[faceI]; - + if( nei < 0 ) continue; sum[nei] -= n; } - + forAll(sum, lfI) { if( Pstream::parRun() && octree_.returnLeaf(lfI).procNo() != Pstream::myProcNo() ) @@ -806,12 +910,12 @@ void meshOctreeAddressing::createOctreeFaces() const void meshOctreeAddressing::calculateLeafFaces() const { - const labelListPMG& owner = octreeFaceOwner(); - const labelListPMG& neighbour = octreeFaceNeighbour(); - + const labelLongList& owner = octreeFaceOwner(); + const labelLongList& neighbour = octreeFaceNeighbour(); + leafFacesPtr_ = new VRWGraph(octree_.numberOfLeaves()); VRWGraph& leafFaces = *leafFacesPtr_; - + labelList nlf(leafFaces.size(), 0); forAll(owner, fI) { @@ -820,11 +924,11 @@ void meshOctreeAddressing::calculateLeafFaces() const continue; ++nlf[neighbour[fI]]; } - + forAll(nlf, leafI) leafFaces.setRowSize(leafI, nlf[leafI]); nlf = 0; - + forAll(owner, fI) { leafFaces(owner[fI], nlf[owner[fI]]++) = fI; @@ -839,19 +943,19 @@ void meshOctreeAddressing::calculateNodeFaces() const const VRWGraph& octreeFaces = this->octreeFaces(); nodeFacesPtr_ = new VRWGraph(numberOfNodes()); VRWGraph& nodeFaces = *nodeFacesPtr_; - + VRWGraphSMPModifier(nodeFaces).reverseAddressing(octreeFaces); nodeFaces.setSize(numberOfNodes()); } void meshOctreeAddressing::calculateLeafLeaves() const { - const labelListPMG& owner = octreeFaceOwner(); - const labelListPMG& neighbour = octreeFaceNeighbour(); - + const labelLongList& owner = octreeFaceOwner(); + const labelLongList& neighbour = octreeFaceNeighbour(); + leafLeavesPtr_ = new VRWGraph(octree_.numberOfLeaves()); VRWGraph& leafLeaves = *leafLeavesPtr_; - + labelList nNei(leafLeaves.size(), 0); forAll(owner, faceI) { @@ -859,23 +963,23 @@ void meshOctreeAddressing::calculateLeafLeaves() const continue; if( neighbour[faceI] < 0 ) continue; - + ++nNei[owner[faceI]]; ++nNei[neighbour[faceI]]; } - + forAll(nNei, leafI) leafLeaves.setRowSize(leafI, nNei[leafI]); - + nNei = 0; - + forAll(owner, faceI) { if( owner[faceI] < 0 ) continue; if( neighbour[faceI] < 0 ) continue; - + leafLeaves(owner[faceI], nNei[owner[faceI]]++) = neighbour[faceI]; leafLeaves(neighbour[faceI], nNei[neighbour[faceI]]++) = owner[faceI]; } @@ -884,7 +988,7 @@ void meshOctreeAddressing::calculateLeafLeaves() const void meshOctreeAddressing::createOctreeEdges() const { const VRWGraph& faces = this->octreeFaces(); - + //- allocate memory for edges, face-edges addressing //- and node-edges addressing octreeEdgesPtr_ = new LongList<edge>(); @@ -894,18 +998,18 @@ void meshOctreeAddressing::createOctreeEdges() const nodeEdgesPtr_ = new VRWGraph(); VRWGraph& nodeEdges = *nodeEdgesPtr_; nodeEdges.setSizeAndColumnWidth(nNodes_, 6); - + forAll(faces, faceI) { faceEdges.setRowSize(faceI, faces[faceI].size()); forAllRow(faceEdges, faceI, feI) faceEdges(faceI, feI) = -1; } - + forAll(faces, faceI) { const label nEdges = faces.sizeOfRow(faceI); - + for(label eI=0;eI<nEdges;++eI) { const edge e @@ -913,7 +1017,7 @@ void meshOctreeAddressing::createOctreeEdges() const faces(faceI, eI), faces(faceI, (eI+1)%nEdges) ); - + label eLabel(-1); forAllRow(nodeEdges, e.start(), neI) { @@ -923,14 +1027,14 @@ void meshOctreeAddressing::createOctreeEdges() const break; } } - + if( eLabel < 0 ) { //- append new edge faceEdges(faceI, eI) = edges.size(); nodeEdges.append(e.start(), edges.size()); nodeEdges.append(e.end(), edges.size()); - + edges.append(e); } else @@ -944,10 +1048,10 @@ void meshOctreeAddressing::createOctreeEdges() const void meshOctreeAddressing::calculateLeafEdges() const { const VRWGraph& edgeLeaves = this->edgeLeaves(); - + leafEdgesPtr_ = new VRWGraph(); VRWGraph& leafEdges = *leafEdgesPtr_; - + VRWGraphSMPModifier(leafEdges).reverseAddressing(edgeLeaves); leafEdges.setSize(octree_.numberOfLeaves()); } @@ -955,13 +1059,13 @@ void meshOctreeAddressing::calculateLeafEdges() const void meshOctreeAddressing::calculateEdgeLeaves() const { const VRWGraph& edgeFaces = this->edgeFaces(); - const labelListPMG& owner = this->octreeFaceOwner(); - const labelListPMG& neighbour = this->octreeFaceNeighbour(); - + const labelLongList& owner = this->octreeFaceOwner(); + const labelLongList& neighbour = this->octreeFaceNeighbour(); + edgeLeavesPtr_ = new VRWGraph(); VRWGraph& edgeLeaves = *edgeLeavesPtr_; edgeLeaves.setSizeAndColumnWidth(edgeFaces.size(), 4); - + forAll(edgeFaces, edgeI) { forAllRow(edgeFaces, edgeI, efI) @@ -969,9 +1073,9 @@ void meshOctreeAddressing::calculateEdgeLeaves() const const label fI = edgeFaces(edgeI, efI); const label own = owner[fI]; const label nei = neighbour[fI]; - + edgeLeaves.appendIfNotIn(edgeI, own); - + if( nei < 0 ) continue; edgeLeaves.appendIfNotIn(edgeI, nei); @@ -984,7 +1088,7 @@ void meshOctreeAddressing::calculateEdgeFaces() const const VRWGraph& faceEdges = this->faceEdges(); edgeFacesPtr_ = new VRWGraph(octreeEdges().size()); VRWGraph& edgeFaces = *edgeFacesPtr_; - + VRWGraphSMPModifier(edgeFaces).reverseAddressing(faceEdges); edgeFaces.setSize(octreeEdges().size()); } diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingGluedMesh.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingGluedMesh.C index ac62e38ea996186f2d013b1c43257a3e09577eed..f4758e35f30e6ef400e80fb7b1f418d2908157da 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingGluedMesh.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingGluedMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,97 +41,97 @@ namespace Foam void meshOctreeAddressing::checkGluedRegions() { - if( !useDATABoxes_ ) - return; - - if( meshDict_.found("checkForGluedMesh") ) - { - if( !readBool(meshDict_.lookup("checkForGluedMesh")) ) - return; - } - else - { - return; - } - - Info << "Removing glued regions" << endl; - const List<direction>& boxType = this->boxType(); - const VRWGraph& nodeLabels = this->nodeLabels(); - const List<direction>& nodeType = this->nodeType(); - + if( !useDATABoxes_ ) + return; + + if( meshDict_.found("checkForGluedMesh") ) + { + if( !readBool(meshDict_.lookup("checkForGluedMesh")) ) + return; + } + else + { + return; + } + + Info << "Removing glued regions" << endl; + const List<direction>& boxType = this->boxType(); + const VRWGraph& nodeLabels = this->nodeLabels(); + const List<direction>& nodeType = this->nodeType(); + const VRWGraph& edgeLeaves = this->edgeLeaves(); const VRWGraph& leafEdges = this->leafEdges(); const FRWGraph<label, 8>& nodeLeaves = this->nodeLeaves(); const LongList<edge>& edges = this->octreeEdges(); - - DynList<label> neighbours(4); - labelListPMG removeBox; - forAll(boxType, leafI) + + DynList<label> neighbours; + labelLongList removeBox; + forAll(boxType, leafI) { - if( - octree_.hasContainedTriangles(leafI) && - (boxType[leafI] & MESHCELL) - ) - { - //- mark the initial INNERNODE + if( + octree_.hasContainedTriangles(leafI) && + (boxType[leafI] & MESHCELL) + ) + { + //- mark the initial INNERNODE labelHashSet innerNodes; - forAllRow(nodeLabels, leafI, nodeI) - if( nodeType[nodeLabels(leafI, nodeI)] & INNERNODE ) - { - innerNodes.insert(nodeLabels(leafI, nodeI)); - break; - } - - //- mark all INNERNODEs for which it is possible to walk along - //- cubes edges without crossing any boundary - bool finished; - do - { - finished = true; - - forAllRow(leafEdges, leafI, leI) - { + forAllRow(nodeLabels, leafI, nodeI) + if( nodeType[nodeLabels(leafI, nodeI)] & INNERNODE ) + { + innerNodes.insert(nodeLabels(leafI, nodeI)); + break; + } + + //- mark all INNERNODEs for which it is possible to walk along + //- cubes edges without crossing any boundary + bool finished; + do + { + finished = true; + + forAllRow(leafEdges, leafI, leI) + { const label edgeI = leafEdges(leafI, leI); const edge& edg = edges[edgeI]; - const label s = edg[0]; - const label e = edg[1]; - - if( - (nodeType[s] & INNERNODE) && (nodeType[e] & INNERNODE) - && (innerNodes.found(s) ^ innerNodes.found(e)) - ) - { - bool foundInside(false); - forAllRow(edgeLeaves, edgeI, elI) - { + const label s = edg[0]; + const label e = edg[1]; + + if( + (nodeType[s] & INNERNODE) && (nodeType[e] & INNERNODE) + && (innerNodes.found(s) ^ innerNodes.found(e)) + ) + { + bool foundInside(false); + forAllRow(edgeLeaves, edgeI, elI) + { const label ecLabel = edgeLeaves(edgeI, elI); - if( ecLabel < 0 ) - continue; - if( octree_.hasContainedTriangles(ecLabel) ) - continue; - if( - !( - octree_.returnLeaf(ecLabel).cubeType() & - meshOctreeCubeBasic::INSIDE - ) - ) - continue; - - foundInside = true; - break; - } - - if( foundInside ) - { - innerNodes.insert(s); - innerNodes.insert(e); - finished = false; - } - } - } - - } while( !finished ); - + if( ecLabel < 0 ) + continue; + if( octree_.hasContainedTriangles(ecLabel) ) + continue; + if( + !( + octree_.returnLeaf(ecLabel).cubeType() & + meshOctreeCubeBasic::INSIDE + ) + ) + continue; + + foundInside = true; + break; + } + + if( foundInside ) + { + innerNodes.insert(s); + innerNodes.insert(e); + finished = false; + } + } + } + + } while( !finished ); + labelHashSet permissibleNeighbours; forAllConstIter(labelHashSet, innerNodes, it) { @@ -140,14 +139,14 @@ void meshOctreeAddressing::checkGluedRegions() forAllRow(nodeLeaves, nodeI, nlI) permissibleNeighbours.insert(nodeLeaves(nodeI, nlI)); } - + if( permissibleNeighbours.size() ) { for(label i=0;i<6;++i) { neighbours.clear(); octree_.findNeighboursInDirection(leafI, i, neighbours); - + forAll(neighbours, neiI) { const label nei = neighbours[neiI]; @@ -167,12 +166,12 @@ void meshOctreeAddressing::checkGluedRegions() { removeBox.append(leafI); } - } + } } - + forAll(removeBox, i) (*boxTypePtr_)[removeBox[i]] = BOUNDARY; - + if( Pstream::parRun() ) { LongList<meshOctreeCubeCoordinates> checkBoundary; @@ -181,14 +180,14 @@ void meshOctreeAddressing::checkGluedRegions() const meshOctreeCubeBasic& oc = octree_.returnLeaf(removeBox[i]); checkBoundary.append(oc.coordinates()); } - + LongList<meshOctreeCubeCoordinates> receivedBoundary; octree_.exchangeRequestsWithNeighbourProcessors ( checkBoundary, receivedBoundary ); - + forAll(receivedBoundary, i) { const label cLabel = @@ -199,7 +198,7 @@ void meshOctreeAddressing::checkGluedRegions() } } - Info << "Finished removing glued regions" << endl; + Info << "Finished removing glued regions" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingI.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingI.H index 5f22cb961cb9eff139e3665d296632c075dda93d..00d580e000bd5bdc09256fa8bead91f477b710f9 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingI.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,7 +38,7 @@ inline label meshOctreeAddressing::numberOfNodes() const if( !nodeLabelsPtr_ ) createNodeLabels(); - return nNodes_; + return nNodes_; } inline const pointField& meshOctreeAddressing::octreePoints() const @@ -49,55 +48,55 @@ inline const pointField& meshOctreeAddressing::octreePoints() const return *octreePointsPtr_; } - + inline const VRWGraph& meshOctreeAddressing::nodeLabels() const { - if( !nodeLabelsPtr_ ) - createNodeLabels(); - - return *nodeLabelsPtr_; + if( !nodeLabelsPtr_ ) + createNodeLabels(); + + return *nodeLabelsPtr_; } inline const FRWGraph<label, 8>& meshOctreeAddressing::nodeLeaves() const { - if( !nodeLeavesPtr_ ) - createNodeLeaves(); - - return *nodeLeavesPtr_; + if( !nodeLeavesPtr_ ) + createNodeLeaves(); + + return *nodeLeavesPtr_; } - + inline const List<direction>& meshOctreeAddressing::boxType() const { - if( !boxTypePtr_ ) - findUsedBoxes(); - - return *boxTypePtr_; + if( !boxTypePtr_ ) + findUsedBoxes(); + + return *boxTypePtr_; } inline void meshOctreeAddressing::setBoxType ( - const label boxI, - const direction type + const label boxI, + const direction type ) { - if( boxTypePtr_ ) - { - List<direction>& boxType = *boxTypePtr_; - boxType[boxI] |= type; - } + if( boxTypePtr_ ) + { + List<direction>& boxType = *boxTypePtr_; + boxType[boxI] |= type; + } } inline const meshOctree& meshOctreeAddressing::octree() const { - return octree_; + return octree_; } inline const List<direction>& meshOctreeAddressing::nodeType() const { - if( !nodeTypePtr_ ) - calculateNodeType(); - - return *nodeTypePtr_; + if( !nodeTypePtr_ ) + calculateNodeType(); + + return *nodeTypePtr_; } inline const VRWGraph& meshOctreeAddressing::octreeFaces() const @@ -108,7 +107,7 @@ inline const VRWGraph& meshOctreeAddressing::octreeFaces() const return *octreeFacesPtr_; } -inline const labelListPMG& meshOctreeAddressing::octreeFaceOwner() const +inline const labelLongList& meshOctreeAddressing::octreeFaceOwner() const { if( !octreeFacesOwnersPtr_ ) createOctreeFaces(); @@ -116,7 +115,7 @@ inline const labelListPMG& meshOctreeAddressing::octreeFaceOwner() const return *octreeFacesOwnersPtr_; } -inline const labelListPMG& meshOctreeAddressing::octreeFaceNeighbour() const +inline const labelLongList& meshOctreeAddressing::octreeFaceNeighbour() const { if( !octreeFacesNeighboursPtr_ ) createOctreeFaces(); @@ -196,7 +195,7 @@ inline const VRWGraph& meshOctreeAddressing::edgeFaces() const return *edgeFacesPtr_; } -inline const labelListPMG& meshOctreeAddressing::globalPointLabel() const +inline const labelLongList& meshOctreeAddressing::globalPointLabel() const { if( !globalPointLabelPtr_ ) calcGlobalPointLabels(); @@ -221,7 +220,7 @@ inline const VRWGraph& meshOctreeAddressing::pointAtProcs() const return *pointProcsPtr_; } -inline const labelListPMG& meshOctreeAddressing::globalFaceLabel() const +inline const labelLongList& meshOctreeAddressing::globalFaceLabel() const { if( !globalFaceLabelPtr_ ) calcGlobalFaceLabels(); @@ -246,7 +245,7 @@ inline const VRWGraph& meshOctreeAddressing::faceAtProcs() const return *faceProcsPtr_; } -inline const labelListPMG& meshOctreeAddressing::globalLeafLabel() const +inline const labelLongList& meshOctreeAddressing::globalLeafLabel() const { if( !globalLeafLabelPtr_ ) calcGlobalLeafLabels(); diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingIrregularConnections.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingIrregularConnections.C index 10c972074a0b1b37136851a2d8673eafdc7acec8..346b6b00086b69c86fc0900aff50a99a29ca8f56 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingIrregularConnections.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingIrregularConnections.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -45,42 +44,42 @@ namespace Foam void meshOctreeAddressing::checkAndFixIrregularConnections() { Info << "Checking the surface of the selected boxes" << endl; - - const labelListPMG& owner = this->octreeFaceOwner(); - const labelListPMG& neighbour = this->octreeFaceNeighbour(); + + const labelLongList& owner = this->octreeFaceOwner(); + const labelLongList& neighbour = this->octreeFaceNeighbour(); const VRWGraph& faceEdges = this->faceEdges(); const VRWGraph& edgeFaces = this->edgeFaces(); const VRWGraph& edgeLeaves = this->edgeLeaves(); const VRWGraph& pointFaces = this->nodeFaces(); - + List<direction>& boxType = *boxTypePtr_; - + boolList boundaryFace(owner.size()); - + label nIrregular; - DynList<label> front(10); - + DynList<label> front; + do { nIrregular = 0; - + labelHashSet changedBoxType(100); - + //- find boundary faces boundaryFace = false; - + forAll(owner, faceI) { const label own = owner[faceI]; const label nei = neighbour[faceI]; - + if( nei < 0 ) { continue; } else { - + if( ((boxType[nei] & BOUNDARY) && (boxType[own] & MESHCELL)) || ((boxType[own] & BOUNDARY) && (boxType[nei] & MESHCELL)) @@ -88,7 +87,7 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() boundaryFace[faceI] = true; } } - + //- remove irregular connections over edges forAll(edgeFaces, edgeI) { @@ -96,11 +95,11 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() forAllRow(edgeFaces, edgeI, efI) { const label faceI = edgeFaces(edgeI, efI); - + if( boundaryFace[faceI] ) ++nBoundaryFaces; } - + if( nBoundaryFaces > 2 ) { ++nIrregular; @@ -112,7 +111,7 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() } } } - + //- check if there exist two or more boundary face groups //- connected to a vertex forAll(pointFaces, pI) @@ -125,7 +124,7 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() if( boundaryFace[faceI] ) bndFacesAtNode.insert(faceI); } - + //- find the number of face groups at a given vertex label nGroups(0); bool watertightSurface(true); @@ -134,20 +133,20 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() front.clear(); front.append(bndFacesAtNode.begin().key()); bndFacesAtNode.erase(front[0]); - + while( front.size() != 0 ) { const label fLabel = front.removeLastElement(); - + forAllRow(faceEdges, fLabel, feI) { const label eI = faceEdges(fLabel, feI); - + bool found(false); forAllRow(edgeFaces, eI, efI) { const label fJ = edgeFaces(eI, efI); - + if( bndFacesAtNode.found(fJ) ) { found = true; @@ -155,7 +154,7 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() bndFacesAtNode.erase(fJ); } } - + if( !found ) { watertightSurface = false; @@ -163,14 +162,14 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() } } } - + ++nGroups; } - + if( watertightSurface && (nGroups > 1) ) { ++nIrregular; - + //- this vertex has two groups of faces connected to it forAllRow(pointFaces, pI, pfI) { @@ -183,10 +182,10 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() changedBoxType.insert(owner[faceI]); boxType[owner[faceI]] = BOUNDARY; } - + if( neighbour[faceI] == -1 ) continue; - + if( boxType[neighbour[faceI]] & MESHCELL ) { changedBoxType.insert(neighbour[faceI]); @@ -196,41 +195,41 @@ void meshOctreeAddressing::checkAndFixIrregularConnections() } } } - + reduce(nIrregular, sumOp<label>()); Info << nIrregular << " surface connections found!" << endl; - + if( Pstream::parRun() && (nIrregular != 0) ) { LongList<meshOctreeCubeCoordinates> exchangeData; forAllConstIter(labelHashSet, changedBoxType, it) exchangeData.append(octree_.returnLeaf(it.key()).coordinates()); - + LongList<meshOctreeCubeCoordinates> receivedData; octree_.exchangeRequestsWithNeighbourProcessors ( exchangeData, receivedData ); - + forAll(receivedData, i) { const label leafI = octree_.findLeafLabelForPosition(receivedData[i]); if( leafI < 0 ) continue; - + boxType[leafI] = BOUNDARY; } } - + } while( nIrregular != 0 ); - + clearNodeAddressing(); clearOctreeFaces(); clearAddressing(); - - Info << "Finished checking the surface of the selected boxes" << endl; + + Info << "Finished checking the surface of the selected boxes" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingParallelAddressing.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingParallelAddressing.C index 18a88ffc2b043fe4c8e05013a4ff907d49078be7..854fd1758fafb2eeedaa9afecc20ad75fb34358c 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingParallelAddressing.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAddressing/meshOctreeAddressingParallelAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -32,7 +31,10 @@ Description #include "helperFunctions.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGAddressing @@ -48,41 +50,41 @@ void meshOctreeAddressing::calcGlobalPointLabels() const if( !Pstream::parRun() ) FatalErrorIn("void meshOctreeAddressing::calcGlobalPointLabels() const") << "Cannot calculate global labels! Exitting" << exit(FatalError); - + const VRWGraph& nodeLabels = this->nodeLabels(); const FRWGraph<label, 8>& nodeLeaves = this->nodeLeaves(); - + //- allocate containers - globalPointLabelPtr_ = new labelListPMG(nodeLeaves.size(), -1); - labelListPMG& globalPointLabel = *globalPointLabelPtr_; - + globalPointLabelPtr_ = new labelLongList(nodeLeaves.size(), -1); + labelLongList& globalPointLabel = *globalPointLabelPtr_; + globalPointToLocalPtr_ = new Map<label>(); Map<label>& globalToLocal = *globalPointToLocalPtr_; - + pointProcsPtr_ = new VRWGraph(nodeLeaves.size()); VRWGraph& pointProcs = *pointProcsPtr_; - + //- find the number of points local to each processor //- The point is taken to be local if it belongs to one processor, only, //- or to the leaf with the smallest label labelList nLocalPoints(Pstream::nProcs(), 0); - + forAll(nodeLeaves, pointI) { DynList<label> procs; procs.append(Pstream::myProcNo()); FixedList<bool, 8> validLeaf(true); - + for(label nlI=0;nlI<8;++nlI) { const label leafI = nodeLeaves(pointI, nlI); - + if( leafI < 0 ) { validLeaf[nlI] = false; continue; } - + for(label i=0;i<nlI;++i) if( nodeLeaves(pointI, i) == nodeLeaves(pointI, nlI) ) { @@ -92,61 +94,61 @@ void meshOctreeAddressing::calcGlobalPointLabels() const procs.appendIfNotIn(octree_.returnLeaf(leafI).procNo()); } - + label minLeaf(octree_.numberOfLeaves()); bool found(false); - + for(label nlI=0;nlI<8;++nlI) { if( !validLeaf[nlI] ) continue; - + const label leafI = nodeLeaves(pointI, nlI); - + minLeaf = Foam::min(leafI, minLeaf); found = true; } - + if( found && octree_.returnLeaf(minLeaf).procNo() == Pstream::myProcNo() ) { if( procs.size() > 1 ) pointProcs.setRow(pointI, procs); - + globalPointLabel[pointI] = -2; ++nLocalPoints[Pstream::myProcNo()]; } } - + //- exchange data with other processors Pstream::gatherList(nLocalPoints); Pstream::scatterList(nLocalPoints); - + //- find the starting point label label startPoint(0); for(label procI=0;procI<Pstream::myProcNo();++procI) startPoint += nLocalPoints[procI]; - + //- assign global labels to local points forAll(globalPointLabel, pointI) { if( globalPointLabel[pointI] == -2 ) { globalPointLabel[pointI] = startPoint++; - + if( pointProcs.sizeOfRow(pointI) != 0 ) globalToLocal.insert(globalPointLabel[pointI], pointI); } } - + //- distribute the labels to other processors //- it is done by sending the global leaf label and the node labels //- to processors which contain the leaves as part of buffer layers //- it is performed in reduce-like manner - const labelListPMG& globalLeafLabel = this->globalLeafLabel(); + const labelLongList& globalLeafLabel = this->globalLeafLabel(); const Map<label>& globalToLocalLeaf = this->globalToLocalLeafAddressing(); const VRWGraph& leafAtProcs = this->leafAtProcs(); const labelList& neiProcs = octree_.neiProcs(); - + DynList<label> below, above; forAll(neiProcs, i) { @@ -159,10 +161,10 @@ void meshOctreeAddressing::calcGlobalPointLabels() const below.append(neiProcs[i]); } } - + VRWGraph procLeaves; procLeaves.reverseAddressing(Pstream::nProcs(), leafAtProcs); - + //- scatter the data from the processors above to the processors below //- receive the data from the processors above forAll(above, aboveI) @@ -171,12 +173,12 @@ void meshOctreeAddressing::calcGlobalPointLabels() const labelList receivedLabels; IPstream fromOtherProc(Pstream::blocking, above[aboveI]); fromOtherProc >> receivedLabels; - + label counter(0); while( counter < receivedLabels.size() ) { const label leafI = globalToLocalLeaf[receivedLabels[counter++]]; - + if( nodeLabels.sizeOfRow(leafI) == 0 ) FatalErrorIn ( @@ -184,22 +186,22 @@ void meshOctreeAddressing::calcGlobalPointLabels() const "calcGlobalPointLabels() const" ) << "1. Leaf " << leafI << " is not used in the mesh!" << " Exitting.." << abort(FatalError); - + for(label i=0;i<8;++i) { const label nI = nodeLabels(leafI, i); - + const label globalLabel = receivedLabels[counter++]; - + const label nProcs = receivedLabels[counter++]; for(label ppI=0;ppI<nProcs;++ppI) pointProcs.appendIfNotIn(nI, receivedLabels[counter++]); - + if( globalLabel < 0 ) continue; - + label& gpl = globalPointLabel[nI]; - + if( (gpl != -1) && (gpl != globalLabel) ) FatalErrorIn ( @@ -207,46 +209,46 @@ void meshOctreeAddressing::calcGlobalPointLabels() const "calcGlobalPointLabels() const" ) << "Wrong global label for point " << nI << " Exitting.." << abort(FatalError); - + gpl = globalLabel; globalToLocal.insert(globalLabel, nI); } } } - + //- send the data to the processors below forAll(below, belowI) { const label neiProc = below[belowI]; - - labelListPMG dts; + + labelLongList dts; forAllRow(procLeaves, neiProc, i) { const label leafI = procLeaves(neiProc, i); - + if( nodeLabels.sizeOfRow(leafI) == 0 ) continue; - + dts.append(globalLeafLabel[leafI]); for(label nI=0;nI<8;++nI) { const label nodeI = nodeLabels(leafI, nI); dts.append(globalPointLabel[nodeI]); - + //- add the current processor pointProcs.appendIfNotIn(nodeI, Pstream::myProcNo()); - + dts.append(pointProcs.sizeOfRow(nodeI)); forAllRow(pointProcs, nodeI, ppI) dts.append(pointProcs(nodeI, ppI)); } } - + //- send the data OPstream toOtherProc(Pstream::blocking, neiProc, dts.byteSize()); toOtherProc << dts; } - + //- gather the data from the processors below to the processors above //- receive the data from the processors below forAllReverse(below, belowI) @@ -255,12 +257,12 @@ void meshOctreeAddressing::calcGlobalPointLabels() const labelList receivedLabels; IPstream fromOtherProc(Pstream::blocking, below[belowI]); fromOtherProc >> receivedLabels; - + label counter(0); while( counter < receivedLabels.size() ) { const label leafI = globalToLocalLeaf[receivedLabels[counter++]]; - + if( nodeLabels.sizeOfRow(leafI) == 0 ) FatalErrorIn ( @@ -268,22 +270,22 @@ void meshOctreeAddressing::calcGlobalPointLabels() const "calcGlobalPointLabels() const" ) << "2. Leaf " << leafI << " is not used in the mesh!" << " Exitting.." << abort(FatalError); - + for(label i=0;i<8;++i) { const label nI = nodeLabels(leafI, i); - + const label globalLabel = receivedLabels[counter++]; - + const label nProcs = receivedLabels[counter++]; for(label ppI=0;ppI<nProcs;++ppI) pointProcs.appendIfNotIn(nI, receivedLabels[counter++]); - + if( globalLabel < 0 ) continue; - + label & gpl = globalPointLabel[nI]; - + if( (gpl != -1) && (gpl != globalLabel) ) FatalErrorIn ( @@ -291,41 +293,41 @@ void meshOctreeAddressing::calcGlobalPointLabels() const "calcGlobalPointLabels() const" ) << "Wrong global label for point " << nI << " Exitting.." << abort(FatalError); - + gpl = globalLabel; globalToLocal.insert(globalLabel, nI); } } } - + //- send the data to the processors below forAllReverse(above, aboveI) { const label neiProc = above[aboveI]; - - labelListPMG dts; + + labelLongList dts; forAllRow(procLeaves, neiProc, i) { const label leafI = procLeaves(neiProc, i); - + if( nodeLabels.sizeOfRow(leafI) == 0 ) continue; - + dts.append(globalLeafLabel[leafI]); for(label nI=0;nI<8;++nI) { const label nodeI = nodeLabels(leafI, nI); dts.append(globalPointLabel[nodeI]); - + //- add the current processor pointProcs.appendIfNotIn(nodeI, Pstream::myProcNo()); - + dts.append(pointProcs.sizeOfRow(nodeI)); forAllRow(pointProcs, nodeI, ppI) dts.append(pointProcs(nodeI, ppI)); } } - + //- send the data OPstream toOtherProc(Pstream::blocking, neiProc, dts.byteSize()); toOtherProc << dts; @@ -337,7 +339,7 @@ void meshOctreeAddressing::calcGlobalFaceLabels() const if( !Pstream::parRun() ) FatalErrorIn("void meshOctreeAddressing::calcGlobalFaceLabels() const") << "Cannot calculate global labels! Exitting" << exit(FatalError); - + FatalError << "Not implemented" << exit(FatalError); } @@ -346,48 +348,50 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const if( !Pstream::parRun() ) FatalErrorIn("void meshOctreeAddressing::calcGlobalLeafLabels() const") << "Cannot calculate global labels! Exitting" << exit(FatalError); - + //- allocate the memory - globalLeafLabelPtr_ = new labelListPMG(octree_.numberOfLeaves(), -1); - labelListPMG& globalLeafLabel = *globalLeafLabelPtr_; - + globalLeafLabelPtr_ = new labelLongList(octree_.numberOfLeaves(), -1); + labelLongList& globalLeafLabel = *globalLeafLabelPtr_; + globalLeafToLocalPtr_ = new Map<label>(); Map<label>& globalToLocal = *globalLeafToLocalPtr_; - + leafAtProcsPtr_ = new VRWGraph(octree_.numberOfLeaves()); VRWGraph& leafAtProcs = *leafAtProcsPtr_; - + //- find the number of leaves local to each processor labelList nLeavesAtProc(Pstream::nProcs(), 0); - + label nLeaves(0); - + + # ifdef USE_OMP # pragma omp parallel for schedule(static) reduction(+:nLeaves) + # endif for(label leafI=0;leafI<octree_.numberOfLeaves();++leafI) { const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); - + if( oc.procNo() == Pstream::myProcNo() ) ++nLeaves; } - + nLeavesAtProc[Pstream::myProcNo()] = nLeaves; - + //- exchange the data with other processors Pstream::gatherList(nLeavesAtProc); Pstream::scatterList(nLeavesAtProc); - - //- find the starting labels for + + //- find the starting labels for nLeaves = 0; for(label procI=0;procI<Pstream::myProcNo();++procI) nLeaves += nLeavesAtProc[procI]; - + //- set the global labels to local leaves - labelListPMG otherProcLeaves; + labelLongList otherProcLeaves; for(label leafI=0;leafI<octree_.numberOfLeaves();++leafI) { const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafI); - + if( oc.procNo() == Pstream::myProcNo() ) { globalLeafLabel[leafI] = nLeaves++; @@ -399,11 +403,11 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const leafAtProcs.append(leafI, oc.procNo()); } } - + //- the rest of the code is needed in case an additional layer of //- of octree leaves belonging to other processors is added in order to //- simplify the procedure for generation of mesh templates - + //- allocate the map for exchanging of data std::map<label, LongList<meshOctreeCubeBasic> > exchangeData; const labelList& neiProcs = octree_.neiProcs(); @@ -414,14 +418,14 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const neiProcs[procI], LongList<meshOctreeCubeBasic>() ); - + exchangeData.insert(pp); } - + //- Here we have to combine the information from all processors //- it is started such that all processors send the leaves to the processor //- that contains them locally - + //- fill the map with data forAll(otherProcLeaves, i) { @@ -430,31 +434,31 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const coc.setProcNo(Pstream::myProcNo()); exchangeData[oc.procNo()].append(coc); } - + //- exchange the data with other processors LongList<meshOctreeCubeBasic> rLeaves; help::exchangeMap(exchangeData, rLeaves, Pstream::scheduled); - + //- update the local data forAll(rLeaves, i) { const label cLabel = octree_.findLeafLabelForPosition(rLeaves[i]); - + globalToLocal.insert(globalLeafLabel[cLabel], cLabel); leafAtProcs.appendIfNotIn(cLabel, Pstream::myProcNo()); leafAtProcs.appendIfNotIn(cLabel, rLeaves[i].procNo()); } - + //- now the global leaf labels shall be sent from the processors //- that own the leaves to the processors that also contain them - std::map<label, labelListPMG> exchangeLabels; + std::map<label, labelLongList> exchangeLabels; std::map<label, LongList<meshOctreeCubeBasic> >::iterator it; for(it=exchangeData.begin();it!=exchangeData.end();++it) { it->second.clear(); - exchangeLabels.insert(std::make_pair(it->first, labelListPMG())); + exchangeLabels.insert(std::make_pair(it->first, labelLongList())); } - + //- fill in the data forAll(leafAtProcs, leafI) { @@ -463,31 +467,31 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const forAllRow(leafAtProcs, leafI, i) { const label procI = leafAtProcs(leafI, i); - + if( procI == Pstream::myProcNo() ) continue; - + exchangeData[procI].append(octree_.returnLeaf(leafI)); exchangeLabels[procI].append(globalLeafLabel[leafI]); } } } - + //- exchange the data rLeaves.clear(); help::exchangeMap(exchangeData, rLeaves, Pstream::scheduled); - labelListPMG rLabels; + labelLongList rLabels; help::exchangeMap(exchangeLabels, rLabels, Pstream::scheduled); - + if( rLeaves.size() != rLabels.size() ) FatalErrorIn("void meshOctreeAddressing::calcGlobalLeafLabels() const") << "Invalid list size!" << abort(FatalError); - + //- set the labels to the leaves originating from other processors forAll(rLeaves, i) { const label cLabel = octree_.findLeafLabelForPosition(rLeaves[i]); - + globalLeafLabel[cLabel] = rLabels[i]; globalToLocal.insert(rLabels[i], cLabel); } @@ -495,52 +499,52 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const //- update leafAtProcs for all processors exchangeLabels.clear(); forAll(neiProcs, procI) - exchangeLabels.insert(std::make_pair(neiProcs[procI], labelListPMG())); - + exchangeLabels.insert(std::make_pair(neiProcs[procI], labelLongList())); + forAllConstIter(Map<label>, globalToLocal, iter) { const label leafI = iter(); - + if( octree_.returnLeaf(leafI).procNo() != Pstream::myProcNo() ) continue; - + forAllRow(leafAtProcs, leafI, i) { const label procI = leafAtProcs(leafI, i); - + if( procI == Pstream::myProcNo() ) continue; - - labelListPMG& dts = exchangeLabels[procI]; + + labelLongList& dts = exchangeLabels[procI]; dts.append(iter.key()); - + dts.append(leafAtProcs.sizeOfRow(leafI)); forAllRow(leafAtProcs, leafI, j) dts.append(leafAtProcs(leafI, j)); } } - + //- exchange the data rLabels.clear(); help::exchangeMap(exchangeLabels, rLabels, Pstream::scheduled); - + //- update the local data label counter(0); while( counter < rLabels.size() ) { const label gLabel = rLabels[counter++]; - + if( !globalToLocal.found(gLabel) ) FatalError << "Cannot find global label " << gLabel << exit(FatalError); - + const label leafI = globalToLocal[gLabel]; - + const label numberOfProcs = rLabels[counter++]; for(label i=0;i<numberOfProcs;++i) leafAtProcs.append(leafI, rLabels[counter++]); } - + # ifdef DEBUGAddressing returnReduce(1, sumOp<label>()); const List<direction>& boxType = this->boxType(); @@ -556,50 +560,50 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const << " and coordinates " << octree_.returnLeaf(leafI) << " and located at procs " << leafAtProcs[leafI] << " node labels " << nodeLabels[leafI] << endl; - + if( octree_.returnLeaf(leafI).procNo() == Pstream::myProcNo() ) continue; if( globalToLocal[globalLeafLabel[leafI]] != leafI ) FatalError << "Crap!!" << abort(FatalError); } } - + returnReduce(1, sumOp<label>()); } - + //- check if the leaf at procs is ok exchangeData.clear(); for(label i=0;i<Pstream::nProcs();++i) { if( i == Pstream::myProcNo() ) continue; - + exchangeData[i]; } - + for(label leafI=0;leafI<octree_.numberOfLeaves();++leafI) for(label i=0;i<Pstream::nProcs();++i) { if( i == Pstream::myProcNo() ) continue; - + exchangeData[i].append(octree_.returnLeaf(leafI)); } - + std::map<label, List<meshOctreeCubeBasic> > rMap; help::exchangeMap(exchangeData, rMap); - + for(std::map<label, List<meshOctreeCubeBasic> >::const_iterator it=rMap.begin();it!=rMap.end();++it) { const List<meshOctreeCubeBasic>& data = it->second; - + forAll(data, i) { const label leafI = octree_.findLeafLabelForPosition(data[i]); - + if( leafI < 0 ) continue; - + if( !leafAtProcs.contains(leafI, it->first) ) FatalError << "Problem!!" << leafI << " does not contain processor " << it->first @@ -607,7 +611,7 @@ void meshOctreeAddressing::calcGlobalLeafLabels() const << abort(FatalError); } } - + returnReduce(1, sumOp<label>()); # endif } diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.C index 84af6f544f465950ab9c7b3bd3e7eef7246b2003..bc2b95fe38f3b50dbbee49131d63c4c08cb96e21 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,7 +39,7 @@ Description namespace Foam { - + void meshOctreeAutomaticRefinement::createOctreeAddressing() const { octreeAddressingPtr_ = @@ -51,11 +50,22 @@ const meshOctreeAddressing& meshOctreeAutomaticRefinement::octreeAddressing() const { if( !octreeAddressingPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const meshOctreeAddressing& meshOctreeAutomaticRefinement" + "::octreeAddressing() const" + ) << "Cannot calculate addressing!" << abort(FatalError); + # endif + createOctreeAddressing(); + } return *octreeAddressingPtr_; } - + void meshOctreeAutomaticRefinement::createSurfacePartitioner() const { partitionerPtr_ = new triSurfacePartitioner(octree_.surface()); @@ -64,11 +74,22 @@ void meshOctreeAutomaticRefinement::createSurfacePartitioner() const const triSurfacePartitioner& meshOctreeAutomaticRefinement::partitioner() const { if( !partitionerPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const triSurfacePartitioner& meshOctreeAutomaticRefinement" + "::partitioner() const" + ) << "Cannot calculate addressing!" << abort(FatalError); + # endif + createSurfacePartitioner(); + } return *partitionerPtr_; } - + void meshOctreeAutomaticRefinement::createCurvatureEstimator() const { curvaturePtr_ = new triSurfaceCurvatureEstimator(octree_.surface()); @@ -78,7 +99,18 @@ const triSurfaceCurvatureEstimator& meshOctreeAutomaticRefinement::curvature() const { if( !curvaturePtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const triSurfaceCurvatureEstimator& " + "meshOctreeAutomaticRefinement::curvature() const" + ) << "Cannot calculate addressing!" << abort(FatalError); + # endif + createCurvatureEstimator(); + } return *curvaturePtr_; } @@ -102,8 +134,8 @@ void meshOctreeAutomaticRefinement::setMaxRefLevel() do { finished = false; - - const scalar lSize = size / pow(2, maxRefLevel_); + + const scalar lSize = size / pow(2, label(maxRefLevel_)); if( lSize < cs ) { diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.H index 080d3711ebfb58ec295ef9275327084999b2de99..218ee09bff60b34e8701e04fe5047db071bfa0c9 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinement.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeAutomaticRefinement Description Automatic octree for mesh generation. This class checks if the current - octree resolution is enough to resolve all surface features + octree resolution is enough to resolve all surface features SourceFiles meshOctreeAutomaticRefinement.C @@ -87,7 +86,7 @@ class meshOctreeAutomaticRefinement //- curvature estimator pointer mutable triSurfaceCurvatureEstimator* curvaturePtr_; - //- calculate curvaturePtr_ + //- calculate curvaturePtr_ void createCurvatureEstimator() const; const triSurfaceCurvatureEstimator& curvature() const; @@ -99,11 +98,11 @@ class meshOctreeAutomaticRefinement void setMaxRefLevel(); //- refine selected boxes - void refineSelectedBoxes(List<direction>&, labelListPMG&); + void refineSelectedBoxes(List<direction>&, labelLongList&); //- refine DATA boxes based on curvature bool curvatureRefinement(); - bool refineBasedOnCurvature(List<direction>&, const labelListPMG&); + bool refineBasedOnCurvature(List<direction>&, const labelLongList&); //- refine DATA boxes which contain two or more independent parts //- of the surface in their vicinity @@ -111,7 +110,7 @@ class meshOctreeAutomaticRefinement bool refineBasedOnProximityTests ( List<direction>&, - const labelListPMG& + const labelLongList& ); //- refine DATA boxes containing 2 or more corners, 2 or more distinct @@ -119,14 +118,14 @@ class meshOctreeAutomaticRefinement bool refineBasedOnContainedPartitions ( List<direction>&, - const labelListPMG& + const labelLongList& ); //- refine boxes based on the number of contained surface corners bool refineBasedOnContainedCorners ( List<direction>&, - const labelListPMG& + const labelLongList& ); // Private copy constructor @@ -151,7 +150,7 @@ public: // Destructor ~meshOctreeAutomaticRefinement(); - + // Member Functions //- activate hex refinement void activateHexRefinement(); diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinementRef.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinementRef.C index 0f759c103cf7dfce035992709fe3cf144627b05f..4a16464809ddccb5ce779cc48e44e0ca1bf237df 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinementRef.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeAutomaticRefinement/meshOctreeAutomaticRefinementRef.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -38,7 +37,9 @@ Description #include "Map.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGAutoRef @@ -78,7 +79,7 @@ void meshOctreeAutomaticRefinement::automaticRefinement() bool meshOctreeAutomaticRefinement::curvatureRefinement() { List<direction> refineBox(octree_.numberOfLeaves(), direction(0)); - labelListPMG refinementCandidates; + labelLongList refinementCandidates; forAll(refineBox, i) refinementCandidates.append(i); while( refineBasedOnCurvature(refineBox, refinementCandidates) ) @@ -93,7 +94,7 @@ bool meshOctreeAutomaticRefinement::proximityRefinement() { bool refine(false); List<direction> refineBox(octree_.numberOfLeaves(), direction(0)); - labelListPMG refinementCandidates; + labelLongList refinementCandidates; forAll(refineBox, i) refinementCandidates.append(i); while( refineBasedOnContainedCorners(refineBox, refinementCandidates) ) @@ -126,14 +127,14 @@ bool meshOctreeAutomaticRefinement::proximityRefinement() bool meshOctreeAutomaticRefinement::refineBasedOnContainedCorners ( List<direction>& refineBox, - const labelListPMG& refCandidates + const labelLongList& refCandidates ) { meshOctreeModifier octreeModifier(octree_); const LongList<meshOctreeCube*>& leaves = octreeModifier.leavesAccess(); const boundBox& rootBox = octree_.rootBox(); - const triSurface& surface = octree_.surface(); - const pointField& points = surface.localPoints(); + const triSurf& surface = octree_.surface(); + const pointField& points = surface.points(); const triSurfacePartitioner& sPart = this->partitioner(); //- find leaves which contains corner nodes @@ -145,7 +146,7 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedCorners forAll(corners, cornerI) { const label cLabel = - octree_.findLeafContainingVertex(points[corners[cornerI]]); + octree_.findLeafContainingVertex(points[corners[cornerI]]); if( cLabel < 0 ) continue; @@ -162,10 +163,12 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedCorners } } - DynList<label> leavesInBox(128); + DynList<label> leavesInBox; + # ifdef USE_OMP # pragma omp parallel for if( refCandidates.size() > 1000 ) \ private(leavesInBox) shared(cornerInLeaf) \ reduction(+ : nMarked) schedule(dynamic, 20) + # endif forAll(refCandidates, refI) { const label leafI = refCandidates[refI]; @@ -218,16 +221,16 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedCorners bool meshOctreeAutomaticRefinement::refineBasedOnContainedPartitions ( List<direction>& refineBox, - const labelListPMG& refCandidates + const labelLongList& refCandidates ) { const boundBox& rootBox = octree_.rootBox(); const triSurfacePartitioner& sPart = this->partitioner(); //- find leaves which contains corner nodes - const List<labelHashSet>& pPart = sPart.partitionPartitions(); - const labelList& edgePartition = sPart.edgePartitions(); - const List<labelHashSet>& ePart = sPart.edgePartitionEdgePartitions(); + const List<labelHashSet>& pPatches = sPart.patchPatches(); + const labelList& edgeGroups = sPart.edgeGroups(); + const List<labelHashSet>& eNeiGroups = sPart.edgeGroupEdgeGroups(); # ifdef DEBUGAutoRef Info << "pPart " << pPart << endl; @@ -236,13 +239,15 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedPartitions label nMarked(0); meshOctreeModifier octreeModifier(octree_); - const triSurface& surf = octree_.surface(); + const triSurf& surf = octree_.surface(); const LongList<meshOctreeCube*>& leaves = octreeModifier.leavesAccess(); - DynList<label> patches, ePartitions, helper(100); + DynList<label> patches, eGroups, helper; + # ifdef USE_OMP # pragma omp parallel for if( refCandidates.size() > 1000 ) \ - private(patches, ePartitions, helper) \ + private(patches, eGroups, helper) \ reduction(+ : nMarked) schedule(dynamic, 20) + # endif forAll(refCandidates, refI) { const label leafI = refCandidates[refI]; @@ -265,9 +270,9 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedPartitions //- find edge partitions contained in this box helper.clear(); octree_.findEdgesInBox(bb, helper); - ePartitions.clear(); + eGroups.clear(); forAll(helper, i) - ePartitions.appendIfNotIn(edgePartition[helper[i]]); + eGroups.appendIfNotIn(edgeGroups[helper[i]]); # ifdef DEBUGAutoRef Info << "patches for leaf " << leafI << " are " << patches << endl; @@ -277,7 +282,7 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedPartitions forAll(patches, patchI) { for(label patchJ=(patchI+1);patchJ<patches.size();++patchJ) - if( !pPart[patches[patchI]].found(patches[patchJ]) ) + if( !pPatches[patches[patchI]].found(patches[patchJ]) ) { # ifdef DEBUGAutoRef Info << "2.Here" << endl; @@ -288,10 +293,10 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedPartitions } } - forAll(ePartitions, ePartI) + forAll(eGroups, egI) { - for(label ePartJ=ePartI+1;ePartJ<ePartitions.size();++ePartJ) - if( !ePart[ePartitions[ePartI]].found(ePartitions[ePartJ]) ) + for(label egJ=egI+1;egJ<eGroups.size();++egJ) + if( !eNeiGroups[eGroups[egI]].found(eGroups[egJ]) ) { refine = true; break; @@ -322,7 +327,7 @@ bool meshOctreeAutomaticRefinement::refineBasedOnContainedPartitions bool meshOctreeAutomaticRefinement::refineBasedOnCurvature ( List<direction>& refineBox, - const labelListPMG& refCandidates + const labelLongList& refCandidates ) { const triSurfaceCurvatureEstimator& curv = curvature(); @@ -330,10 +335,12 @@ bool meshOctreeAutomaticRefinement::refineBasedOnCurvature const boundBox& rootBox = octree_.rootBox(); label nMarked(0); - DynList<label> containedTrias(100); + DynList<label> containedTrias; + # ifdef USE_OMP # pragma omp parallel for if( refCandidates.size() > 10000 ) \ private(containedTrias) \ reduction(+ : nMarked) schedule(dynamic, 100) + # endif forAll(refCandidates, refI) { const label leafI = refCandidates[refI]; @@ -392,17 +399,18 @@ bool meshOctreeAutomaticRefinement::refineBasedOnCurvature bool meshOctreeAutomaticRefinement::refineBasedOnProximityTests ( List<direction>& refineBox, - const labelListPMG& refCandidates + const labelLongList& refCandidates ) { const boundBox& rootBox = octree_.rootBox(); const triSurf& surf = octree_.surface(); label nMarked(0); - DynList<label> neighbours(64), helper(128); + DynList<label> helper; + # ifdef USE_OMP # pragma omp parallel for if( refCandidates.size() > 1000 ) \ - private(neighbours, helper) \ - reduction(+ : nMarked) schedule(dynamic, 20) + private(helper) reduction(+ : nMarked) schedule(dynamic, 20) + # endif forAll(refCandidates, refI) { const label leafI = refCandidates[refI]; @@ -444,18 +452,18 @@ bool meshOctreeAutomaticRefinement::refineBasedOnProximityTests } reduce(nMarked, sumOp<label>()); - Info << nMarked << " boxed marked by proximity criteria" << endl; + Info << nMarked << " boxed marked by proximity criteria" << endl; if( nMarked != 0 ) return true; - return false; + return false; } void meshOctreeAutomaticRefinement::refineSelectedBoxes ( List<direction>& refineBox, - labelListPMG& refCandidates + labelLongList& refCandidates ) { deleteDemandDrivenData(octreeAddressingPtr_); diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.C index 13ff05f5b291518059f1561e05c0ebab3ceeaff8..975c0408e44f2c99e304f48db5e3b16f4064dea1 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -28,7 +27,6 @@ Description #include "meshOctreeCreator.H" #include "triSurf.H" -#include "IOdictionary.H" #include "boundBox.H" #include "demandDrivenData.H" @@ -45,6 +43,7 @@ namespace Foam meshOctreeCreator::meshOctreeCreator(meshOctree& mo) : octree_(mo), + scalingFactor_(1.0), meshDictPtr_(NULL), hexRefinement_(false), globalRefLevel_(0), @@ -58,6 +57,7 @@ meshOctreeCreator::meshOctreeCreator ) : octree_(mo), + scalingFactor_(1.0), meshDictPtr_(&dict), hexRefinement_(false), globalRefLevel_(0), @@ -73,6 +73,7 @@ meshOctreeCreator::meshOctreeCreator ) : octree_(mo), + scalingFactor_(1.0), meshDict_(dict), hexRefinement_(false), globalRefLevel_(0), @@ -101,6 +102,11 @@ meshOctreeCreator::~meshOctreeCreator() // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +void meshOctreeCreator::setScalingFactor(const scalar s) +{ + scalingFactor_ = s; +} + void meshOctreeCreator::activateHexRefinement() { hexRefinement_ = true; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.H index 26c884c8ad092c8a045e80640633daed14bdfb43..f2d2ee87bdba8cf341a78ebae8258254f72d8542 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreator.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeCreator @@ -65,6 +64,9 @@ protected: //- Reference to meshOctree meshOctree& octree_; + //- Scaling factor + scalar scalingFactor_; + //- Dictionary containing information necessary to perform refinement const IOdictionary* meshDictPtr_; @@ -137,6 +139,9 @@ public: // Member Functions + //- set the scaling factor + void setScalingFactor(const scalar); + //- activate octree refinement which marks all sons of an octree box //- for refinement in case a single son is marked for refinement //- this type of refinement is necessary for creating hex meshes diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorAdjustOctreeToSurface.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorAdjustOctreeToSurface.C index d32a2609d5e585841ed7416c42085cc95b3c5460..a066a72ac89944c000aa388e075bfbf2eebaa044 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorAdjustOctreeToSurface.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorAdjustOctreeToSurface.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,20 +30,17 @@ Description #include "boundBox.H" #include "demandDrivenData.H" #include "objectRefinementList.H" -#include "IOdictionary.H" #include "VRWGraph.H" #include "meshOctreeModifier.H" #include "HashSet.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define OCTREETiming //#define DEBUGSearch -# ifdef DEBUGSearch -#include "writeOctreeEnsight.H" -# endif - // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam @@ -72,8 +68,10 @@ void meshOctreeCreator::refineBoundary() List<direction> refineCubes(leaves.size(), direction(0)); //- select boxes which need to be refined + # ifdef USE_OMP # pragma omp parallel for reduction(+ : nMarked) \ schedule(dynamic, Foam::min(20, leaves.size()/omp_get_num_threads()+1)) + # endif forAll(leaves, leafI) { const meshOctreeCube& oc = *leaves[leafI]; @@ -150,38 +148,65 @@ void meshOctreeCreator::refineBoxesContainedInObjects() objectRefinementList refObjects; // Read polyPatchList - Istream& is = meshDictPtr_->lookup("objectRefinements"); + if( meshDictPtr_->isDict("objectRefinements") ) + { + const dictionary& dict = meshDictPtr_->subDict("objectRefinements"); + const wordList objectNames = dict.toc(); - PtrList<entry> objectEntries(is); - refObjects.setSize(objectEntries.size()); + refObjects.setSize(objectNames.size()); - forAll(refObjects, objectI) - { - refObjects.set - ( - objectI, - objectRefinement::New + forAll(refObjects, objectI) + { + const entry& objectEntry = + dict.lookupEntry(objectNames[objectI], false, false); + + refObjects.set ( - objectEntries[objectI].keyword(), - objectEntries[objectI].dict() - ) - ); + objectI, + objectRefinement::New + ( + objectEntry.keyword(), + objectEntry.dict() + ) + ); + } } + else + { + Istream& is = meshDictPtr_->lookup("objectRefinements"); - objectEntries.clear(); + PtrList<entry> objectEntries(is); + refObjects.setSize(objectEntries.size()); + + forAll(refObjects, objectI) + { + refObjects.set + ( + objectI, + objectRefinement::New + ( + objectEntries[objectI].keyword(), + objectEntries[objectI].dict() + ) + ); + } + + objectEntries.clear(); + } scalar s(readScalar(meshDictPtr_->lookup("maxCellSize"))); + List<direction> refLevels(refObjects.size(), globalRefLevel_); label nMarked; do { nMarked = 0; forAll(refObjects, oI) - if( refObjects[oI].cellSize() <= s * (1.+SMALL) ) - { - ++nMarked; - ++refLevels[oI]; - } + if( refObjects[oI].cellSize() <= s * (1.+SMALL) ) + { + ++nMarked; + ++refLevels[oI]; + } s /= 2.0; @@ -215,8 +240,10 @@ void meshOctreeCreator::refineBoxesContainedInObjects() List<direction> refineCubes(leaves.size(), direction(0)); //- select boxes which need to be refined + # ifdef USE_OMP # pragma omp parallel for if( leaves.size() > 1000 ) \ reduction( + : nMarked) schedule(dynamic, 20) + # endif forAll(leaves, leafI) { const meshOctreeCube& oc = *leaves[leafI]; @@ -298,7 +325,6 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) const LongList<meshOctreeCube*>& leaves = octreeModifier.leavesAccess(); # ifdef DEBUGSearch - writeOctreeEnsight(octree_, "BeforeMarking"); forAll(leaves, leafI) Info << "Leaf " << leafI << " is " << *leaves[leafI] << " type " << label(leaves[leafI]->cubeType()) << endl; @@ -309,8 +335,10 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) labelHashSet transferCoordinates; LongList<meshOctreeCubeCoordinates> checkCoordinates; + # ifdef USE_OMP # pragma omp parallel for if( leaves.size() > 1000 ) \ schedule(dynamic, 20) + # endif forAll(leaves, leafI) { if( leaves[leafI]->hasContainedElements() ) @@ -332,7 +360,9 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) if( neiLabel == meshOctreeCube::OTHERPROC ) { + # ifdef USE_OMP # pragma omp critical + # endif { if( !transferCoordinates.found(leafI) ) { @@ -343,6 +373,7 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) continue; } + if( neiLabel == -1 ) continue; @@ -371,8 +402,10 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) receivedCoordinates ); + # ifdef USE_OMP # pragma omp parallel for if( receivedCoordinates.size() > 1000 ) \ schedule(dynamic, 20) + # endif forAll(receivedCoordinates, ccI) { const meshOctreeCubeCoordinates& cc = receivedCoordinates[ccI]; @@ -408,8 +441,10 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) transferCoordinates.clear(); } + # ifdef USE_OMP # pragma omp parallel for if( leaves.size() > 1000 ) \ schedule(dynamic, 20) + # endif forAll(leaves, leafI) { if( refineBox[leafI] == i ) @@ -431,7 +466,9 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) if( neiLabel == meshOctreeCube::OTHERPROC ) { + # ifdef USE_OMP # pragma omp critical + # endif { if( !transferCoordinates.found(leafI) ) { @@ -472,8 +509,10 @@ void meshOctreeCreator::refineBoxesNearDataBoxes(const direction nLayers) receivedCoordinates ); + # ifdef USE_OMP # pragma omp parallel for if( receivedCoordinates.size() > 1000 ) \ schedule(dynamic, 20) + # endif forAll(receivedCoordinates, ccI) { const meshOctreeCubeCoordinates& cc = receivedCoordinates[ccI]; @@ -554,8 +593,10 @@ void meshOctreeCreator::refineBoxes List<direction> refineCubes(leaves.size(), direction(0)); + # ifdef USE_OMP # pragma omp parallel for if( leaves.size() > 1000 ) \ reduction(+ : nRefined) schedule(dynamic, 20) + # endif forAll(leaves, leafI) { const meshOctreeCube& oc = *leaves[leafI]; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorCreateOctreeBoxes.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorCreateOctreeBoxes.C index 9df98f4d76a212de43516900f910661f3fcd5245..1037b1b35d1bd82048e68cea3388fcdcf964e224 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorCreateOctreeBoxes.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorCreateOctreeBoxes.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,9 @@ Description #include "triSurf.H" #include "meshOctreeAutomaticRefinement.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGOctree @@ -57,7 +58,11 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() return; } - const scalar maxSize(readScalar(meshDictPtr_->lookup("maxCellSize"))); + const scalar maxSize + ( + scalingFactor_ * + readScalar(meshDictPtr_->lookup("maxCellSize")) + ); octreeModifier.searchRangeAccess() = 0.25 * maxSize; @@ -79,11 +84,12 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() { finished = false; - const scalar lSize = size / pow(2, globalRefLevel_); + const scalar lSize = size / Foam::pow(2, label(globalRefLevel_)); if( lSize < (maxSize * (1.0-SMALL)) ) { - const scalar bbSize = 0.5 * maxSize * pow(2, globalRefLevel_); + const scalar bbSize = + 0.5 * maxSize * Foam::pow(2, label(globalRefLevel_)); rootBox.max() = c + point(bbSize, bbSize, bbSize); rootBox.min() = c - point(bbSize, bbSize, bbSize); finished = true; @@ -116,7 +122,7 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() { direction boundaryRefLevel_ = globalRefLevel_; scalar cs(readScalar(meshDictPtr_->lookup("boundaryCellSize"))); - cs *= (1.0 + SMALL); + cs *= (scalingFactor_ + SMALL); octreeModifier.searchRangeAccess() = cs; @@ -125,9 +131,9 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() { finished = false; - const scalar lSize = maxSize / pow(2, addLevel); + const scalar lSize = maxSize / Foam::pow(2, addLevel); - if( lSize < cs ) + if( lSize <= cs ) { finished = true; } @@ -156,7 +162,35 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() //- set patch-wise ref levels if( meshDictPtr_->found("patchCellSize") ) { - patchRefinementList refPatches(meshDictPtr_->lookup("patchCellSize")); + patchRefinementList refPatches; + + if( meshDictPtr_->isDict("patchCellSize") ) + { + const dictionary& dict = meshDictPtr_->subDict("patchCellSize"); + const wordList patchNames = dict.toc(); + + refPatches.setSize(patchNames.size()); + label counter(0); + + forAll(patchNames, patchI) + { + if( !dict.isDict(patchNames[patchI]) ) + continue; + + const dictionary& patchDict = dict.subDict(patchNames[patchI]); + const scalar cs = readScalar(patchDict.lookup("cellSize")); + + refPatches[counter] = patchRefinement(patchNames[patchI], cs); + ++counter; + } + + refPatches.setSize(counter); + } + else + { + patchRefinementList prl(meshDictPtr_->lookup("patchCellSize")); + refPatches.transfer(prl); + } forAll(refPatches, patchI) { @@ -166,16 +200,16 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() continue; scalar cs = refPatches[patchI].cellSize(); - cs *= (1.0 + SMALL); + cs *= (scalingFactor_ + SMALL); label addLevel(0); do { finished = false; - const scalar lSize = maxSize / pow(2, addLevel); + const scalar lSize = maxSize / Foam::pow(2, addLevel); - if( lSize < cs ) + if( lSize <= cs ) { finished = true; } @@ -202,13 +236,42 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() if( meshDictPtr_->found("subsetCellSize") ) { - patchRefinementList refPatches(meshDictPtr_->lookup("subsetCellSize")); + patchRefinementList refPatches; + + if( meshDictPtr_->isDict("subsetCellSize") ) + { + const dictionary& dict = meshDictPtr_->subDict("subsetCellSize"); + const wordList patchNames = dict.toc(); + + refPatches.setSize(patchNames.size()); + label counter(0); + + forAll(patchNames, patchI) + { + if( !dict.isDict(patchNames[patchI]) ) + continue; + + const dictionary& patchDict = dict.subDict(patchNames[patchI]); + const scalar cs = readScalar(patchDict.lookup("cellSize")); + + refPatches[counter] = patchRefinement(patchNames[patchI], cs); + ++counter; + } + + refPatches.setSize(counter); + } + else + { + patchRefinementList srl(meshDictPtr_->lookup("subsetCellSize")); + refPatches.transfer(srl); + } forAll(refPatches, patchI) { const word subsetName = refPatches[patchI].patchName(); - if( !surface.doesFaceSubsetExist(subsetName) ) + const label subsetID = surface.facetSubsetIndex(subsetName); + if( subsetID < 0 ) { Warning << "Surface subset " << subsetName << " does not exist" << endl; @@ -216,16 +279,16 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() } scalar cs = refPatches[patchI].cellSize(); - cs *= (1.0 + SMALL); + cs *= (scalingFactor_+ SMALL); label addLevel(0); do { finished = false; - const scalar lSize = maxSize / pow(2, addLevel); + const scalar lSize = maxSize / Foam::pow(2, addLevel); - if( lSize < cs ) + if( lSize <= cs ) { finished = true; } @@ -238,14 +301,104 @@ void meshOctreeCreator::setRootCubeSizeAndRefParameters() if( Pstream::parRun() ) reduce(addLevel, maxOp<label>()); - const labelListPMG& subsetFaces = - surface.facesInSubset(subsetName); + labelLongList subsetFaces; + surface.facetsInSubset(subsetID, subsetFaces); const direction level = globalRefLevel_ + addLevel; forAll(subsetFaces, tI) if( surfRefLevel_[subsetFaces[tI]] < level ) surfRefLevel_[subsetFaces[tI]] = level; } } + + if( meshDictPtr_->found("localRefinement") ) + { + if( meshDictPtr_->isDict("localRefinement") ) + { + const dictionary& dict = meshDictPtr_->subDict("localRefinement"); + const wordList entries = dict.toc(); + + //- map patch name to its index + std::map<word, label> patchToIndex; + forAll(surface.patches(), patchI) + patchToIndex[surface.patches()[patchI].name()] = patchI; + + //- map a facet subset name to its index + std::map<word, label> setToIndex; + DynList<label> setIDs; + surface.facetSubsetIndices(setIDs); + forAll(setIDs, i) + setToIndex[surface.facetSubsetName(setIDs[i])] = setIDs[i]; + + //- set refinement for these entries + forAll(entries, dictI) + { + if( !dict.isDict(entries[dictI]) ) + continue; + + const word& pName = entries[dictI]; + const dictionary& patchDict = dict.subDict(pName); + + label nLevel(0); + + if( patchDict.found("additionalRefinementLevels") ) + { + nLevel = + readLabel(patchDict.lookup("additionalRefinementLevels")); + } + else if( patchDict.found("cellSize") ) + { + const scalar cs = + readScalar(patchDict.lookup("cellSize")); + + do + { + finished = false; + + const scalar lSize = maxSize / Foam::pow(2, nLevel); + + if( lSize <= cs ) + { + finished = true; + } + else + { + ++nLevel; + } + } while( !finished ); + } + + const direction level = globalRefLevel_ + nLevel; + + if( patchToIndex.find(pName) != patchToIndex.end() ) + { + //- patch-based refinement + const label patchI = patchToIndex[pName]; + + forAll(surface, triI) + { + if( surface[triI].region() == patchI ) + surfRefLevel_[triI] = + Foam::max(surfRefLevel_[triI], level); + } + } + if( setToIndex.find(pName) != setToIndex.end() ) + { + //- this is a facet subset + const label subsetId = setToIndex[pName]; + + labelLongList facetsInSubset; + surface.facetsInSubset(subsetId, facetsInSubset); + + forAll(facetsInSubset, i) + { + const label triI = facetsInSubset[i]; + surfRefLevel_[triI] = + Foam::max(surfRefLevel_[triI], level); + } + } + } + } + } } void meshOctreeCreator::refineInsideAndUnknownBoxes() @@ -258,14 +411,17 @@ void meshOctreeCreator::refineInsideAndUnknownBoxes() void meshOctreeCreator::createOctreeBoxes() { //- set root cube size in order to achieve desired maxCellSize + Info << "Setting root cube size and refinement parameters" << endl; setRootCubeSizeAndRefParameters(); //- refine to required boundary resolution + Info << "Refining boundary" << endl; refineBoundary(); //- perform automatic octree refinement if( !Pstream::parRun() ) { + Info << "Performing automatic refinement" << endl; meshOctreeAutomaticRefinement autoRef(octree_, *meshDictPtr_, false); if( hexRefinement_ ) @@ -295,11 +451,11 @@ void meshOctreeCreator::createOctreeBoxes() } //- delete octree data which is not needed any more - if( Pstream::parRun() ) - { - meshOctreeModifier om(octree_); - om.reduceMemoryConsumption(); - } +// if( Pstream::parRun() ) +// { +// meshOctreeModifier om(octree_); +// om.reduceMemoryConsumption(); +// } } void meshOctreeCreator::createOctreeWithRefinedBoundary @@ -308,7 +464,9 @@ void meshOctreeCreator::createOctreeWithRefinedBoundary const label nTrianglesInLeaf ) { - const triSurface& surface = octree_.surface(); + const triSurf& surface = octree_.surface(); + surface.facetEdges(); + surface.edgeFacets(); const boundBox& rootBox = octree_.rootBox(); meshOctreeModifier octreeModifier(octree_); List<meshOctreeSlot>& slots = octreeModifier.dataSlotsAccess(); @@ -320,11 +478,19 @@ void meshOctreeCreator::createOctreeWithRefinedBoundary label nMarked(0); + # ifdef USE_OMP # pragma omp parallel reduction(+ : nMarked) + # endif { + # ifdef USE_OMP meshOctreeSlot* slotPtr = &slots[omp_get_thread_num()]; + # else + meshOctreeSlot* slotPtr = &slots[0]; + # endif + # ifdef USE_OMP # pragma omp for schedule(dynamic, 20) + # endif forAll(leaves, leafI) { meshOctreeCube& oc = *leaves[leafI]; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorFrontalMarking.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorFrontalMarking.C index bb1a787c2c9dd5ddf077b065c4a4f8ff8e4e8008..bca907508e6830e3f88e08c7600972a96f471db4 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorFrontalMarking.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorFrontalMarking.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,9 +29,6 @@ Description #include "meshOctreeInsideOutside.H" //#define DEBUGSearch -# ifdef DEBUGSearch -#include "writeOctreeEnsight.H" -# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -46,13 +42,6 @@ void meshOctreeCreator::createInsideOutsideInformation() Info << "Marking inside/outside." << endl; meshOctreeInsideOutside insideOutside(octree_); - - # ifdef DEBUGSearch - writeOctreeEnsight(octree_, "octreeInternal", meshOctreeCubeBasic::INSIDE); - writeOctreeEnsight(octree_, "octreeOutside", meshOctreeCubeBasic::OUTSIDE); - writeOctreeEnsight(octree_, "octreeData", meshOctreeCubeBasic::DATA); - writeOctreeEnsight(octree_, "octreeUnknown", meshOctreeCubeBasic::UNKNOWN); - # endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorLoadDistribution.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorLoadDistribution.C index a987d5e0d7f0e319c9fb824bac539c1ae1f1d387..92cf6d49968fae3374c56cc726d4ffcd1ced7cac 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorLoadDistribution.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCreator/meshOctreeCreatorLoadDistribution.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -34,7 +33,6 @@ Description # ifdef DEBUGBalancing #include <sstream> -#include "writeOctreeEnsight.H" # endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.C index 89c84a1cf578c9c911733aa1a3bebd81f811a437..76f8a42e2136d7126216a82404a29c764b87bc62 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.H index 54263be62990a81aa6a1ecd0ced874fcf6af00dd..7a70526c4f656df9fc94db1d937b6c87c44fd4d8 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCube.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeCube @@ -47,7 +46,7 @@ namespace Foam { class Ostream; -class triSurface; +class triSurf; class VRWGraph; class meshOctreeSlot; @@ -90,7 +89,7 @@ class meshOctreeCube //- find edges contained in the cube void findContainedEdges ( - const triSurface&, + const triSurf&, const boundBox& ); @@ -128,10 +127,19 @@ public: ~meshOctreeCube(); // Member Functions + + //- refine cube in two directions, it is used for generating quadtrees + void refineCube2D + ( + const triSurf&, + const boundBox&, + meshOctreeSlot* slotPtr = NULL + ); + //- subdivide the octree cube void refineCube ( - const triSurface&, + const triSurf&, const boundBox&, meshOctreeSlot* slotPtr = NULL ); @@ -140,7 +148,7 @@ public: //- cube is reached (this function is used for parallel octree creation) void refineMissingCube ( - const triSurface&, + const triSurf&, const boundBox&, const label scI, meshOctreeSlot* slotPtr = NULL @@ -175,7 +183,7 @@ public: //- check if this box has some contained triangles bool hasContainedTriangles ( - const triSurface&, + const triSurf&, const boundBox&, const VRWGraph& containedElements ) const; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasic.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasic.H index e1404a3eaa47abecf4c433a6f56a4869ccad3f45..8b5fba051a8d1590410f61ad3493a688c39048ad 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasic.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasic.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeCubeBasic diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasicI.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasicI.H index d5146b18d3bcc6011f953c0c1ed0a2696d22dfa6..cca780029319d4bf019199cee1c411e4ebd7d7f1 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasicI.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeBasicI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinates.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinates.H index 38ff5bd483502a5b2a5f0ec674c541f48820b75e..76911eaab70b618b827bf9b0df844049003a2d38 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinates.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinates.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeCubeCoordinates @@ -47,7 +46,7 @@ SourceFiles namespace Foam { -class triSurface; +class triSurf; class boundBox; /*---------------------------------------------------------------------------*\ @@ -166,14 +165,14 @@ public: //- check if the surface triangle intersects the cube bool intersectsTriangle ( - const triSurface&, + const triSurf&, const boundBox&, const label ) const; bool intersectsTriangleExact ( - const triSurface&, + const triSurf&, const boundBox&, const label ) const; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesI.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesI.H index 01f5f30a524c1c76a2a9f7d5bff9256edbc0253c..8b815f788e731717ee9462930e68293524ce6bf8 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesI.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -110,7 +109,7 @@ inline meshOctreeCubeCoordinates meshOctreeCubeCoordinates::refineForPosition ( 2*posX_+addPos[0], 2*posY_+addPos[1], - 2*posZ_+addPos[2], + posZ_<0?posZ_:2*posZ_+addPos[2], level_+1 ); } @@ -126,7 +125,7 @@ inline meshOctreeCubeCoordinates meshOctreeCubeCoordinates::reduceLevelBy ( posX_ / divider, posY_ / divider, - posZ_ / divider, + posZ_<0?posZ_:posZ_ / divider, level_ - diff ); } @@ -151,7 +150,7 @@ inline meshOctreeCubeCoordinates meshOctreeCubeCoordinates::increaseToLevelMin ( posX_ << diff, posY_ << diff, - posZ_ << diff, + posZ_<0?posZ_:posZ_ << diff, l ); } @@ -166,7 +165,7 @@ inline meshOctreeCubeCoordinates meshOctreeCubeCoordinates::increaseToLevelMax ( ((posX_ + 1) << diff) - 1, ((posY_ + 1) << diff) - 1, - ((posZ_ + 1) << diff) - 1, + posZ_<0?posZ_:((posZ_ + 1) << diff) - 1, l ); } @@ -178,11 +177,24 @@ inline void meshOctreeCubeCoordinates::cubeBox point& max ) const { - const vector dc = (rootBox.max() - rootBox.min()) / (1 << level_); + vector dc = (rootBox.max() - rootBox.min()); + const label shift = 1 << level_; + + dc.x() /= shift; + dc.y() /= shift; + if( posZ_>=0 ) + dc.z() /= shift; min.x() = rootBox.min().x() + dc.x() * this->posX(); min.y() = rootBox.min().y() + dc.y() * this->posY(); - min.z() = rootBox.min().z() + dc.z() * this->posZ(); + if( posZ_ >= 0 ) + { + min.z() = rootBox.min().z() + dc.z() * this->posZ(); + } + else + { + min.z() = rootBox.min().z(); + } max = min + dc; } diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesIntersections.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesIntersections.C index 0211df57e7a4019c21ae1d5a637bfc03c7a9cfa2..145cea6f73ddca6093854396d0cdb00b0e477c96 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesIntersections.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeCoordinatesIntersections.C @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ -#include "triSurface.H" +#include "triSurf.H" #include "meshOctreeCubeCoordinates.H" #include "helperFunctions.H" @@ -152,13 +151,13 @@ void meshOctreeCubeCoordinates::edgeVertices bool meshOctreeCubeCoordinates::intersectsTriangle ( - const triSurface& surface, + const triSurf& surface, const boundBox& rootBox, const label tI ) const { const pointField& points = surface.points(); - const labelledTri& ltri = surface.localFaces()[tI]; + const labelledTri& ltri = surface[tI]; const vector tol = SMALL * (rootBox.max() - rootBox.min()); @@ -186,7 +185,7 @@ bool meshOctreeCubeCoordinates::intersectsTriangle bool meshOctreeCubeCoordinates::intersectsTriangleExact ( - const triSurface& surface, + const triSurf& surface, const boundBox& rootBox, const label tI ) const diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeI.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeI.H index 7fe749830525dffe5918451320749a1376aac86d..b700b9832d66a2e3260658bd3291e2a5628aed0a 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeI.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeIntersections.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeIntersections.C index 48717635e6d9eaa7e14dea764d264c6975764a1c..b7ecaf40f002e91bbfa9a2cb46355b7f2990d524 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeIntersections.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeIntersections.C @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ -#include "triSurface.H" +#include "triSurf.H" #include "meshOctreeCube.H" #include "VRWGraph.H" #include "helperFunctions.H" @@ -42,7 +41,7 @@ namespace Foam bool meshOctreeCube::hasContainedTriangles ( - const triSurface& surface, + const triSurf& surface, const boundBox& rootBox, const VRWGraph& containedElements ) const diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRecursiveFunctions.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRecursiveFunctions.C index 87069a08354c906cee515f7341c86c7925325b8b..15ddaa0157b3693a53ba60a1e537c8d298d4257c 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRecursiveFunctions.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRecursiveFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,7 @@ Description #include "meshOctreeCube.H" #include "demandDrivenData.H" #include "Ostream.H" -#include "../meshOctree.H" +#include "meshOctree.H" //#define DEBUGSearch @@ -72,7 +71,7 @@ void meshOctreeCube::leavesInBox leaves ); } - else + else if( Pstream::parRun() ) { meshOctreeCubeCoordinates cc = refineForPosition(scI); cc.cubeBox(rootBox, min, max); diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRefine.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRefine.C index da052d0d524124f9d8e8abaa4ef8b1a12f2ce8ee..5dda64fc33bcd7908034871f6ff3f8e4f3ae5e74 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRefine.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCube/meshOctreeCubeRefine.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -28,8 +27,11 @@ Description #include "meshOctreeCube.H" #include "VRWGraph.H" +#include "triSurf.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGSearch @@ -42,42 +44,46 @@ namespace Foam void meshOctreeCube::findContainedEdges ( - const triSurface& surface, + const triSurf& surface, const boundBox& rootBox ) { - const labelListList& faceEdges = surface.faceEdges(); - const labelListList& edgeFaces = surface.edgeFaces(); - const edgeList& edges = surface.edges(); + const VRWGraph& faceEdges = surface.facetEdges(); + const VRWGraph& edgeFaces = surface.edgeFacets(); + const edgeLongList& edges = surface.edges(); const pointField& points = surface.points(); const VRWGraph& containedElements = activeSlotPtr_->containedTriangles_; VRWGraph& containedEdges = activeSlotPtr_->containedEdges_; - DynList<label> addedEdges(10); + DynList<label> addedEdges; labelHashSet addEdge; forAllRow(containedElements, containedElementsLabel_, tI) { - const labelList& fEdges = - faceEdges[containedElements(containedElementsLabel_, tI)]; - forAll(fEdges, feI) + const label facetI = containedElements(containedElementsLabel_, tI); + + forAllRow(faceEdges, facetI, feI) { - if( addEdge.found(fEdges[feI]) ) + const label edgeI = faceEdges(facetI, feI); + + if( addEdge.found(edgeI) ) continue; - const labelList& eFaces = edgeFaces[fEdges[feI]]; - if( eFaces.size() != 2 ) + if( edgeFaces.sizeOfRow(edgeI) != 2 ) continue; - if( surface[eFaces[0]].region() != surface[eFaces[1]].region() ) + if( + surface[edgeFaces(edgeI, 0)].region() != + surface[edgeFaces(edgeI, 1)].region() + ) { - const edge& edg = edges[fEdges[feI]]; + const edge& edg = edges[edgeI]; const point& s = points[edg.start()]; const point& e = points[edg.end()]; if( intersectsLine(rootBox, s, e) ) { - addEdge.insert(fEdges[feI]); - addedEdges.append(fEdges[feI]); + addEdge.insert(edgeI); + addedEdges.append(edgeI); } } } @@ -92,9 +98,130 @@ void meshOctreeCube::findContainedEdges // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +void meshOctreeCube::refineCube2D +( + const triSurf& surface, + const boundBox& rootBox, + meshOctreeSlot* slotPtr +) +{ + if( !slotPtr ) + slotPtr = activeSlotPtr_; + + # ifdef DEBUGSearch + Info << "Refining the cube " << *this << endl; + # endif + + //- set the cube label to -1 + cubeLabel_ = -1; + + //- create subCubes + FixedList<meshOctreeCube*, 8> subCubes; + forAll(subCubes, scI) + subCubes[scI] = NULL; + + //- create new cubes in the Z-order fashion + for(label scI=0;scI<4;++scI) + { + const label cubeI = slotPtr->cubes_.size(); + const meshOctreeCubeCoordinates cc = this->refineForPosition(scI); + + slotPtr->cubes_.append(cc); + + subCubes[scI] = &slotPtr->cubes_[cubeI]; + subCubes[scI]->activeSlotPtr_ = slotPtr; + subCubes[scI]->setCubeType(this->cubeType()); + subCubes[scI]->setProcNo(this->procNo()); + } + + const label subCubesLabel = slotPtr->childCubes_.size(); + slotPtr->childCubes_.appendFixedList(subCubes); + subCubesPtr_ = &slotPtr->childCubes_(subCubesLabel, 0); + + if( hasContainedElements() ) + { + const VRWGraph& containedElements = + activeSlotPtr_->containedTriangles_; + + # ifdef DEBUGSearch + Info << "Distributing contained elements " + << containedElements[containedElementsLabel_] << endl; + # endif + + //- check if the subCube contain the element + FixedList<DynList<label, 512>, 4> elementsInSubCubes; + + forAllRow(containedElements, containedElementsLabel_, tI) + { + const label elI = containedElements(containedElementsLabel_, tI); + + bool used(false); + for(label scI=0;scI<4;++scI) + if( + subCubes[scI]->intersectsTriangleExact + ( + surface, + rootBox, + elI + ) + ) + { + used = true; + elementsInSubCubes[scI].append(elI); + } + + if( !used ) + { + Warning << "Triangle " << elI + << " is not transferred to the child cubes!" << endl; + } + } + + forAll(elementsInSubCubes, scI) + { + const DynList<label, 512>& elmts = elementsInSubCubes[scI]; + + if( elmts.size() != 0 ) + { + VRWGraph& ct = slotPtr->containedTriangles_; + subCubes[scI]->containedElementsLabel_ = ct.size(); + ct.appendList(elmts); + + + # ifdef DEBUGSearch + Info << "Elements in leaf " << scI << " are " + << ct[subCubes[scI]->containedElements()] + << endl; + # endif + } + } + + //- find surface edges within the cube + for(label scI=0;scI<4;++scI) + if( subCubes[scI]->hasContainedElements() ) + { + subCubes[scI]->findContainedEdges + ( + surface, + rootBox + ); + } + else if( subCubes[scI]->cubeType() & DATA ) + { + subCubes[scI]->setCubeType(UNKNOWN); + } + } + + # ifdef DEBUGSearch + for(label scI=0;scI<4;++scI) + Info << "Refined cube " << scI << " is " + << *subCubes[scI] << endl; + # endif +} + void meshOctreeCube::refineCube ( - const triSurface& surface, + const triSurf& surface, const boundBox& rootBox, meshOctreeSlot* slotPtr ) @@ -211,7 +338,7 @@ void meshOctreeCube::refineCube void meshOctreeCube::refineMissingCube ( - const triSurface& ts, + const triSurf& ts, const boundBox& rootBox, const label scI, meshOctreeSlot* slotPtr @@ -227,6 +354,7 @@ void meshOctreeCube::refineMissingCube sCubes[i] = NULL; const label subCubesLabel = slotPtr->childCubes_.size(); + slotPtr->childCubes_.appendFixedList(sCubes); subCubesPtr_ = &slotPtr->childCubes_(subCubesLabel, 0); } @@ -247,7 +375,7 @@ void meshOctreeCube::refineMissingCube { const VRWGraph& containedElements = activeSlotPtr_->containedTriangles_; - DynList<label> ce(containedElements.sizeOfRow(containedElementsLabel_)); + DynList<label, 512> ce; forAllRow(containedElements, containedElementsLabel_, tI) { diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCubePatches.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCubePatches.C index 5721312ba281ee9467e21f64c1feed284f8674ea..8ee3472de308a3483c32841a8ab60c978cced01e 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeCubePatches.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeCubePatches.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeFindNearestSurfacePoint.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeFindNearestSurfacePoint.C index 5d312ce8a90c9aed22fde8682ef4ad23ab26fd18..bb6ca1d9d9864bbf747cf182b8be277e574fdda6 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeFindNearestSurfacePoint.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeFindNearestSurfacePoint.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,6 +29,7 @@ Description #include "triSurf.H" #include "demandDrivenData.H" #include "helperFunctions.H" +#include "HashSet.H" // #define DEBUGSearch @@ -44,11 +44,13 @@ void meshOctree::findNearestSurfacePoint ( point& nearest, scalar& distSq, + label& nearestTriangle, label& region, const point& p ) const { region = -1; + nearestTriangle = 1; const label cLabel = findLeafContainingVertex(p); vector sizeVec; @@ -58,20 +60,20 @@ void meshOctree::findNearestSurfacePoint } else { - const scalar s = 1.5 * leaves_[cLabel]->size(rootBox_); + const scalar s = 0.75 * leaves_[cLabel]->size(rootBox_); sizeVec.x() = sizeVec.y() = sizeVec.z() = s; } //- find nearest surface vertex to the point p - bool found; - label iterationI(0); + bool found(false); + label iterationI(0); DynList<const meshOctreeCube*, 256> neighbours; + distSq = VGREAT; + do { - found = false; boundBox bb(p - sizeVec, p + sizeVec); - distSq = Foam::sqr(sizeVec.x()); neighbours.clear(); findLeavesContainedInBox(bb, neighbours); @@ -84,18 +86,18 @@ void meshOctree::findNearestSurfacePoint const VRWGraph& ct = neighbours[neiI]->slotPtr()->containedTriangles_; - const constRow el = - ct[neighbours[neiI]->containedElements()]; + const constRow el = ct[neighbours[neiI]->containedElements()]; forAll(el, tI) { const point p0 = help::nearestPointOnTheTriangle(el[tI], surface_, p); - const scalar dSq = magSqr(p0 - p); + const scalar dSq = Foam::magSqr(p0 - p); if( dSq < distSq ) { distSq = dSq; nearest = p0; + nearestTriangle = el[tI]; region = surface_[el[tI]].region(); found = true; } @@ -107,14 +109,29 @@ void meshOctree::findNearestSurfacePoint } while( !found && (iterationI++ < 5) ); + # ifdef DEBUGSearch + forAll(surface_, triI) + { + const point pp = help::nearestPointOnTheTriangle(triI, surface_, p); + + if( distSq - magSqr(pp - p) > SMALL ) + Pout << "Point " << p << " current nearest " << nearest + << " closer point " << pp << endl; + } + # endif + if( (!found || (region < 0)) && !Pstream::parRun() ) + { Warning << "Could not find a boundary region for vertex " << p << endl; + Warning << "Found " << found << " and region " << region << endl; + } } void meshOctree::findNearestSurfacePointInRegion ( point& nearest, scalar& distSq, + label& nearestTriangle, const label region, const point& p ) const @@ -127,20 +144,21 @@ void meshOctree::findNearestSurfacePointInRegion } else { - const scalar s = 1.5 * leaves_[cLabel]->size(rootBox_); + const scalar s = 0.75 * leaves_[cLabel]->size(rootBox_); sizeVec.x() = sizeVec.y() = sizeVec.z() = s; } //- find nearest surface vertex to the point p - bool found; - label iterationI(0); + bool found(false); + label iterationI(0); DynList<const meshOctreeCube*, 256> neighbours; + nearestTriangle = -1; + + distSq = VGREAT; do { - found = false; - boundBox bb(p - sizeVec, p + sizeVec); - distSq = Foam::sqr(sizeVec.x()); + const boundBox bb(p - sizeVec, p + sizeVec); neighbours.clear(); findLeavesContainedInBox(bb, neighbours); @@ -163,11 +181,12 @@ void meshOctree::findNearestSurfacePointInRegion const point p0 = help::nearestPointOnTheTriangle(el[tI], surface_, p); - const scalar dSq = magSqr(p0 - p); + const scalar dSq = Foam::magSqr(p0 - p); if( dSq < distSq ) { distSq = dSq; nearest = p0; + nearestTriangle = el[tI]; found = true; } } @@ -184,10 +203,11 @@ void meshOctree::findNearestSurfacePointInRegion bool meshOctree::findNearestEdgePoint ( - const point& p, - const DynList<label>& regions, point& edgePoint, - scalar& distSq + scalar& distSq, + label& nearestEdge, + const point& p, + const DynList<label>& regions ) const { //- find the estimate for the searching range @@ -199,24 +219,26 @@ bool meshOctree::findNearestEdgePoint } else { - const scalar s = 1.5 * leaves_[cLabel]->size(rootBox_); + const scalar s = 0.75 * leaves_[cLabel]->size(rootBox_); sizeVec.x() = sizeVec.y() = sizeVec.z() = s; } DynList<const meshOctreeCube*, 256> neighbours; - const pointField& sp = surface_.localPoints(); - const edgeList& edges = surface_.edges(); - const labelListList& edgeFaces = surface_.edgeFaces(); + const pointField& sp = surface_.points(); + const edgeLongList& edges = surface_.edges(); + const VRWGraph& edgeFaces = surface_.edgeFacets(); edgePoint = p; bool foundAnEdge(false); label iterationI(0); + distSq = VGREAT; + nearestEdge = -1; + do { boundBox bb(p - sizeVec, p + sizeVec); - distSq = Foam::sqr(sizeVec.x()); neighbours.clear(); findLeavesContainedInBox(bb, neighbours); @@ -235,10 +257,12 @@ bool meshOctree::findNearestEdgePoint { //- find if the edge is in correct patches bool correctPatches(true); - const labelList& ef = edgeFaces[ce[eI]]; - forAll(ef, efI) + + forAllRow(edgeFaces, ce[eI], efI) { - if( !regions.contains(surface_[ef[efI]].region()) ) + const label facetI = edgeFaces(ce[eI], efI); + + if( !regions.contains(surface_[facetI].region()) ) { correctPatches = false; break; @@ -251,11 +275,13 @@ bool meshOctree::findNearestEdgePoint const point s = sp[edges[ce[eI]].start()]; const point e = sp[edges[ce[eI]].end()]; const point np = help::nearestPointOnTheEdgeExact(s, e, p); + const scalar dSq = Foam::magSqr(np - p); - if( magSqr(np - p) < distSq ) + if( dSq < distSq ) { - distSq = magSqr(np - p); + distSq = dSq; edgePoint = np; + nearestEdge = ce[eI]; foundAnEdge = true; } } @@ -269,28 +295,30 @@ bool meshOctree::findNearestEdgePoint return foundAnEdge; } -bool meshOctree::findNearestVertexToTheEdge +bool meshOctree::findNearestPointToEdge ( - const FixedList<point, 2>& edgePoints, - const FixedList<label, 2>& edgePointRegions, point& nearest, - scalar& distSq + scalar& distSq, + label& nearestEdge, + const FixedList<point, 2>& edgePoints, + const FixedList<label, 2>& edgePointRegions ) const { const point c = 0.5 * (edgePoints[0] + edgePoints[1]); const scalar dst = mag(edgePoints[0] - edgePoints[1]); vector sizeVec(dst, dst, dst); - boundBox bb(c - 1.5 * sizeVec, c + 1.5 * sizeVec); + boundBox bb(c - 0.75 * sizeVec, c + 0.75 * sizeVec); DynList<const meshOctreeCube*, 256> leavesInBox; findLeavesContainedInBox(bb, leavesInBox); - const labelListList& edgeFaces = surface_.edgeFaces(); - const pointField& points = surface_.localPoints(); - const edgeList& surfaceEdges = surface_.edges(); + const VRWGraph& edgeFaces = surface_.edgeFacets(); + const pointField& points = surface_.points(); + const edgeLongList& surfaceEdges = surface_.edges(); distSq = VGREAT; + nearestEdge = -1; bool found(false); @@ -306,7 +334,7 @@ bool meshOctree::findNearestVertexToTheEdge forAll(edges, eI) { - const labelList& ef = edgeFaces[edges[eI]]; + const constRow ef = edgeFaces[edges[eI]]; if( ef.size() != 2 ) continue; @@ -339,6 +367,7 @@ bool meshOctree::findNearestVertexToTheEdge if( magSqr(nearestOnEdge - nearestOnLine) < distSq ) { nearest = nearestOnEdge; + nearestEdge = edges[eI]; distSq = magSqr(nearestOnEdge - nearestOnLine); found = true; } @@ -350,6 +379,204 @@ bool meshOctree::findNearestVertexToTheEdge return found; } +bool meshOctree::findNearestCorner +( + point& nearest, + scalar& distSq, + label& nearestPoint, + const point& p, + const DynList<label>& patches +) const +{ + + + const label cLabel = findLeafContainingVertex(p); + vector sizeVec; + if( cLabel < 0 ) + { + sizeVec.x() = sizeVec.y() = sizeVec.z() = searchRange_; + } + else + { + const scalar s = 0.75 * leaves_[cLabel]->size(rootBox_); + sizeVec.x() = sizeVec.y() = sizeVec.z() = s; + } + + //- find nearest surface vertex to the point p + bool found(false); + label iterationI(0); + DynList<const meshOctreeCube*, 256> neighbours; + + const pointField& points = surface_.points(); + const VRWGraph& pEdges = surface_.pointEdges(); + const VRWGraph& eFacets = surface_.edgeFacets(); + + distSq = VGREAT; + nearestPoint = -1; + + do + { + boundBox bb(p - sizeVec, p + sizeVec); + + neighbours.clear(); + findLeavesContainedInBox(bb, neighbours); + labelHashSet checkedPoint; + + //- find nearest projection + forAll(neighbours, neiI) + { + if( !neighbours[neiI]->hasContainedElements() ) + continue; + + const VRWGraph& ct = + neighbours[neiI]->slotPtr()->containedTriangles_; + const constRow el = ct[neighbours[neiI]->containedElements()]; + forAll(el, tI) + { + const labelledTri& tri = surface_[el[tI]]; + + forAll(tri, pI) + { + const label spI = tri[pI]; + + if( checkedPoint.found(spI) ) + continue; + + checkedPoint.insert(spI); + + DynList<label> nodePatches; + label nEdges(0); + + forAllRow(pEdges, spI, i) + { + const label eI = pEdges(spI, i); + + if( eFacets.sizeOfRow(eI) != 2 ) + break; + + if( + surface_[eFacets(eI, 0)].region() != + surface_[eFacets(eI, 1)].region() + ) + { + //- found an edge attached to this vertex + ++nEdges; + nodePatches.appendIfNotIn + ( + surface_[eFacets(eI, 0)].region() + ); + nodePatches.appendIfNotIn + ( + surface_[eFacets(eI, 1)].region() + ); + } + } + + if( nEdges > 2 ) + { + //- check if all required patches + //- are present at this corner + nEdges = 0; + forAll(patches, i) + { + if( nodePatches.contains(patches[i]) ) + ++nEdges; + } + + if( nEdges >= patches.size() ) + { + //- all patches are present, check the distance + const scalar dSq = Foam::magSqr(points[spI] - p); + + if( dSq < distSq ) + { + distSq = dSq; + found = true; + nearest = points[spI]; + nearestPoint = spI; + } + } + } + } + } + } + + if( !found ) + sizeVec *= 2.0; + + } while( !found && (iterationI++ < 5) ); + + return found; +} + +bool meshOctree::findNearestPointToPatches +( + point& nearest, + scalar& distSq, + const point& p, + const DynList<label>& patches, + const scalar tol +) const +{ + if( patches.size() == 0 ) + return false; + + point mapPoint(p); + scalar dSq(VGREAT); + + bool found(false); + if( patches.size() == 2 ) + { + label nse; + found = findNearestEdgePoint(mapPoint, dSq, nse, p, patches); + } + else if( patches.size() > 2 ) + { + label nsp; + found = findNearestCorner(mapPoint, dSq, nsp, p, patches); + } + + point mapPointApprox(p); + scalar distSqApprox; + label iter(0); + while( iter++ < 20 ) + { + point newP(vector::zero); + forAll(patches, patchI) + { + point np; + label nearestTri; + this->findNearestSurfacePointInRegion + ( + np, + distSqApprox, + nearestTri, + patches[patchI], + mapPointApprox + ); + + newP += np; + } + + newP /= patches.size(); + if( Foam::magSqr(newP - mapPointApprox) < tol * dSq ) + break; + + mapPointApprox = newP; + } + + distSq = Foam::magSqr(mapPointApprox - p); + nearest = mapPointApprox; + + if( found && (dSq < 1.5 * distSq) ) + { + nearest = mapPoint; + distSq = dSq; + } + + return true; +} + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // } // End namespace Foam diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeI.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeI.H index 33d0ef3ce671b660b3ac27fead585a590fdd0d1a..eae37b281994dfb69ccc3071dea12114a7745fcd 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeI.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -34,6 +33,11 @@ Description namespace Foam { +inline bool meshOctree::isQuadtree() const +{ + return isQuadtree_; +} + //- return octant vectors inline const FixedList<Vector<label>, 8>& meshOctree::octantVectors() const { @@ -54,7 +58,7 @@ inline label meshOctree::numberOfLeaves() const inline const meshOctreeCubeBasic& meshOctree::returnLeaf ( - const label leafI + const label leafI ) const { return *leaves_[leafI]; @@ -171,21 +175,21 @@ inline void meshOctree::findNeighboursOverEdge inline void meshOctree::findNeighboursInDirection ( - const label leafI, - const label dir, - DynList<label>& neiLeaves + const label leafI, + const label dir, + DynList<label>& neiLeaves ) const { - findNeighboursInDirection(leaves_[leafI]->coordinates(), dir, neiLeaves); + findNeighboursInDirection(leaves_[leafI]->coordinates(), dir, neiLeaves); } inline void meshOctree::findNeighboursForLeaf ( - const label leafI, - DynList<label>& neighbourLeaves + const label leafI, + DynList<label>& neighbourLeaves ) const { - findNeighboursForLeaf(leaves_[leafI]->coordinates(), neighbourLeaves); + findNeighboursForLeaf(leaves_[leafI]->coordinates(), neighbourLeaves); } inline void meshOctree::findAllLeafNeighbours diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideCalculations.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideCalculations.C index ffc1fb1006885b3fa5bec04b7ce8467d9b1c6c46..89d5f105439df75495d31b2898588d326994037c 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideCalculations.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideCalculations.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -64,7 +63,7 @@ void meshOctree::findEdgesInBox(const boundBox& bb, DynList<label>& edges) const findLeavesContainedInBox(bb, neighbours); const pointField& points = surface_.points(); - const edgeList& sEdges = surface_.edges(); + const edgeLongList& sEdges = surface_.edges(); const point c = (bb.min() + bb.max()) / 2.0; const scalar dSq = Foam::sqr(0.5 * (bb.max().x() - bb.min().x())); diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.C index c73f3081193d4ef09a3bf10b564da7bcc957e07d..a751abd164401ea63a07ea12cfd246c51e495ffa 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,9 +28,11 @@ Description #include "meshOctreeInsideOutside.H" #include "triSurf.H" #include "boundBox.H" -#include "labelListPMG.H" +#include "labelLongList.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -115,7 +116,9 @@ void meshOctreeInsideOutside::initialiseBoxes() { const LongList<meshOctreeCube*>& leaves = octreeModifier_.leavesAccess(); + # ifdef USE_OMP # pragma omp parallel for if( leaves.size() > 1000 ) + # endif forAll(leaves, leafI) { if( leaves[leafI]->hasContainedElements() ) @@ -134,141 +137,158 @@ void meshOctreeInsideOutside::frontalMarking() communicationCubes_.clear(); neighbouringGroups_.clear(); - labelListPMG frontCubes; - DynList<label> neighbours(24); + labelLongList frontCubes; + DynList<label> neighbours; - label nGroup(0), chunkI(0), nChunks, chunkSize; + label nGroup(0), nThreads(1); const LongList<meshOctreeCube*>& leaves = octreeModifier_.leavesAccess(); const meshOctree& octree = octreeModifier_.octree(); boolList commCubes(leaves.size(), false); - # pragma omp parallel if( leaves.size() > 1000 ) \ + # ifdef USE_OMP + if( leaves.size() > 1000 ) + nThreads = 3 * omp_get_num_procs(); + + # pragma omp parallel num_threads(nThreads) \ private(frontCubes, neighbours) + # endif { LongList<std::pair<label, label> > threadCommPairs; - # pragma omp master - { - nChunks = 3 * omp_get_num_threads(); - chunkSize = leaves.size() / nChunks + 1; - } + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif - # pragma omp barrier + const label chunkSize = leaves.size() / nThreads + 1; - while( chunkI < nChunks ) - { - label minLeaf, maxLeaf; - # pragma omp critical - minLeaf = chunkI++ * chunkSize; + const label minLeaf = threadI * chunkSize; - if( minLeaf >= leaves.size() ) - break; + const label maxLeaf = Foam::min(leaves.size(), minLeaf + chunkSize); - maxLeaf = Foam::min(leaves.size(), minLeaf + chunkSize); + for(label leafI=minLeaf;leafI<maxLeaf;++leafI) + { + if( leaves[leafI]->hasContainedElements() ) + continue; + if( cubeGroup_[leafI] != -1 ) + continue; - for(label leafI=minLeaf;leafI<maxLeaf;++leafI) - { - if( leaves[leafI]->hasContainedElements() ) - continue; - if( cubeGroup_[leafI] != -1 ) - continue; + label groupI; + # ifdef USE_OMP + # pragma omp critical + # endif + groupI = nGroup++; - label groupI; - # pragma omp critical - groupI = nGroup++; + direction cType(meshOctreeCubeBasic::UNKNOWN); + frontCubes.clear(); + frontCubes.append(leafI); + cubeGroup_[leafI] = groupI; - direction cType(meshOctreeCubeBasic::UNKNOWN); - frontCubes.clear(); - frontCubes.append(leafI); - cubeGroup_[leafI] = groupI; + labelLongList neiDATACubes; - labelListPMG neiDATACubes; + while( frontCubes.size() ) + { + const label fLabel = frontCubes.removeLastElement(); + octree.findNeighboursForLeaf(fLabel, neighbours); - while( frontCubes.size() ) + forAll(neighbours, neiI) { - const label fLabel = frontCubes.removeLastElement(); - octree.findNeighboursForLeaf(fLabel, neighbours); - - forAll(neighbours, neiI) + const label nei = neighbours[neiI]; + if( (nei >= minLeaf) && (nei < maxLeaf) ) { - const label nei = neighbours[neiI]; - if( (nei >= minLeaf) && (nei < maxLeaf) ) - { - if( cubeGroup_[nei] != -1 ) - continue; + if( cubeGroup_[nei] != -1 ) + continue; - if( leaves[nei]->hasContainedElements() ) - { - neiDATACubes.append(nei); - } - else - { - frontCubes.append(nei); - cubeGroup_[nei] = groupI; - } + if( leaves[nei]->hasContainedElements() ) + { + neiDATACubes.append(nei); } - else if( nei == -1 ) + else { - cType = meshOctreeCubeBasic::OUTSIDE; + frontCubes.append(nei); + cubeGroup_[nei] = groupI; } - else if( nei == meshOctreeCubeBasic::OTHERPROC ) + } + else if( nei == -1 ) + { + cType = meshOctreeCubeBasic::OUTSIDE; + } + else if( nei == meshOctreeCubeBasic::OTHERPROC ) + { + commCubes[fLabel] = true; + } + else + { + if( leaves[nei]->hasContainedElements() ) { - commCubes[fLabel] = true; + neiDATACubes.append(nei); } else { - if( leaves[nei]->hasContainedElements() ) - { - neiDATACubes.append(nei); - } - else - { - threadCommPairs.append - ( - std::make_pair(fLabel, nei) - ); - } + threadCommPairs.append + ( + std::make_pair(fLabel, nei) + ); } } } + } - # pragma omp critical - { - if( groupI >= boundaryDATACubes_.size() ) - boundaryDATACubes_.setSize(groupI+1); + # ifdef USE_OMP + # pragma omp critical + # endif + { + if( groupI >= boundaryDATACubes_.size() ) + boundaryDATACubes_.setSize(groupI+1); - boundaryDATACubes_.setRow(groupI, neiDATACubes); - groupType_[groupI] = cType; - } + boundaryDATACubes_.setRow(groupI, neiDATACubes); + groupType_[groupI] = cType; } } + # ifdef USE_OMP # pragma omp barrier + # endif - # pragma omp master - neighbouringGroups_.setSize(nGroup); - - # pragma omp barrier - - forAll(threadCommPairs, pairI) + //- find group to neighbouring groups addressing + List<DynList<label> > localNeiGroups(nGroup); + forAll(threadCommPairs, cfI) { - const std::pair<label, label>& cubesPair = threadCommPairs[pairI]; - const label groupI = cubeGroup_[cubesPair.first]; - const label neiGroup = cubeGroup_[cubesPair.second]; + const std::pair<label, label>& lp = threadCommPairs[cfI]; + const label groupI = cubeGroup_[lp.first]; + const label neiGroup = cubeGroup_[lp.second]; - if( neiGroup >= nGroup ) - FatalError << "neiGroup " << neiGroup << " is >= than " + if( (neiGroup >= nGroup) || (groupI >= nGroup) ) + FatalError << "neiGroup " << neiGroup + << " groupI " << groupI << " are >= than " << "nGroups " << nGroup << abort(FatalError); - if( - (neiGroup != -1) && - !neighbouringGroups_.contains(groupI, neiGroup) - ) + if( neiGroup != -1 ) + { + localNeiGroups[groupI].appendIfNotIn(neiGroup); + localNeiGroups[neiGroup].appendIfNotIn(groupI); + } + } + + # ifdef USE_OMP + # pragma omp critical + # endif + { + neighbouringGroups_.setSize(nGroup); + + forAll(localNeiGroups, groupI) { - # pragma omp critical - neighbouringGroups_.append(groupI, neiGroup); + const DynList<label>& lGroups = localNeiGroups[groupI]; + + neighbouringGroups_.appendIfNotIn(groupI, groupI); + + forAll(lGroups, i) + { + neighbouringGroups_.append(groupI, lGroups[i]); + } } } } @@ -321,7 +341,7 @@ void meshOctreeInsideOutside::markOutsideCubes() const LongList<meshOctreeCube*>& leaves = octreeModifier_.leavesAccess(); const meshOctree& octree = octreeModifier_.octree(); - DynList<label> neighbours(24); + DynList<label> neighbours; label nChanged; bool keepUpdating; @@ -385,8 +405,10 @@ void meshOctreeInsideOutside::markOutsideCubes() //- local boxes are their neighbours. If a local neighbour is //- a DATA box set the hasOutsideNeighbour_ flag to true. If the //- local neighbour is of UNKNOWN type set it to OUTSIDE. + # ifdef USE_OMP # pragma omp parallel for if( receivedCoords.size() > 100 ) \ private(neighbours) schedule(dynamic, 20) + # endif forAll(receivedCoords, i) { octree.findNeighboursForLeaf(receivedCoords[i], neighbours); @@ -457,8 +479,8 @@ void meshOctreeInsideOutside::reviseDataBoxes() //- triangles in different patches const LongList<meshOctreeCube*>& leaves = octreeModifier_.leavesAccess(); const meshOctree& octree = octreeModifier_.octree(); - const triSurface& surface = octree.surface(); - DynList<label> neighbours(60); + const triSurf& surface = octree.surface(); + DynList<label> neighbours; boolList checkedPatches(leaves.size(), false); @@ -471,8 +493,10 @@ void meshOctreeInsideOutside::reviseDataBoxes() LongList<meshOctreeCubeCoordinates> checkCoordinates; labelHashSet transferCoordinates; + # ifdef USE_OMP # pragma omp parallel for if( leaves.size() > 1000 ) \ private(neighbours) schedule(dynamic, 20) reduction(+ : nMarked) + # endif forAll(leaves, leafI) if( Pstream::parRun() && hasOutsideNeighbour_[leafI] ) { @@ -480,7 +504,9 @@ void meshOctreeInsideOutside::reviseDataBoxes() forAll(neighbours, neiI) if( neighbours[neiI] == meshOctreeCubeBasic::OTHERPROC ) { + # ifdef USE_OMP # pragma omp critical + # endif { if( !transferCoordinates.found(leafI) ) { @@ -549,8 +575,10 @@ void meshOctreeInsideOutside::reviseDataBoxes() //- check if any of the local neighbours is a data box with //- no OUTSIDE neighbours + # ifdef USE_OMP # pragma omp parallel for if( receivedCoords.size() > 100 ) \ private(neighbours) schedule(dynamic, 20) reduction(+ : nMarked) + # endif forAll(receivedCoords, i) { octree.findAllLeafNeighbours(receivedCoords[i], neighbours); @@ -707,8 +735,10 @@ void meshOctreeInsideOutside::markInsideCubes() receivedCoords ); + # ifdef USE_OMP # pragma omp parallel for if( receivedCoords.size() > 100 ) \ private(neighbours) schedule(dynamic, 20) + # endif forAll(receivedCoords, i) { octree.findNeighboursForLeaf(receivedCoords[i], neighbours); @@ -760,8 +790,10 @@ void meshOctreeInsideOutside::markInsideCubes() //- local boxes are their neighbours. If a local neighbour is //- a DATA box set the hasOutsideNeighbour_ flag to true. If the //- local neighbour is of UNKNOWN type set it to OUTSIDE. + # ifdef USE_OMP # pragma omp parallel for if( receivedCoords.size() > 100 ) \ private(neighbours) schedule(dynamic, 20) reduction(+ : nChanged) + # endif forAll(receivedCoords, i) { octree.findNeighboursForLeaf(receivedCoords[i], neighbours); diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.H index 588004ecfdcc1950bb7f440d600f6dc8a3cd6301..d07df0000b4f5240d3d57cc3b0324b7983f6da59 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeInsideOutside/meshOctreeInsideOutside.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeInsideOutside @@ -55,7 +54,7 @@ class meshOctreeInsideOutside meshOctreeModifier octreeModifier_; //- group for a given leaf - labelListPMG cubeGroup_; + labelLongList cubeGroup_; //- cubes belonging to each group of octree boxes VRWGraph cubesInGroup_; @@ -70,7 +69,7 @@ class meshOctreeInsideOutside boolList hasOutsideNeighbour_; //- label of cubes at processor boundaries - labelListPMG communicationCubes_; + labelLongList communicationCubes_; //- labels of cubes marked by different threads VRWGraph neighbouringGroups_; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.C index b9f779354e5df0d4862a2f3d892077c94ecd4890..7d862d05af1d1b69839500a52d5fcb8054edaf16 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -45,7 +44,7 @@ meshOctreeModifier::meshOctreeModifier meshOctree& octree ) : - octree_(octree) + octree_(octree) {} // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.H index 2e7722720b295bffbdbe6ad0e3d16418d58a3d38..38a132475dfcc5e0c475ebfe7ba5fda691e8dbb3 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifier.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeModifier diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierDistributeLeavesToProcessors.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierDistributeLeavesToProcessors.C index bae02d512216905ad392fa8550d4df42ad8112fe..a34f07578be4359a89b6efecd4c3bea5c5ba4c1d 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierDistributeLeavesToProcessors.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierDistributeLeavesToProcessors.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierEnsureCorrectRegularity.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierEnsureCorrectRegularity.C index d0b75b4683c61a0ad1f75c960bf0c04ce2d6ec15..3ae0d31043c354d43bf7476ed754b838705f8edc 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierEnsureCorrectRegularity.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierEnsureCorrectRegularity.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,9 @@ Description #include "meshOctreeModifier.H" #include "HashSet.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGSearch @@ -49,7 +50,7 @@ void meshOctreeModifier::ensureCorrectRegularity(List<direction>& refineBox) //- this is needed for parallel runs to reduce the bandwidth labelHashSet transferCoordinates; - labelListPMG front; + labelLongList front; forAll(refineBox, leafI) { if( refineBox[leafI] ) @@ -64,16 +65,22 @@ void meshOctreeModifier::ensureCorrectRegularity(List<direction>& refineBox) nMarked = 0; LongList<meshOctreeCubeCoordinates> processorChecks; + # ifdef USE_OMP # pragma omp parallel if( front.size() > 1000 ) \ private(neighbours) reduction(+ : nMarked) + # endif { - labelListPMG tFront; + labelLongList tFront; + # ifdef USE_OMP # pragma omp for + # endif forAll(front, i) tFront.append(front[i]); + # ifdef USE_OMP # pragma omp barrier + # endif front.clear(); @@ -103,7 +110,9 @@ void meshOctreeModifier::ensureCorrectRegularity(List<direction>& refineBox) { neighbours[posI] = NULL; + # ifdef USE_OMP # pragma omp critical + # endif { if( !transferCoordinates.found(leafI) ) { @@ -140,8 +149,10 @@ void meshOctreeModifier::ensureCorrectRegularity(List<direction>& refineBox) ); //- check consistency with received cube coordinates + # ifdef USE_OMP # pragma omp parallel for if( receivedCoords.size() > 100 ) \ - schedule(guided, 20) + schedule(dynamic, 40) + # endif forAll(receivedCoords, ccI) { forAll(rp, posI) @@ -162,7 +173,9 @@ void meshOctreeModifier::ensureCorrectRegularity(List<direction>& refineBox) { refineBox[nei->cubeLabel()] = 1; + # ifdef USE_OMP # pragma omp critical + # endif front.append(nei->cubeLabel()); } } @@ -185,7 +198,9 @@ bool meshOctreeModifier::ensureCorrectRegularitySons(List<direction>& refineBox) label nMarked(0); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 100) reduction(+ : nMarked) + # endif forAll(leaves, leafI) { if( !refineBox[leafI] ) @@ -207,7 +222,9 @@ bool meshOctreeModifier::ensureCorrectRegularitySons(List<direction>& refineBox) else if( neiLeaf == meshOctreeCube::OTHERPROC ) { //- propagate this information to other processors + # ifdef USE_OMP # pragma omp critical + # endif transferCoordinates.append(cc); } } @@ -222,8 +239,10 @@ bool meshOctreeModifier::ensureCorrectRegularitySons(List<direction>& refineBox) receivedCoords ); + # ifdef USE_OMP # pragma omp parallel for if( receivedCoords.size() > 100 ) \ reduction(+ : nMarked) + # endif forAll(receivedCoords, ccI) { const meshOctreeCubeCoordinates& cc = receivedCoords[ccI]; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierI.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierI.H index 70a0483c922720f4e48b30008a3d2232af8ad9c3..7d707f43e43274e76c75451d80b18c4375a8df85 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierI.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierLoadDistribution.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierLoadDistribution.C index 3c5140c9416116aa777756d9c76a4d42646673a3..9030eb675471eec3bb282962bd1030ea3737f4ce 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierLoadDistribution.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierLoadDistribution.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,14 +28,16 @@ Description #include "meshOctreeModifier.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif //#define OCTREETiming //#define DEBUGBalancing # ifdef DEBUGBalancing #include <sstream> -#include "writeOctreeEnsight.H" # endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -139,7 +140,7 @@ void meshOctreeModifier::loadDistribution(const direction usedType) //- leaf boxes which are not in the range for the current processor //- shall be migrated to other processors - std::map<label, labelListPMG> leavesToSend; + std::map<label, labelLongList> leavesToSend; bool oneRemainingBox(false); forAll(globalLeafWeight, leafI) @@ -189,7 +190,7 @@ void meshOctreeModifier::loadDistribution(const direction usedType) label counter(0); for ( - std::map<label, labelListPMG>::const_iterator it=leavesToSend.begin(); + std::map<label, labelLongList>::const_iterator it=leavesToSend.begin(); it!=leavesToSend.end(); ++it ) @@ -272,12 +273,14 @@ void meshOctreeModifier::loadDistribution(const direction usedType) //- create boxes from the received coordinates forAll(migratedCubes, mcI) + { refineTreeForCoordinates ( migratedCubes[mcI].coordinates(), Pstream::myProcNo(), migratedCubes[mcI].cubeType() ); + } createListOfLeaves(); diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierParallelRefinement.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierParallelRefinement.C index a9f2cf71cbca5d077e77344c35439e7829be8a5a..fa92e6ee6329358842d33716bdf3d9f77ab9bffa 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierParallelRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierParallelRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -71,7 +70,7 @@ void meshOctreeModifier::refineTreeForCoordinates meshOctreeCube* nei(octree_.initialCubePtr_); - for(label i=(l-1);i>=0;--i) + for(label i=(l-1);i>=0;--i) { const label levelLimiter = (1 << i); @@ -164,20 +163,6 @@ void meshOctreeModifier::refineTreeForCoordinates if( nei->isLeaf() ) { -/* label containedTrianglesI(-1), containedEdgesI(-1); - - if( containedTriangles.size() ) - { - containedTrianglesI = octree_.containedTriangles_.size(); - octree_.containedTriangles_.appendList(containedTriangles); - } - - if( containedEdges.size() ) - { - containedEdgesI = octree_.containedEdges_.size(); - octree_.containedEdges_.appendList(containedEdges); - } -*/ //- refine the missing cube //nei->refineMissingCube(scI, containedTrianglesI, containedEdgesI); nei->refineMissingCube @@ -278,7 +263,7 @@ void meshOctreeModifier::addLayerFromNeighbouringProcessors() //- cubes which share a common, face, edge or vertex are added into //- the current processor's tree - DynList<label> neighbours(56); + DynList<label> neighbours; forAll(receivedCoordinates, ccI) { octree_.findAllLeafNeighbours @@ -344,7 +329,7 @@ void meshOctreeModifier::addLayerFromNeighbouringProcessors() } # endif - Info << "Finished adding an additional layer of octree cubes" << endl; + Info << "Finished adding an additional layer of octree cubes" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierReduceMemoryConsumption.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierReduceMemoryConsumption.C index afaa74d6677c9e94e84f37d3d2323f2604ae7633..6981376391fc4cb40d1f7a1e0d638cb484d6fe87 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierReduceMemoryConsumption.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierReduceMemoryConsumption.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierRefineSelectedBoxes.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierRefineSelectedBoxes.C index dafa1c119fc0219ab13867ced52d53143acb542f..a6889b3404a249efd75df5e58dea48b0beb97ba7 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierRefineSelectedBoxes.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierRefineSelectedBoxes.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,7 +29,10 @@ Description #include "triSurf.H" #include "HashSet.H" +# ifdef USE_OMP #include <omp.h> +# endif + #include <sys/stat.h> //#define OCTREETiming @@ -62,8 +64,10 @@ void meshOctreeModifier::markAdditionalLayers { LongList<meshOctreeCubeCoordinates> processorChecks; + # ifdef USE_OMP # pragma omp parallel for if( leaves.size() > 1000 ) \ private(neighbours) schedule(dynamic, 20) + # endif forAll(leaves, leafI) { if( refineBox[leafI] != i ) @@ -92,7 +96,9 @@ void meshOctreeModifier::markAdditionalLayers { neighbours[posI] = NULL; + # ifdef USE_OMP # pragma omp critical + # endif { if( !transferCoordinates.found(leafI) ) { @@ -127,8 +133,10 @@ void meshOctreeModifier::markAdditionalLayers ); //- check consistency with received cube coordinates + # ifdef USE_OMP # pragma omp parallel for if( receivedCoords.size() > 1000 ) \ schedule(dynamic, 20) + # endif forAll(receivedCoords, ccI) { forAll(rp, posI) @@ -176,26 +184,47 @@ void meshOctreeModifier::refineSelectedBoxes Info << "Time for ensuring regularity " << (regTime-startTime) << endl; # endif - const triSurface& surface = octree_.surface(); + const triSurf& surface = octree_.surface(); const boundBox& rootBox = octree_.rootBox(); const LongList<meshOctreeCube*>& leaves = octree_.leaves_; //- this is needed for thread safety //- such solutions make me a sad bunny :( - surface.faceEdges(); - surface.edgeFaces(); + surface.facetEdges(); + surface.edgeFacets(); surface.edges(); + # ifdef USE_OMP # pragma omp parallel num_threads(octree_.dataSlots_.size()) + # endif { + # ifdef USE_OMP meshOctreeSlot* slotPtr = &octree_.dataSlots_[omp_get_thread_num()]; + # else + meshOctreeSlot* slotPtr = &octree_.dataSlots_[0]; + # endif - # pragma omp for \ - schedule(dynamic, Foam::min(20, leaves.size() / omp_get_num_threads() + 1)) - forAll(leaves, leafI) + if( !octree_.isQuadtree() ) { - if( refineBox[leafI] ) - leaves[leafI]->refineCube(surface, rootBox, slotPtr); + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 100) + # endif + forAll(leaves, leafI) + { + if( refineBox[leafI] ) + leaves[leafI]->refineCube(surface, rootBox, slotPtr); + } + } + else + { + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 100) + # endif + forAll(leaves, leafI) + { + if( refineBox[leafI] ) + leaves[leafI]->refineCube2D(surface, rootBox, slotPtr); + } } } diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierUpdateCommunicationPattern.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierUpdateCommunicationPattern.C index e50fbafb8643442c39a71528ea45b17bcc81ab13..c8d8e2ac90e78734de1b63d04a689ed30daf41f6 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierUpdateCommunicationPattern.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeModifier/meshOctreeModifierUpdateCommunicationPattern.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,9 @@ Description #include "meshOctreeModifier.H" #include "HashSet.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define OCTREETiming //#define OCTREE_DEBUG diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeNeighbourSearches.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeNeighbourSearches.C index b3b65be7eebba73f86beb09541f6ca6f4b140bf0..62b729860fd06a32e2a8a62677c0fc9d27d57463 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeNeighbourSearches.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeNeighbourSearches.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -48,9 +47,9 @@ label meshOctree::findLeafContainingVertex Info << "Finding leaf for vertex " << p << endl; # endif - const meshOctreeCube* oc = initialCubePtr_; + const meshOctreeCube* ocPtr = initialCubePtr_; - if( !oc->isVertexInside(rootBox_, p) ) + if( !ocPtr->isVertexInside(rootBox_, p) ) { # ifdef OCTREE_DEBUG Info << "Vertex " << p << " is not in the initial cube" << endl; @@ -62,10 +61,10 @@ label meshOctree::findLeafContainingVertex do { - if( oc && !oc->isLeaf() ) + if( ocPtr && !ocPtr->isLeaf() ) { //- find a subCube containing the vertex; - const point c = oc->centre(rootBox_); + const point c = ocPtr->centre(rootBox_); label scI(0); @@ -73,10 +72,10 @@ label meshOctree::findLeafContainingVertex scI |= 1; if( p.y() >= c.y() ) scI |= 2; - if( p.z() >= c.z() ) + if( !isQuadtree_ && p.z() >= c.z() ) scI |= 4; - oc = oc->subCube(scI); + ocPtr = ocPtr->subCube(scI); } else { @@ -84,9 +83,9 @@ label meshOctree::findLeafContainingVertex } } while( !finished ); - if( oc ) + if( ocPtr ) { - return oc->cubeLabel(); + return ocPtr->cubeLabel(); } return meshOctreeCubeBasic::OTHERPROC; @@ -98,46 +97,52 @@ label meshOctree::findNeighbourOverNode const label nodeI ) const { - const meshOctreeCubeCoordinates coords(cc + regularityPositions_[18+nodeI]); + if( isQuadtree_ ) + return -1; + + const meshOctreeCubeCoordinates nc(cc + regularityPositions_[18+nodeI]); - const meshOctreeCube* nei = findCubeForPosition(coords); + const meshOctreeCube* neiPtr = findCubeForPosition(nc); - if( !nei ) + if( !neiPtr ) { const label levelLimiter = (1 << cc.level()); if( - (coords.posX() >= levelLimiter) || (coords.posX() < 0) || - (coords.posY() >= levelLimiter) || (coords.posY() < 0) || - (coords.posZ() >= levelLimiter) || (coords.posZ() < 0) + (nc.posX() >= levelLimiter) || (nc.posX() < 0) || + (nc.posY() >= levelLimiter) || (nc.posY() < 0) || + (!isQuadtree_ && (nc.posZ() >= levelLimiter || nc.posZ() < 0)) || + (isQuadtree_ && (nc.posZ() != initialCubePtr_->posZ())) ) { return -1; } - else + else if( Pstream::parRun() ) { return meshOctreeCubeBasic::OTHERPROC; } + + return -1; } - else if( nei->isLeaf() ) + else if( neiPtr->isLeaf() ) { # ifdef OCTREE_DEBUG - if( leaves_[nei->cubeLabel()] != nei ) + if( leaves_[neiPtr->cubeLabel()] != neiPtr ) FatalError << "Cube does not correspond to itself" << abort(FatalError); # endif - return nei->cubeLabel(); + return neiPtr->cubeLabel(); } else { - FixedList<label, 8> sc; + FixedList<label, 8> sc(-1); for(label scI=0;scI<8;++scI) { - meshOctreeCube* scPtr = nei->subCube(scI); + meshOctreeCube* scPtr = neiPtr->subCube(scI); if( scPtr ) { sc[scI] = scPtr->cubeLabel(); } - else + else if( Pstream::parRun() ) { sc[scI] = meshOctreeCubeBasic::OTHERPROC; } @@ -151,7 +156,7 @@ label meshOctree::findNeighbourOverNode "label meshOctree::findNeighbourOverNode(" "const meshOctreeCubeCoordinates& cc," "const label nodeI) const" - ) << "Should not come here!" << abort(FatalError); + ) << "Should not be here!" << abort(FatalError); return -1; } @@ -163,55 +168,73 @@ void meshOctree::findNeighboursOverEdge DynList<label>& neighbourLeaves ) const { - const meshOctreeCubeCoordinates coords(cc + regularityPositions_[6+eI]); + if( isQuadtree_ && (eI >= 8) ) + { + neighbourLeaves.append(-1); + return; + } - const meshOctreeCube* nei = findCubeForPosition(coords); + const meshOctreeCubeCoordinates nc(cc + regularityPositions_[6+eI]); - if( !nei ) + const meshOctreeCube* neiPtr = findCubeForPosition(nc); + + if( !neiPtr ) { const label levelLimiter = (1 << cc.level()); if( - (coords.posX() >= levelLimiter) || (coords.posX() < 0) || - (coords.posY() >= levelLimiter) || (coords.posY() < 0) || - (coords.posZ() >= levelLimiter) || (coords.posZ() < 0) + (nc.posX() >= levelLimiter) || (nc.posX() < 0) || + (nc.posY() >= levelLimiter) || (nc.posY() < 0) || + (!isQuadtree_ && (nc.posZ() >= levelLimiter || nc.posZ() < 0)) || + (isQuadtree_ && (nc.posZ() != initialCubePtr_->posZ())) ) { neighbourLeaves.append(-1); } - else + else if( Pstream::parRun() ) { neighbourLeaves.append(meshOctreeCubeBasic::OTHERPROC); } } - else if( nei->isLeaf() ) + else if( neiPtr->isLeaf() ) { # ifdef OCTREE_DEBUG - if( leaves_[nei->cubeLabel()] != nei ) + if( leaves_[neiPtr->cubeLabel()] != neiPtr ) FatalError << "Cube does not correspond to itself" << abort(FatalError); # endif - neighbourLeaves.append(nei->cubeLabel()); + neighbourLeaves.append(neiPtr->cubeLabel()); } else { - FixedList<label, 8> sc; + FixedList<label, 8> sc(-1); for(label scI=0;scI<8;++scI) { - meshOctreeCube* scPtr = nei->subCube(scI); + meshOctreeCube* scPtr = neiPtr->subCube(scI); if( scPtr ) { sc[scI] = scPtr->cubeLabel(); } - else + else if( Pstream::parRun() ) { sc[scI] = meshOctreeCubeBasic::OTHERPROC; } } const label* eNodes = meshOctreeCubeCoordinates::edgeNodes_[eI]; - neighbourLeaves.append(sc[7-eNodes[1]]); - neighbourLeaves.append(sc[7-eNodes[0]]); + + if( !isQuadtree_) + { + neighbourLeaves.append(sc[7-eNodes[1]]); + neighbourLeaves.append(sc[7-eNodes[0]]); + } + else + { + if( sc[7-eNodes[1]] >= 0 ) + neighbourLeaves.append(sc[7-eNodes[1]]); + if( (sc[7-eNodes[0]] >= 0) && (sc[7-eNodes[0]] != sc[7-eNodes[1]]) ) + neighbourLeaves.append(sc[7-eNodes[0]]); + } } } @@ -222,6 +245,12 @@ void meshOctree::findNeighboursInDirection DynList<label>& neighbourLeaves ) const { + if( isQuadtree_ && dir >= 4 ) + { + neighbourLeaves.append(-1); + return; + } + label cpx = cc.posX(); label cpy = cc.posY(); label cpz = cc.posZ(); @@ -259,49 +288,50 @@ void meshOctree::findNeighboursInDirection break; } - const meshOctreeCube* nei = + const meshOctreeCube* neiPtr = findCubeForPosition ( meshOctreeCubeCoordinates(cpx, cpy, cpz, cc.level()) ); - if( !nei ) + if( !neiPtr ) { const label levelLimiter = (1 << cc.level()); if( (cpx >= levelLimiter) || (cpx < 0) || (cpy >= levelLimiter) || (cpy < 0) || - (cpz >= levelLimiter) || (cpz < 0) + (!isQuadtree_ && (cpz >= levelLimiter || cpz < 0)) || + (isQuadtree_ && (cpz != initialCubePtr_->posZ())) ) { neighbourLeaves.append(-1); } - else + else if( Pstream::parRun() ) { neighbourLeaves.append(meshOctreeCubeBasic::OTHERPROC); } } - else if( nei->isLeaf() ) + else if( neiPtr->isLeaf() ) { # ifdef OCTREE_DEBUG - if( leaves_[nei->cubeLabel()] != nei ) + if( leaves_[neiPtr->cubeLabel()] != neiPtr ) FatalError << "Cube does not correspond to itself" << abort(FatalError); # endif - neighbourLeaves.append(nei->cubeLabel()); + neighbourLeaves.append(neiPtr->cubeLabel()); } else { - FixedList<label, 8> sc; + FixedList<label, 8> sc(-1); for(label scI=0;scI<8;++scI) { - meshOctreeCube* scPtr = nei->subCube(scI); + meshOctreeCube* scPtr = neiPtr->subCube(scI); if( scPtr ) { sc[scI] = scPtr->cubeLabel(); } - else + else if( Pstream::parRun() ) { sc[scI] = meshOctreeCubeBasic::OTHERPROC; } @@ -309,7 +339,12 @@ void meshOctree::findNeighboursInDirection const label* fNodes = meshOctreeCubeCoordinates::faceNodes_[dir]; for(label i=0;i<4;++i) + { + if( isQuadtree_ && sc[7-fNodes[i]] < 0 ) + continue; + neighbourLeaves.append(sc[7-fNodes[i]]); + } } } @@ -321,7 +356,8 @@ void meshOctree::findNeighboursForLeaf { neighbourLeaves.clear(); - for(label i=0;i<6;++i) + const label nCubeFaces = isQuadtree_?4:6; + for(label i=0;i<nCubeFaces;++i) { findNeighboursInDirection(cc, i, neighbourLeaves); } @@ -336,15 +372,20 @@ void meshOctree::findAllLeafNeighbours neighbourLeaves.clear(); //- neighbours over nodes - for(label i=0;i<8;++i) - neighbourLeaves.append(findNeighbourOverNode(cc, i)); + if( !isQuadtree_ ) + { + for(label i=0;i<8;++i) + neighbourLeaves.append(findNeighbourOverNode(cc, i)); + } //- neighbours over edges - for(label i=0;i<12;++i) + const label nCubeEdges = isQuadtree_?8:12; + for(label i=0;i<nCubeEdges;++i) findNeighboursOverEdge(cc, i, neighbourLeaves); //- neighbours over faces - for(label i=0;i<6;++i) + const label nCubeFaces = isQuadtree_?4:6; + for(label i=0;i<nCubeFaces;++i) findNeighboursInDirection(cc, i, neighbourLeaves); } @@ -362,7 +403,7 @@ void meshOctree::findLeavesForCubeVertex for(label i=0;i<8;++i) { - positions[i] = cc + vrtLeavesPos_[vrtI][i]; + positions[i] = cc + vrtLeavesPos_[vrtI][i]; } forAll(positions, posI) @@ -403,17 +444,18 @@ meshOctreeCube* meshOctree::findCubeForPosition if( (cpx >= levelLimiter) || (cpx < 0) || (cpy >= levelLimiter) || (cpy < 0) || - (cpz >= levelLimiter) || (cpz < 0) + (!isQuadtree_ && (cpz >= levelLimiter || cpz < 0)) || + (isQuadtree_ && (cpz != initialCubePtr_->posZ())) ) { return NULL; } - meshOctreeCube* nei(initialCubePtr_); + meshOctreeCube* neiPtr(initialCubePtr_); for(label i=(l-1);i>=0;--i) { - if( nei && !nei->isLeaf() ) + if( neiPtr && !neiPtr->isLeaf() ) { levelLimiter = (1 << i); @@ -423,10 +465,10 @@ meshOctreeCube* meshOctree::findCubeForPosition scI |= 1; if( cpy & levelLimiter ) scI |= 2; - if( cpz & levelLimiter ) + if( !isQuadtree_ && (cpz & levelLimiter) ) scI |= 4; - nei = nei->subCube(scI); + neiPtr = neiPtr->subCube(scI); } else { @@ -435,10 +477,10 @@ meshOctreeCube* meshOctree::findCubeForPosition } # ifdef OCTREE_DEBUG - Info << "Found position is " << *nei << endl; + Info << "Found position is " << *neiPtr << endl; # endif - return nei; + return neiPtr; } label meshOctree::findLeafLabelForPosition @@ -446,19 +488,20 @@ label meshOctree::findLeafLabelForPosition const meshOctreeCubeCoordinates& cc ) const { - const meshOctreeCube* oc = findCubeForPosition(cc); + const meshOctreeCube* ocPtr = findCubeForPosition(cc); - if( oc && oc->isLeaf() ) + if( ocPtr && ocPtr->isLeaf() ) { - return oc->cubeLabel(); + return ocPtr->cubeLabel(); } - else if( !oc && (neiProcs_.size() != 0) ) + else if( !ocPtr && (neiProcs_.size() != 0) ) { const label levelLimiter = (1 << cc.level()); if( - (cc.posX() < levelLimiter) || (cc.posX() >= 0) || - (cc.posY() < levelLimiter) || (cc.posY() >= 0) || - (cc.posZ() < levelLimiter) || (cc.posZ() >= 0) + (cc.posX() < levelLimiter) && (cc.posX() >= 0) && + (cc.posY() < levelLimiter) && (cc.posY() >= 0) && + ((!isQuadtree_ && (cc.posZ() < levelLimiter && cc.posZ() >= 0)) || + (isQuadtree_ && (cc.posZ() == initialCubePtr_->posZ()))) ) { return meshOctreeCubeBasic::OTHERPROC; diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeParallelCommunication.C b/meshLibrary/utilities/octrees/meshOctree/meshOctreeParallelCommunication.C index e31ab1ffb09fadabcc2551418e5d64e054126b01..938f1b4daf94a02fdb10cfdf6dd1179b92c5faf9 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeParallelCommunication.C +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeParallelCommunication.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/meshOctree/meshOctreeSlot.H b/meshLibrary/utilities/octrees/meshOctree/meshOctreeSlot.H index 10bd9ecfff047576d7df4240a71185561a206e75..48e2f66bbef9f04407ab42bfa6ac817823b6c9a8 100644 --- a/meshLibrary/utilities/octrees/meshOctree/meshOctreeSlot.H +++ b/meshLibrary/utilities/octrees/meshOctree/meshOctreeSlot.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOctreeSlot diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.C b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.C index b36fd8afaeb78c3b7276f0519d9e6e1c740ce41c..1ee99c006870f8dd624b0b82b048da017e97cc21 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -41,39 +40,39 @@ addToRunTimeSelectionTable(objectRefinement, boxRefinement, dictionary); boxRefinement::boxRefinement() : objectRefinement(), - centre_(), - lengthX_(-1.0), - lengthY_(-1.0), - lengthZ_(-1.0) - //angleX_(0.0), - //angleY_(0.0), - //angleZ_(0.0) + centre_(), + lengthX_(-1.0), + lengthY_(-1.0), + lengthZ_(-1.0) + //angleX_(0.0), + //angleY_(0.0), + //angleZ_(0.0) {} boxRefinement::boxRefinement ( - const word& name, + const word& name, const scalar cellSize, - const point& centre, - const scalar lengthX, - const scalar lengthY, - const scalar lengthZ - //const scalar angleX, - //const scalar angleY, - //const scalar angleZ + const point& centre, + const scalar lengthX, + const scalar lengthY, + const scalar lengthZ + //const scalar angleX, + //const scalar angleY, + //const scalar angleZ ) : objectRefinement(), - centre_(centre), - lengthX_(lengthX), - lengthY_(lengthY), - lengthZ_(lengthZ) - //angleX_(angleX), - //angleY_(angleY), - //angleZ_(angleZ) + centre_(centre), + lengthX_(lengthX), + lengthY_(lengthY), + lengthZ_(lengthZ) + //angleX_(angleX), + //angleY_(angleY), + //angleZ_(angleZ) { - setName(name); - setCellSize(cellSize); + setName(name); + setCellSize(cellSize); } boxRefinement::boxRefinement @@ -84,63 +83,63 @@ boxRefinement::boxRefinement : objectRefinement(name, dict) { - this->operator=(dict); + this->operator=(dict); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // bool boxRefinement::intersectsObject(const boundBox& bb) const { - vector v(0.5*lengthX_, 0.5*lengthY_, 0.5*lengthZ_); - boundBox box(centre_ - v, centre_ + v); - - if( box.overlaps(bb) ) - return true; - - return false; + vector v(0.5*lengthX_, 0.5*lengthY_, 0.5*lengthZ_); + boundBox box(centre_ - v, centre_ + v); + + if( box.overlaps(bb) ) + return true; + + return false; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // dictionary boxRefinement::dict(bool ignoreType) const { - dictionary dict; + dictionary dict; - dict.add("cellSize", cellSize()); - dict.add("type", type()); + dict.add("cellSize", cellSize()); + dict.add("type", type()); dict.add("centre", centre_); dict.add("lengthX", lengthX_); - dict.add("lengthY", lengthY_); - dict.add("lengthZ", lengthZ_); - - //dict.add("angleX", angleX_); - //dict.add("angleY", angleY_); - //dict.add("angleZ", angleZ_); + dict.add("lengthY", lengthY_); + dict.add("lengthZ", lengthZ_); + + //dict.add("angleX", angleX_); + //dict.add("angleY", angleY_); + //dict.add("angleZ", angleZ_); return dict; } void boxRefinement::write(Ostream& os) const { - os << " type: " << type() + os << " type: " << type() << " centre: " << centre_ << " lengthX: " << lengthX_ - << " lengthY: " << lengthY_ - << " lengthZ: " << lengthZ_; - //<< " angleX: " << angleX_ - //<< " angleY: " << angleY_ - //<< " angleZ: " << angleZ_; + << " lengthY: " << lengthY_ + << " lengthZ: " << lengthZ_; + //<< " angleX: " << angleX_ + //<< " angleY: " << angleY_ + //<< " angleZ: " << angleZ_; } void boxRefinement::writeDict(Ostream& os, bool subDict) const { - if( subDict ) + if( subDict ) { os << indent << token::BEGIN_BLOCK << incrIndent << nl; } - - os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; + + os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; // only write type for derived types if( type() != typeName_() ) @@ -150,11 +149,11 @@ void boxRefinement::writeDict(Ostream& os, bool subDict) const os.writeKeyword("centre") << centre_ << token::END_STATEMENT << nl; os.writeKeyword("lengthX") << lengthX_ << token::END_STATEMENT << nl; - os.writeKeyword("lengthY") << lengthY_ << token::END_STATEMENT << nl; - os.writeKeyword("lengthZ") << lengthZ_ << token::END_STATEMENT << nl; - //os.writeKeyword("angleX") << angleX_ << token::END_STATEMENT << nl; - //os.writeKeyword("angleY") << angleY_ << token::END_STATEMENT << nl; - //os.writeKeyword("angleZ") << angleZ_ << token::END_STATEMENT << nl; + os.writeKeyword("lengthY") << lengthY_ << token::END_STATEMENT << nl; + os.writeKeyword("lengthZ") << lengthZ_ << token::END_STATEMENT << nl; + //os.writeKeyword("angleX") << angleX_ << token::END_STATEMENT << nl; + //os.writeKeyword("angleY") << angleY_ << token::END_STATEMENT << nl; + //os.writeKeyword("angleZ") << angleZ_ << token::END_STATEMENT << nl; if( subDict ) { @@ -179,10 +178,10 @@ void boxRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void boxRefinement::operator=(const dictionary& d)" - ) << "Entry centre is not sopecified!" << exit(FatalError); + FatalErrorIn + ( + "void boxRefinement::operator=(const dictionary& d)" + ) << "Entry centre is not sopecified!" << exit(FatalError); centre_ = vector::zero; } @@ -193,42 +192,42 @@ void boxRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void boxRefinement::operator=(const dictionary& d)" - ) << "Entry lengthX is not sopecified!" << exit(FatalError); + FatalErrorIn + ( + "void boxRefinement::operator=(const dictionary& d)" + ) << "Entry lengthX is not sopecified!" << exit(FatalError); lengthX_ = -1.0; } - - // specify lengthY + + // specify lengthY if( dict.found("lengthY") ) { lengthY_ = readScalar(dict.lookup("lengthY")); } else { - FatalErrorIn - ( - "void boxRefinement::operator=(const dictionary& d)" - ) << "Entry lengthY is not sopecified!" << exit(FatalError); + FatalErrorIn + ( + "void boxRefinement::operator=(const dictionary& d)" + ) << "Entry lengthY is not sopecified!" << exit(FatalError); lengthY_ = -1.0; } - - // specify lengthZ + + // specify lengthZ if( dict.found("lengthZ") ) { lengthZ_ = readScalar(dict.lookup("lengthZ")); } else { - FatalErrorIn - ( - "void boxRefinement::operator=(const dictionary& d)" - ) << "Entry lengthZ is not sopecified!" << exit(FatalError); + FatalErrorIn + ( + "void boxRefinement::operator=(const dictionary& d)" + ) << "Entry lengthZ is not sopecified!" << exit(FatalError); lengthZ_ = -1.0; } - - // specify angleX + + // specify angleX /* if( dict.found("angleX") ) { angleX_ = readScalar(dict.lookup("angleX")); @@ -237,8 +236,8 @@ void boxRefinement::operator=(const dictionary& d) { angleX_ = -1.0; } - - // specify angleY + + // specify angleY if( dict.found("angleY") ) { angleY_ = readScalar(dict.lookup("angleY")); @@ -247,8 +246,8 @@ void boxRefinement::operator=(const dictionary& d) { angleY_ = -1.0; } - - // specify angleX + + // specify angleX if( dict.found("angleZ") ) { angleZ_ = readScalar(dict.lookup("angleZ")); @@ -264,14 +263,14 @@ void boxRefinement::operator=(const dictionary& d) Ostream& boxRefinement::operator<<(Ostream& os) const { - os << "name " << name() << nl; - os << "cell size " << cellSize() << nl; - write(os); - return os; + os << "name " << name() << nl; + os << "cell size " << cellSize() << nl; + write(os); + return os; } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + } // End namespace Foam // ************************************************************************* // diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.H index a47944f4e6be657588178b4a0b546edb0dab495f..5a1de77434580b4296bba69b1584429f2a3637ea 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/boxRefinement.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class boxRefinement @@ -53,19 +52,19 @@ class boxRefinement : public objectRefinement { - // Private data - //- centre of the box - point centre_; - - //- length of box sides - scalar lengthX_; - scalar lengthY_; - scalar lengthZ_; - - //- angles to the global coordinate system - //scalar angleX_; - //scalar angleY_; - //scalar angleZ_; + // Private data + //- centre of the box + point centre_; + + //- length of box sides + scalar lengthX_; + scalar lengthY_; + scalar lengthZ_; + + //- angles to the global coordinate system + //scalar angleX_; + //scalar angleY_; + //scalar angleZ_; public: @@ -84,46 +83,46 @@ public: const word& name, const scalar cellSize, const point& centre, - const scalar lengthX, - const scalar lengthY, - const scalar lengthZ - //const scalar angleX = 0., - //const scalar angleY = 0., - //const scalar angleZ = 0. + const scalar lengthX, + const scalar lengthY, + const scalar lengthZ + //const scalar angleX = 0., + //const scalar angleY = 0., + //const scalar angleZ = 0. ); //- Construct from dictionary boxRefinement(const word& name, const dictionary& dict); - - //- Construct and return a clone + + //- Construct and return a clone virtual autoPtr<objectRefinement> clone - ( - const boxRefinement& sr - ) const + ( + const boxRefinement& sr + ) const { return autoPtr<objectRefinement> - ( - new boxRefinement - ( - sr.name(), - sr.cellSize(), - sr.centre_, - sr.lengthX_, - sr.lengthY_, - sr.lengthZ_ - //sr.angleX_, - //sr.angleY_, - //sr.angleZ_ - ) - ); + ( + new boxRefinement + ( + sr.name(), + sr.cellSize(), + sr.centre_, + sr.lengthX_, + sr.lengthY_, + sr.lengthZ_ + //sr.angleX_, + //sr.angleY_, + //sr.angleZ_ + ) + ); } - - // Member Functions - - //- check if a boundBox intersects or is inside the object - bool intersectsObject(const boundBox&) const; - - //- Return as dictionary of entries + + // Member Functions + + //- check if a boundBox intersects or is inside the object + bool intersectsObject(const boundBox&) const; + + //- Return as dictionary of entries dictionary dict(bool ignoreType = false) const; // Write @@ -133,15 +132,15 @@ public: //- Write dictionary void writeDict(Ostream&, bool subDict = true) const; - - // Member Operators + + // Member Operators //- assign from dictionary void operator=(const dictionary&); // IOstream Operators - Ostream& operator<<(Ostream&) const; + Ostream& operator<<(Ostream&) const; }; diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.C b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.C index d54cdeaa09582e8ff24b6823fabf6afa242f00b5..923adbe637c6aa93c7fbc33f766d08f6d3bf9ee1 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -41,30 +40,30 @@ addToRunTimeSelectionTable(objectRefinement, coneRefinement, dictionary); coneRefinement::coneRefinement() : objectRefinement(), - p0_(), - r0_(-1.0), - p1_(), - r1_(-1.0) + p0_(), + r0_(-1.0), + p1_(), + r1_(-1.0) {} coneRefinement::coneRefinement ( - const word& name, + const word& name, const scalar cellSize, - const point& p0, - const scalar radius0, - const point& p1, - const scalar radius1 + const point& p0, + const scalar radius0, + const point& p1, + const scalar radius1 ) : objectRefinement(), - p0_(p0), - r0_(radius0), - p1_(p1), - r1_(radius1) + p0_(p0), + r0_(radius0), + p1_(p1), + r1_(radius1) { - setName(name); - setCellSize(cellSize); + setName(name); + setCellSize(cellSize); } coneRefinement::coneRefinement @@ -75,68 +74,68 @@ coneRefinement::coneRefinement : objectRefinement(name, dict) { - this->operator=(dict); + this->operator=(dict); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // bool coneRefinement::intersectsObject(const boundBox& bb) const { - //- check if the centre is inside the cone - const point c = (bb.max() + bb.min()) / 2.0; - - const vector v = p1_ - p0_; - const scalar d = magSqr(v); - - if( d < VSMALL ) - return false; - - const scalar t = ((c - p0_) & v) / d; - if( (t > 1.0) || (t < 0.0) ) - return false; - - const scalar r = r0_ + (r1_ - r0_) * t; - - if( mag(p0_ + t * v - c) < r ) - return true; - - return false; + //- check if the centre is inside the cone + const point c = (bb.max() + bb.min()) / 2.0; + + const vector v = p1_ - p0_; + const scalar d = magSqr(v); + + if( d < VSMALL ) + return false; + + const scalar t = ((c - p0_) & v) / d; + if( (t > 1.0) || (t < 0.0) ) + return false; + + const scalar r = r0_ + (r1_ - r0_) * t; + + if( mag(p0_ + t * v - c) < r ) + return true; + + return false; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // dictionary coneRefinement::dict(bool ignoreType) const { - dictionary dict; + dictionary dict; - dict.add("cellSize", cellSize()); - dict.add("type", type()); + dict.add("cellSize", cellSize()); + dict.add("type", type()); dict.add("p0", p0_); dict.add("radius0", r0_); - dict.add("p1", p1_); - dict.add("radius1", r1_); + dict.add("p1", p1_); + dict.add("radius1", r1_); return dict; } void coneRefinement::write(Ostream& os) const { - os << " type: " << type() + os << " type: " << type() << " p0: " << p0_ << " radius0: " << r0_ - << " p1: " << p1_ - << " radius1: " << r1_; + << " p1: " << p1_ + << " radius1: " << r1_; } void coneRefinement::writeDict(Ostream& os, bool subDict) const { - if( subDict ) + if( subDict ) { os << indent << token::BEGIN_BLOCK << incrIndent << nl; } - - os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; + + os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; // only write type for derived types if( type() != typeName_() ) @@ -146,9 +145,9 @@ void coneRefinement::writeDict(Ostream& os, bool subDict) const os.writeKeyword("p0") << p0_ << token::END_STATEMENT << nl; os.writeKeyword("radius0") << r0_ << token::END_STATEMENT << nl; - os.writeKeyword("p1") << p1_ << token::END_STATEMENT << nl; + os.writeKeyword("p1") << p1_ << token::END_STATEMENT << nl; os.writeKeyword("radius1") << r1_ << token::END_STATEMENT << nl; - + if( subDict ) { os << decrIndent << indent << token::END_BLOCK << endl; @@ -172,10 +171,10 @@ void coneRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void coneRefinement::operator=(const dictionary& d)" - ) << "Entry p0 is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void coneRefinement::operator=(const dictionary& d)" + ) << "Entry p0 is not specified!" << exit(FatalError); p0_ = vector::zero; } @@ -186,24 +185,24 @@ void coneRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void coneRefinement::operator=(const dictionary& d)" - ) << "Entry radius0 is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void coneRefinement::operator=(const dictionary& d)" + ) << "Entry radius0 is not specified!" << exit(FatalError); r0_ = -1.0; } - - // unspecified centre is (0 0 0) + + // unspecified centre is (0 0 0) if( dict.found("p1") ) { dict.lookup("p1") >> p1_; } else { - FatalErrorIn - ( - "void coneRefinement::operator=(const dictionary& d)" - ) << "Entry p1 is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void coneRefinement::operator=(const dictionary& d)" + ) << "Entry p1 is not specified!" << exit(FatalError); p1_ = vector::zero; } @@ -214,10 +213,10 @@ void coneRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void coneRefinement::operator=(const dictionary& d)" - ) << "Entry radius1 is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void coneRefinement::operator=(const dictionary& d)" + ) << "Entry radius1 is not specified!" << exit(FatalError); r1_ = -1.0; } } @@ -226,14 +225,14 @@ void coneRefinement::operator=(const dictionary& d) Ostream& coneRefinement::operator<<(Ostream& os) const { - os << "name " << name() << nl; - os << "cell size " << cellSize() << nl; - write(os); - return os; + os << "name " << name() << nl; + os << "cell size " << cellSize() << nl; + write(os); + return os; } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + } // End namespace Foam // ************************************************************************* // diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.H index 82e57455040472d5d79e834d8740fcbe5196f7b3..b25510f25b30c1e3a66353a5ac94a25b48d126f6 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/coneRefinement.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class coneRefinement @@ -53,14 +52,14 @@ class coneRefinement : public objectRefinement { - // Private data - //- start point and the radius - point p0_; - scalar r0_; - - //- end point and the radius - point p1_; - scalar r1_; + // Private data + //- start point and the radius + point p0_; + scalar r0_; + + //- end point and the radius + point p1_; + scalar r1_; public: @@ -80,39 +79,39 @@ public: const scalar cellSize, const point& p0, const scalar radius0, - const point& p1, - const scalar radius1 + const point& p1, + const scalar radius1 ); //- Construct from dictionary coneRefinement(const word& name, const dictionary& dict); - - //- Construct and return a clone + + //- Construct and return a clone virtual autoPtr<objectRefinement> clone - ( - const coneRefinement& sr - ) const + ( + const coneRefinement& sr + ) const { return autoPtr<objectRefinement> - ( - new coneRefinement - ( - sr.name(), - sr.cellSize(), - sr.p0_, - sr.r0_, - sr.p1_, - sr.r1_ - ) - ); + ( + new coneRefinement + ( + sr.name(), + sr.cellSize(), + sr.p0_, + sr.r0_, + sr.p1_, + sr.r1_ + ) + ); } - - // Member Functions - - //- check if a boundBox intersects or is inside the object - bool intersectsObject(const boundBox&) const; - - //- Return as dictionary of entries + + // Member Functions + + //- check if a boundBox intersects or is inside the object + bool intersectsObject(const boundBox&) const; + + //- Return as dictionary of entries dictionary dict(bool ignoreType = false) const; // Write @@ -122,15 +121,15 @@ public: //- Write dictionary void writeDict(Ostream&, bool subDict = true) const; - - // Member Operators + + // Member Operators //- assign from dictionary void operator=(const dictionary&); // IOstream Operators - Ostream& operator<<(Ostream&) const; + Ostream& operator<<(Ostream&) const; }; diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.C b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.C index fac4c5e980f59c620cb618eb06338c38945c6acd..46327193d46a3af29c40b11e22c6063a473a9c3f 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -41,24 +40,24 @@ addToRunTimeSelectionTable(objectRefinement, lineRefinement, dictionary); lineRefinement::lineRefinement() : objectRefinement(), - p0_(), - p1_() + p0_(), + p1_() {} lineRefinement::lineRefinement ( - const word& name, + const word& name, const scalar cellSize, - const point& p0, - const point& p1 + const point& p0, + const point& p1 ) : objectRefinement(), - p0_(p0), - p1_(p1) + p0_(p0), + p1_(p1) { - setName(name); - setCellSize(cellSize); + setName(name); + setCellSize(cellSize); } lineRefinement::lineRefinement @@ -69,7 +68,7 @@ lineRefinement::lineRefinement : objectRefinement(name, dict) { - this->operator=(dict); + this->operator=(dict); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -77,8 +76,8 @@ lineRefinement::lineRefinement bool lineRefinement::intersectsObject(const boundBox& bb) const { //- check if the cube contains start point or end point - const scalar l = bb.max().x() - bb.min().x(); - + const scalar l = bb.max().x() - bb.min().x(); + const point min = bb.min() - l * vector(SMALL, SMALL, SMALL); const point max = bb.max() + l * vector(SMALL, SMALL, SMALL); @@ -207,10 +206,10 @@ bool lineRefinement::intersectsObject(const boundBox& bb) const dictionary lineRefinement::dict(bool ignoreType) const { - dictionary dict; + dictionary dict; - dict.add("cellSize", cellSize()); - dict.add("type", type()); + dict.add("cellSize", cellSize()); + dict.add("type", type()); dict.add("p0", p0_); dict.add("p1", p1_); @@ -220,19 +219,19 @@ dictionary lineRefinement::dict(bool ignoreType) const void lineRefinement::write(Ostream& os) const { - os << " type: " << type() + os << " type: " << type() << " p0: " << p0_ << " p1: " << p1_; } void lineRefinement::writeDict(Ostream& os, bool subDict) const { - if( subDict ) + if( subDict ) { os << indent << token::BEGIN_BLOCK << incrIndent << nl; } - - os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; + + os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; // only write type for derived types if( type() != typeName_() ) @@ -266,10 +265,10 @@ void lineRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void lineRefinement::operator=(const dictionary& d)" - ) << "Entry p0 is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void lineRefinement::operator=(const dictionary& d)" + ) << "Entry p0 is not specified!" << exit(FatalError); p0_ = vector::zero; } @@ -280,10 +279,10 @@ void lineRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void lineRefinement::operator=(const dictionary& d)" - ) << "Entry p1 is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void lineRefinement::operator=(const dictionary& d)" + ) << "Entry p1 is not specified!" << exit(FatalError); p1_ = vector::zero; } } @@ -292,14 +291,14 @@ void lineRefinement::operator=(const dictionary& d) Ostream& lineRefinement::operator<<(Ostream& os) const { - os << "name " << name() << nl; - os << "cell size " << cellSize() << nl; - write(os); - return os; + os << "name " << name() << nl; + os << "cell size " << cellSize() << nl; + write(os); + return os; } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + } // End namespace Foam // ************************************************************************* // diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.H index c8761a0e11b917307bb27c11ea13774f769443ee..20b7ece27b6996a54c17506a872eedef6f76fac1 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/lineRefinement.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class lineRefinement @@ -53,12 +52,12 @@ class lineRefinement : public objectRefinement { - // Private data - //- start point of the line - point p0_; - - //- end point of the line - point p1_; + // Private data + //- start point of the line + point p0_; + + //- end point of the line + point p1_; public: @@ -82,31 +81,31 @@ public: //- Construct from dictionary lineRefinement(const word& name, const dictionary& dict); - - //- Construct and return a clone + + //- Construct and return a clone virtual autoPtr<objectRefinement> clone - ( - const lineRefinement& sr - ) const + ( + const lineRefinement& sr + ) const { return autoPtr<objectRefinement> - ( - new lineRefinement - ( - sr.name(), - sr.cellSize(), - sr.p0_, - sr.p1_ - ) - ); + ( + new lineRefinement + ( + sr.name(), + sr.cellSize(), + sr.p0_, + sr.p1_ + ) + ); } - - // Member Functions - - //- check if the line intersects the box - bool intersectsObject(const boundBox&) const; - - //- Return as dictionary of entries + + // Member Functions + + //- check if the line intersects the box + bool intersectsObject(const boundBox&) const; + + //- Return as dictionary of entries dictionary dict(bool ignoreType = false) const; // Write @@ -116,15 +115,15 @@ public: //- Write dictionary void writeDict(Ostream&, bool subDict = true) const; - - // Member Operators + + // Member Operators //- assign from dictionary void operator=(const dictionary&); // IOstream Operators - Ostream& operator<<(Ostream&) const; + Ostream& operator<<(Ostream&) const; }; diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/newObjectRefinement.C b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/newObjectRefinement.C index 6032fc2325b536de26ded19bd4a310b444e73603..e9d52d198a2401f27702b6395ea4a35904ae758a 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/newObjectRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/newObjectRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -52,7 +51,7 @@ autoPtr<Foam::objectRefinement> Foam::objectRefinement::New word refType(typeName_()); if( dict.found("type") ) { - dict.lookup("type") >> refType; + dict.lookup("type") >> refType; } dictionaryConstructorTable::iterator cstrIter = diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.C b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.C index 5ec770cddfed7074a4f66176cf8231c2157998aa..10e05e81bbbc844b13100fff7b8f9e5c7f547ccd 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -32,7 +31,7 @@ License namespace Foam { - + defineTypeNameAndDebug(objectRefinement, 0); defineRunTimeSelectionTable(objectRefinement, dictionary); @@ -41,7 +40,7 @@ defineRunTimeSelectionTable(objectRefinement, dictionary); objectRefinement::objectRefinement() : name_(), - cellSize_() + cellSize_() {} @@ -52,7 +51,7 @@ objectRefinement::objectRefinement ) : name_(name), - cellSize_(readScalar(dict.lookup("cellSize"))) + cellSize_(readScalar(dict.lookup("cellSize"))) { } @@ -161,9 +160,9 @@ void coordinateSystem::operator=(const dictionary& rhs) Ostream& operator<<(Ostream& os, const objectRefinement& obr) { - os << obr.name() << nl; - obr.writeDict(os, true); - return os; + os << obr.name() << nl; + obr.writeDict(os, true); + return os; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.H index cf814456cc61b3ab87aa4af6e15ff0359e5f4560..9a782c8bda4f97a1d58aa8feacfb19171d392f4d 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinement.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class objectRefinement diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinementList.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinementList.H index 79ac07a7c41033ab5b3d22cc74910b3ce73144d8..8ce3b9d28d23c4cef4ad9a02ac9111f624dec59d 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinementList.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/objectRefinementList.H @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class objectRefinementList Description - A list of object refinements + A list of object refinements SourceFiles diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.C b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.C index 0d362ada68062fa771d5d65f548e90869181e6be..8098eca89811fb8f66dcfd315b285fdace94c604 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. \*---------------------------------------------------------------------------*/ @@ -41,24 +40,24 @@ addToRunTimeSelectionTable(objectRefinement, sphereRefinement, dictionary); sphereRefinement::sphereRefinement() : objectRefinement(), - centre_(), - radius_(-1.0) + centre_(), + radius_(-1.0) {} sphereRefinement::sphereRefinement ( - const word& name, + const word& name, const scalar cellSize, - const point& centre, - const scalar radius + const point& centre, + const scalar radius ) : objectRefinement(), - centre_(centre), - radius_(radius) + centre_(centre), + radius_(radius) { - setName(name); - setCellSize(cellSize); + setName(name); + setCellSize(cellSize); } sphereRefinement::sphereRefinement @@ -69,7 +68,7 @@ sphereRefinement::sphereRefinement : objectRefinement(name, dict) { - this->operator=(dict); + this->operator=(dict); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -79,19 +78,19 @@ bool sphereRefinement::intersectsObject(const boundBox& bb) const const point& c = (bb.max() + bb.min()) / 2.0; if( magSqr(c - centre_) < sqr(radius_) ) - return true; - - return false; + return true; + + return false; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // dictionary sphereRefinement::dict(bool ignoreType) const { - dictionary dict; + dictionary dict; - dict.add("cellSize", cellSize()); - dict.add("type", type()); + dict.add("cellSize", cellSize()); + dict.add("type", type()); dict.add("centre", centre_); dict.add("radius", radius_); @@ -101,19 +100,19 @@ dictionary sphereRefinement::dict(bool ignoreType) const void sphereRefinement::write(Ostream& os) const { - os << " type: " << type() + os << " type: " << type() << " centre: " << centre_ << " radius: " << radius_; } void sphereRefinement::writeDict(Ostream& os, bool subDict) const { - if( subDict ) + if( subDict ) { os << indent << token::BEGIN_BLOCK << incrIndent << nl; } - - os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; + + os.writeKeyword("cellSize") << cellSize() << token::END_STATEMENT << nl; // only write type for derived types if( type() != typeName_() ) @@ -147,10 +146,10 @@ void sphereRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void sphereRefinement::operator=(const dictionary& d)" - ) << "Entry centre is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void sphereRefinement::operator=(const dictionary& d)" + ) << "Entry centre is not specified!" << exit(FatalError); centre_ = vector::zero; } @@ -161,10 +160,10 @@ void sphereRefinement::operator=(const dictionary& d) } else { - FatalErrorIn - ( - "void sphereRefinement::operator=(const dictionary& d)" - ) << "Entry radius is not specified!" << exit(FatalError); + FatalErrorIn + ( + "void sphereRefinement::operator=(const dictionary& d)" + ) << "Entry radius is not specified!" << exit(FatalError); radius_ = -1.0; } } @@ -173,14 +172,14 @@ void sphereRefinement::operator=(const dictionary& d) Ostream& sphereRefinement::operator<<(Ostream& os) const { - os << "name " << name() << nl; - os << "cell size " << cellSize() << nl; - write(os); - return os; + os << "name " << name() << nl; + os << "cell size " << cellSize() << nl; + write(os); + return os; } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + } // End namespace Foam // ************************************************************************* // diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.H index 1e1b0bcfd6eed16c487270b76d6e88cfa1a91c52..99239a252d3960f7b499634bd479f94df8120567 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/objectRefinement/sphereRefinement.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright held by original author - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class sphereRefinement @@ -53,12 +52,12 @@ class sphereRefinement : public objectRefinement { - // Private data - //- centre of the sphere - point centre_; - - //- radius of the sphere - scalar radius_; + // Private data + //- centre of the sphere + point centre_; + + //- radius of the sphere + scalar radius_; public: @@ -82,31 +81,31 @@ public: //- Construct from dictionary sphereRefinement(const word& name, const dictionary& dict); - - //- Construct and return a clone + + //- Construct and return a clone virtual autoPtr<objectRefinement> clone - ( - const sphereRefinement& sr - ) const + ( + const sphereRefinement& sr + ) const { return autoPtr<objectRefinement> - ( - new sphereRefinement - ( - sr.name(), - sr.cellSize(), - sr.centre_, - sr.radius_ - ) - ); + ( + new sphereRefinement + ( + sr.name(), + sr.cellSize(), + sr.centre_, + sr.radius_ + ) + ); } - - // Member Functions - - //- check if a boundBox intersects or is inside the object - bool intersectsObject(const boundBox&) const; - - //- Return as dictionary of entries + + // Member Functions + + //- check if a boundBox intersects or is inside the object + bool intersectsObject(const boundBox&) const; + + //- Return as dictionary of entries dictionary dict(bool ignoreType = false) const; // Write @@ -116,15 +115,15 @@ public: //- Write dictionary void writeDict(Ostream&, bool subDict = true) const; - - // Member Operators + + // Member Operators //- assign from dictionary void operator=(const dictionary&); // IOstream Operators - Ostream& operator<<(Ostream&) const; + Ostream& operator<<(Ostream&) const; }; diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.C b/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.C index e4e56a80c32b3173af03f4f4028458ad9d206a2e..29d9541f193704237c33202a41da5713ea0fad5c 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.C +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.C @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ #include "patchRefinement.H" -#include "triSurface.H" +#include "triSurf.H" #include "Istream.H" #include "demandDrivenData.H" @@ -73,7 +72,7 @@ word patchRefinement::patchName() const return patchName_; } -label patchRefinement::patchInSurface(const triSurface& ts) const +label patchRefinement::patchInSurface(const triSurf& ts) const { forAll(ts.patches(), patchI) if( ts.patches()[patchI].name() == patchName_ ) @@ -81,7 +80,7 @@ label patchRefinement::patchInSurface(const triSurface& ts) const FatalErrorIn ( - "label patchRefinement::patchInSurface(const triSurface& ts) const" + "label patchRefinement::patchInSurface(const triSurf& ts) const" ) << "Patch " << patchName_ << " does not exist in surface " << ts.patches() << exit(FatalError); @@ -98,8 +97,8 @@ scalar patchRefinement::cellSize() const void patchRefinement::operator=(const patchRefinement& pr) { - patchName_ = pr.patchName_; - cellSize_ = pr.cellSize_; + patchName_ = pr.patchName_; + cellSize_ = pr.cellSize_; } Istream& operator>>(Istream& is, patchRefinement& pr) diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.H index c9ca3fc755a84009634e97af6e70b430e4ac154c..494dadca6c4c55688557ff249c3195be0ed4cb32 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinement.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class patchRefinement Description A class used for octree refinement. Refinement of boxes intersected - by a given patch to the prescribed size. + by a given patch to the prescribed size. SourceFiles patchRefinement.C @@ -46,7 +45,7 @@ namespace Foam { // Forward declarations -class triSurface; +class triSurf; class Istream; class Ostream; @@ -82,13 +81,13 @@ public: // Member Functions word patchName() const; - label patchInSurface(const triSurface&) const; + label patchInSurface(const triSurf&) const; scalar cellSize() const; - + // Operators - void operator=(const patchRefinement&); + void operator=(const patchRefinement&); friend Istream& operator>>(Istream&, patchRefinement&); friend Ostream& operator<<(Ostream&, const patchRefinement&); friend bool operator==(const patchRefinement&, const patchRefinement&); diff --git a/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinementList.H b/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinementList.H index 5f929fb62059a801221bb2c15aec5e15d8e0c699..c84dd0c4971c6bc5421b4d4fd75ea440a38310e0 100644 --- a/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinementList.H +++ b/meshLibrary/utilities/octrees/meshOctree/refinementControls/patchRefinement/patchRefinementList.H @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class patchRefinementList Description - A list of patch refinements + A list of patch refinements SourceFiles diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.C b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.C index 174b42f9da53d1a46385985ccdf7c7d9e38cb0f8..bc48ea4e44991836a4af74bd98cd3191f429588f 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.C +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.C @@ -1,34 +1,34 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ #include "surfaceIntersectionsOctree.H" -#include "triSurface.H" +#include "triSurf.H" #include "boundBox.H" +#include "SLList.H" // #define DEBUGSearch @@ -42,7 +42,7 @@ namespace Foam // Construct from surface. Holds reference! surfaceIntersectionsOctree::surfaceIntersectionsOctree ( - const triSurface& surface, + const triSurf& surface, const short maxN, const direction maxL ) @@ -61,12 +61,12 @@ surfaceIntersectionsOctree::surfaceIntersectionsOctree { Info << "Constructing octree" << endl; //- all triangles are within the initial cube - forAll(surface_.localFaces(), faceI) + forAll(surface_, faceI) initialCube_.append(faceI); //- find the smallest edge. Size of the smallest surfaceIntersectionsOctreeCube should not be //- smaller than the smallest edge - const edgeList& edges = surface_.edges(); + const edgeLongList& edges = surface_.edges(); const pointField& points = surface_.points(); scalar dist(GREAT); @@ -74,38 +74,34 @@ surfaceIntersectionsOctree::surfaceIntersectionsOctree if( edges[eI].mag(points) < dist ) dist = edges[eI].mag(points); - (const_cast<triSurface&>(surface_)).clearTopology(); + (const_cast<triSurf&>(surface_)).clearAddressing(); label n = label(initialCube_.bb().mag() / dist); direction k(0); - while( (pow(2, k) < n) && (k < maxL) ) + while( (pow(2, label(k)) < n) && (k < maxL) ) { - k++; + ++k; } //- refine the tree such that there are not more than maxNInCube triangle //- in a single octree cube initialCube_.refineTree(maxN, k); - SLList<surfaceIntersectionsOctreeCube*> leaves; + LongList<surfaceIntersectionsOctreeCube*> leaves; findLeavesForCube(&initialCube_, leaves); - for(SLList<surfaceIntersectionsOctreeCube*>::iterator cIter = leaves.begin(); - cIter != leaves.end(); - ++cIter - ) + forAll(leaves, leafI) { - surfaceIntersectionsOctreeCube& oc = *cIter(); + surfaceIntersectionsOctreeCube& oc = *leaves[leafI]; if( oc.containedElements().size() > 0 ) { - oc.setCubeType(surfaceIntersectionsOctreeCube::DATA); + oc.setCubeType(surfaceIntersectionsOctreeCube::DATA); } else { - const point p = (oc.bb().max() + oc.bb().min()) / 2.0; bool inside(true); const FixedList<point, 8> vrt = oc.vertices(); forAll(vrt, vrtI) @@ -126,15 +122,14 @@ surfaceIntersectionsOctree::surfaceIntersectionsOctree // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // surfaceIntersectionsOctree::~surfaceIntersectionsOctree() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void surfaceIntersectionsOctree::findLeavesForCube ( surfaceIntersectionsOctreeCube* oc, - SLList<surfaceIntersectionsOctreeCube*>& lvs + LongList<surfaceIntersectionsOctreeCube*>& lvs ) const { if( oc->isLeaf() ) @@ -153,14 +148,15 @@ void surfaceIntersectionsOctree::findLeavesForCube } } -surfaceIntersectionsOctreeCube* surfaceIntersectionsOctree::findLeafContainingVertex(const point& p) const +surfaceIntersectionsOctreeCube* +surfaceIntersectionsOctree::findLeafContainingVertex(const point& p) const { # ifdef OCTREE_DEBUG Info << "Finding leaf for vertex " << p << endl; # endif surfaceIntersectionsOctreeCube* oc = - const_cast<surfaceIntersectionsOctreeCube*>(&initialCube_); + const_cast<surfaceIntersectionsOctreeCube*>(&initialCube_); if( !oc->isVertexInside(p) ) { @@ -177,7 +173,8 @@ surfaceIntersectionsOctreeCube* surfaceIntersectionsOctree::findLeafContainingVe if( !oc->isLeaf() ) { //- find a subCube containing the vertex; - const FixedList<surfaceIntersectionsOctreeCube*, 8>& sc = *oc->subCubes(); + const FixedList<surfaceIntersectionsOctreeCube*, 8>& sc = + *oc->subCubes(); bool found(false); @@ -195,8 +192,8 @@ surfaceIntersectionsOctreeCube* surfaceIntersectionsOctree::findLeafContainingVe if( !found ) FatalErrorIn ( - "surfaceIntersectionsOctreeCube* meshOctree::findLeafContainingVertex" - "(const point& p) const" + "surfaceIntersectionsOctreeCube* meshOctree::" + "findLeafContainingVertex(const point& p) const" ) << "Vertex is not found in any subCubes!!" << abort(FatalError); } diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.H b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.H index 9d77dba1595e43452065a3072e5ea82923ce4b60..39f080e2150b373d9a33803c7ae178e0650f20df 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.H +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctree.H @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class surfaceIntersectionsOctree Description - Helper class to search on triSurface. + Helper class to search on triSurf. SourceFiles surfaceIntersectionsOctree.C @@ -36,7 +35,7 @@ SourceFiles #ifndef surfaceIntersectionsOctree_H #define surfaceIntersectionsOctree_H -#include "SLList.H" +#include "LongList.H" #include "boolList.H" #include "pointIndexHit.H" #include "surfaceIntersectionsOctreeCube.H" @@ -47,10 +46,10 @@ namespace Foam { // Class forward declarations -class triSurface; +class triSurf; /*---------------------------------------------------------------------------*\ - Class surfaceIntersectionsOctree Declaration + Class surfaceIntersectionsOctree Declaration \*---------------------------------------------------------------------------*/ class surfaceIntersectionsOctree @@ -58,7 +57,7 @@ class surfaceIntersectionsOctree // Private data //- Reference to surface to work on - const triSurface& surface_; + const triSurf& surface_; //- Root cube of the octree structure surfaceIntersectionsOctreeCube initialCube_; @@ -87,7 +86,11 @@ class surfaceIntersectionsOctree ) const; //- find leaves for cubes - void findLeavesForCube(surfaceIntersectionsOctreeCube*, SLList<surfaceIntersectionsOctreeCube*>&) const; + void findLeavesForCube + ( + surfaceIntersectionsOctreeCube*, + LongList<surfaceIntersectionsOctreeCube*>& + ) const; //- Disallow default bitwise copy construct surfaceIntersectionsOctree(const surfaceIntersectionsOctree&); @@ -100,7 +103,7 @@ public: // Constructors //- Construct from surface. Holds reference to surface! - surfaceIntersectionsOctree(const triSurface&, const short, const direction); + surfaceIntersectionsOctree(const triSurf&, const short, const direction); // Destructor @@ -125,7 +128,7 @@ public: ) const; //- helper function which checks if all normal vectors - //- of the triSurface point outside + //- of the triSurf point outside bool normalOk(const label, bool&) const; //- check if the edge intersects the surface in a manner @@ -138,7 +141,10 @@ public: ) const; //- find a cube containing the vertex - surfaceIntersectionsOctreeCube* findLeafContainingVertex(const point&) const; + surfaceIntersectionsOctreeCube* findLeafContainingVertex + ( + const point& + ) const; }; diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.C b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.C index e389ff72d661f1199c26329e1e764e2dd1863634..e2a946552444af5ed28d78f4876170497600dbf1 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.C +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.C @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ -#include "triSurface.H" +#include "triSurf.H" #include "boundBox.H" #include "surfaceIntersectionsOctreeCube.H" @@ -93,7 +92,7 @@ List< List<point> > surfaceIntersectionsOctreeCube::edges() const helper[0] = cP[0]; helper[1] = cP[4]; edg[8] = helper; - + helper[0] = cP[1]; helper[1] = cP[5]; edg[9] = helper; @@ -115,7 +114,7 @@ List< List<point> > surfaceIntersectionsOctreeCube::edges() const // Construct from surface. Holds reference! surfaceIntersectionsOctreeCube::surfaceIntersectionsOctreeCube ( - const triSurface& surface, + const triSurf& surface, const boundBox& bb, const direction& l ) diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.H b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.H index 1686d84e3e251bd86ca80a207a8ca298c3b43352..6d07d87396d2030aae9eb7ebfd315660f569da34 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.H +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCube.H @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class surfaceIntersectionsOctreeCube Description - A cube for octree needed for evaluating surface intersections + A cube for octree needed for evaluating surface intersections SourceFiles @@ -46,10 +45,10 @@ namespace Foam { // Class forward declarations -class triSurface; +class triSurf; /*---------------------------------------------------------------------------*\ - Class surfaceIntersectionsOctreeCube Declaration + Class surfaceIntersectionsOctreeCube Declaration \*---------------------------------------------------------------------------*/ class surfaceIntersectionsOctreeCube @@ -57,7 +56,7 @@ class surfaceIntersectionsOctreeCube // Private data //- Reference to surface to work on - const triSurface& surface_; + const triSurf& surface_; //- cube level in the octree structure direction level_; @@ -76,7 +75,7 @@ class surfaceIntersectionsOctreeCube //- is the cube outside, data or outside of the domain direction cubeType_; - //- returns cube's edges + //- returns cube's edges List< List<point> > edges() const; //- Disallow default bitwise copy construct @@ -89,13 +88,13 @@ public: // Constructors //- Construct from surface. Holds reference to surface! - surfaceIntersectionsOctreeCube(const triSurface&, const boundBox&, const direction&); + surfaceIntersectionsOctreeCube(const triSurf&, const boundBox&, const direction&); // Destructor ~surfaceIntersectionsOctreeCube(); - // Enumerators + // Enumerators enum cubeTypes { OUTSIDE = 0, @@ -109,20 +108,20 @@ public: //- is cube a leaf inline bool isLeaf() const; - - //- return and set cube type - direction cubeType() const - { - return cubeType_; - }; - void setCubeType(const direction t) - { - cubeType_ = t; - } + + //- return and set cube type + direction cubeType() const + { + return cubeType_; + }; + void setCubeType(const direction t) + { + cubeType_ = t; + } //- vertices FixedList<point, 8> vertices() const; - + //- sub cubes inline FixedList<surfaceIntersectionsOctreeCube*, 8>* subCubes() const; diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeI.H b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeI.H index c98ddd083fc64804d5c58ecb00854af248cd7787..87f7ae9e44e8fe2248707a4232df4e395458bc5e 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeI.H +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeIntersections.C b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeIntersections.C index 0a47f40a153848602d554ce52670c836ac00bfa1..4643211cbf7df793018ab74240b8f37d0b315e73 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeIntersections.C +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeIntersections.C @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ -#include "triSurface.H" +#include "triSurf.H" #include "surfaceIntersectionsOctreeCube.H" #include "helperFunctions.H" @@ -42,7 +41,7 @@ namespace Foam bool surfaceIntersectionsOctreeCube::intersectsTriangle(const label tI) const { const pointField& points = surface_.points(); - const labelledTri& ltri = surface_.localFaces()[tI]; + const labelledTri& ltri = surface_[tI]; point max_(-GREAT, -GREAT, -GREAT); point min_(GREAT, GREAT, GREAT); @@ -51,7 +50,7 @@ bool surfaceIntersectionsOctreeCube::intersectsTriangle(const label tI) const max_ = Foam::max(points[ltri[pI]], max_); min_ = Foam::min(points[ltri[pI]], min_); } - + min_ -= point(SMALL, SMALL, SMALL); max_ += point(SMALL, SMALL, SMALL); @@ -198,13 +197,15 @@ void surfaceIntersectionsOctreeCube::intersectionCandidates Info << "Cube " << cubeBox_ << " contains elements " << containedElements_ << endl; # endif - point intersection; + //- add elements within the cube for(SLList<label>::const_iterator eIter = containedElements_.begin(); eIter != containedElements_.end(); ++eIter ) { + point intersection; + if( help::triLineIntersection ( @@ -215,13 +216,15 @@ void surfaceIntersectionsOctreeCube::intersectionCandidates intersection ) ) - cp.append(pointIndexHit(true,intersection, eIter())); + cp.append(pointIndexHit(true, intersection, eIter())); } - + //- check subCubes if there are any if( subCubesPtr_ ) { - const FixedList<surfaceIntersectionsOctreeCube*, 8>& subCubes_ = *subCubesPtr_; + const FixedList<surfaceIntersectionsOctreeCube*, 8>& subCubes_ = + *subCubesPtr_; + forAll(subCubes_, cubeI) subCubes_[cubeI]->intersectionCandidates(cp, s, e); } diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeRefine.C b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeRefine.C index 2190bc445ddf80df93f87bb0e6e748d9f7b8c226..3bb7cd10441f9551a1e4d74896455e1115b6955b 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeRefine.C +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeCube/surfaceIntersectionsOctreeCubeRefine.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeIntersections.C b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeIntersections.C index a95cb0c58a007f607863bb3eab8936dc3e82f974..3e24903ec6e2f169a395ac9157502e0b18726735 100644 --- a/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeIntersections.C +++ b/meshLibrary/utilities/octrees/surfaceIntersectionsOctree/surfaceIntersectionsOctreeIntersections.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,7 +30,7 @@ Description #include "boundBox.H" #include "DynList.H" #include "helperFunctions.H" -//#include "DimSpace.H" +#include "SLList.H" // #define DEBUGSearch @@ -64,7 +63,7 @@ bool surfaceIntersectionsOctree::checkPointIntersections //- check visibility of other triangles sharing the intersected //- vertex - const labelList& pp = surface_.pointFaces()[ltri[pI]]; + const constRow pp = surface_.pointFacets()[ltri[pI]]; forAll(pp, nI) { @@ -107,9 +106,9 @@ bool surfaceIntersectionsOctree::checkEdgeIntersections if( (d > -SMALL) && (d < SMALL) ) { - const label edgeI = surface_.faceEdges()[ph.index()][eI]; + const label edgeI = surface_.facetEdges()(ph.index(), eI); - const labelList& ef = surface_.edgeFaces()[edgeI]; + const constRow ef = surface_.edgeFacets()[edgeI]; if( ef.size() != 2 ) FatalErrorIn @@ -152,7 +151,7 @@ void surfaceIntersectionsOctree::checkIntersections Info << "Intersection candidates are " << intersections << endl; short nIntersections(0); - point intersection; + point intersection(vector::zero); SLList<label> ints; forAll(surface_, faceI) @@ -170,7 +169,7 @@ void surfaceIntersectionsOctree::checkIntersections ints.append(faceI); Info << "Intersection " << nIntersections << " is " << intersection << endl; - nIntersections++; + ++nIntersections; } Info << "nIntersections " << nIntersections << endl; @@ -195,9 +194,10 @@ void surfaceIntersectionsOctree::checkIntersections if( !found ) FatalErrorIn ( - "bool surfaceIntersectionsOctree::isPointInside(const point& p) const" + "bool surfaceIntersectionsOctree::isPointInside" + "(const point&) const" ) << "Intersection " << pIter() << " was not found by the octree!" - << abort(FatalError); + << abort(FatalError); } } @@ -254,7 +254,7 @@ bool surfaceIntersectionsOctree::isPointInside(const point& p) const else { pointIndexHit nearest(false, p, -1); - + scalar dist(GREAT); for(SLList<pointIndexHit>::const_iterator iIter = intersections.begin(); @@ -298,7 +298,11 @@ bool surfaceIntersectionsOctree::isPointInside(const point& p) const } } -pointIndexHit surfaceIntersectionsOctree::intersection(const point& s, const point& e) const +pointIndexHit surfaceIntersectionsOctree::intersection +( + const point& s, + const point& e +) const { SLList<pointIndexHit> intersections; initialCube_.intersectionCandidates(intersections, s, e); @@ -338,7 +342,7 @@ pointIndexHit surfaceIntersectionsOctree::intersection(const point& s, const poi << exit(FatalError); pointIndexHit nearest(false, s, -1); - + scalar dist(GREAT); for(SLList<pointIndexHit>::const_iterator iIter = intersections.begin(); @@ -348,7 +352,7 @@ pointIndexHit surfaceIntersectionsOctree::intersection(const point& s, const poi if( (mag(iIter().rawPoint() - s) < dist) && checkPointIntersections(s, iIter()) && - checkEdgeIntersections(s, iIter()) + checkEdgeIntersections(s, iIter()) ) { dist = mag(iIter().rawPoint() - s); @@ -362,7 +366,7 @@ pointIndexHit surfaceIntersectionsOctree::intersection(const point& s, const poi if( !nearest.hit() || nearest.index() < 0 || - nearest.index() >= surface_.localFaces().size() + nearest.index() >= surface_.size() ) { Info << "intersections " << intersections << endl; @@ -437,7 +441,7 @@ void surfaceIntersectionsOctree::intersection iIter != intersections.end(); ++iIter ) - if( + if( checkPointIntersections(s, iIter()) && checkEdgeIntersections(s, iIter()) ) @@ -460,7 +464,7 @@ void surfaceIntersectionsOctree::intersection if( !hs.hit() || hs.index() < 0 || - hs.index() >= surface_.localFaces().size() + hs.index() >= surface_.size() ) { Info << "intersections " << intersections << endl; @@ -475,11 +479,11 @@ void surfaceIntersectionsOctree::intersection ) << "Intersection is invalid!!" << exit(FatalError); } - + if( !he.hit() || he.index() < 0 || - he.index() >= surface_.localFaces().size() + he.index() >= surface_.size() ) { Info << "intersections " << intersections << endl; @@ -544,7 +548,7 @@ bool surfaceIntersectionsOctree::normalOk(const label faceI, bool& sure) const { e = i; set = true; - } + } } if( !set ) { @@ -633,7 +637,7 @@ bool surfaceIntersectionsOctree::normalOk(const label faceI, bool& sure) const (mag(hits[hitI].rawPoint() - hits[hitJ].rawPoint()) < SMALL) ) found = true; - + if( !checkEdgeIntersections(s, hits[hitI]) || !checkPointIntersections(s, hits[hitI]) @@ -646,8 +650,8 @@ bool surfaceIntersectionsOctree::normalOk(const label faceI, bool& sure) const { sure = true; } - - + + if( !found ) intersections.append(hits[hitI]); } @@ -694,7 +698,7 @@ bool surfaceIntersectionsOctree::validIntersection if( store ) hits.append(pIter()); } - + intersections.clear(); forAll(hits, hI) intersections.append(hits[hI]); @@ -715,7 +719,7 @@ bool surfaceIntersectionsOctree::validIntersection { vector lv = n ^ edges[eI].vec(points); lv /= mag(lv); - + vector pv = pIter().hitPoint() - points[ltri[eI]]; if( mag(pv) < SMALL ) { @@ -723,13 +727,13 @@ bool surfaceIntersectionsOctree::validIntersection return false; } pv /= mag(pv); - + const scalar d = pv & lv; - + if( (d > -SMALL) && (d < SMALL) ) { - const labelList& fe = surface_.faceEdges()[pIter().index()]; - const labelList& ef = surface_.edgeFaces()[fe[eI]]; + const constRow fe = surface_.facetEdges()[pIter().index()]; + const constRow ef = surface_.edgeFacets()[fe[eI]]; label neighbourTri(-1); if( ef[0] == pIter().index() ) { diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.C index b7589f181809ef0c89650986dc9e21d1a2051afa..394117810b8622b7644054697a01f548c38f4467 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,20 +38,20 @@ Description namespace Foam { - + // * * * * * * * * Private member functions * * * * * * * * * * * * * * * * * // - + const meshSurfaceEngine& meshOptimizer::meshSurface() const { - if( !msePtr_ ) - msePtr_ = new meshSurfaceEngine(mesh_); - - return *msePtr_; + if( !msePtr_ ) + msePtr_ = new meshSurfaceEngine(mesh_); + + return *msePtr_; } void meshOptimizer::clearSurface() { - deleteDemandDrivenData(msePtr_); + deleteDemandDrivenData(msePtr_); } label meshOptimizer::findBadFaces @@ -62,7 +61,7 @@ label meshOptimizer::findBadFaces ) const { badFaces.clear(); - + polyMeshGenChecks::checkFacePyramids ( mesh_, @@ -71,7 +70,7 @@ label meshOptimizer::findBadFaces &badFaces, &changedFace ); - + polyMeshGenChecks::checkFaceFlatness ( mesh_, @@ -80,7 +79,7 @@ label meshOptimizer::findBadFaces &badFaces, &changedFace ); - + polyMeshGenChecks::checkCellPartTetrahedra ( mesh_, @@ -89,7 +88,7 @@ label meshOptimizer::findBadFaces &badFaces, &changedFace ); - + polyMeshGenChecks::checkFaceAreas ( mesh_, @@ -98,9 +97,9 @@ label meshOptimizer::findBadFaces &badFaces, &changedFace ); - + const label nBadFaces = returnReduce(badFaces.size(), sumOp<label>()); - + return nBadFaces; } @@ -111,7 +110,7 @@ label meshOptimizer::findLowQualityFaces ) const { badFaces.clear(); - + polyMeshGenChecks::checkFaceDotProduct ( mesh_, @@ -119,7 +118,7 @@ label meshOptimizer::findLowQualityFaces 70.0, &badFaces ); - + polyMeshGenChecks::checkFaceSkewness ( mesh_, @@ -127,9 +126,9 @@ label meshOptimizer::findLowQualityFaces 2.0, &badFaces ); - + const label nBadFaces = returnReduce(badFaces.size(), sumOp<label>()); - + return nBadFaces; } @@ -138,31 +137,31 @@ label meshOptimizer::findLowQualityFaces // Construct from mesh meshOptimizer::meshOptimizer(polyMeshGen& mesh) : - mesh_(mesh), + mesh_(mesh), vertexLocation_(mesh.points().size(), INSIDE), - msePtr_(NULL) + msePtr_(NULL) { - const meshSurfaceEngine& mse = meshSurface(); - const labelList& bPoints = mse.boundaryPoints(); - + const meshSurfaceEngine& mse = meshSurface(); + const labelList& bPoints = mse.boundaryPoints(); + //- mark boundary vertices - forAll(bPoints, bpI) + forAll(bPoints, bpI) vertexLocation_[bPoints[bpI]] = BOUNDARY; - + //- mark edge vertices meshSurfacePartitioner mPart(mse); - forAllConstIter(labelHashSet, mPart.edgeNodes(), it) + forAllConstIter(labelHashSet, mPart.edgePoints(), it) vertexLocation_[bPoints[it.key()]] = EDGE; - + //- mark corner vertices forAllConstIter(labelHashSet, mPart.corners(), it) vertexLocation_[bPoints[it.key()]] = CORNER; - + if( Pstream::parRun() ) { const polyMeshGenAddressing& addresing = mesh_.addressingData(); const VRWGraph& pointAtProcs = addresing.pointAtProcs(); - + forAll(pointAtProcs, pointI) if( pointAtProcs.sizeOfRow(pointI) != 0 ) vertexLocation_[pointI] |= PARALLELBOUNDARY; @@ -173,7 +172,7 @@ meshOptimizer::meshOptimizer(polyMeshGen& mesh) meshOptimizer::~meshOptimizer() { - clearSurface(); + clearSurface(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.H b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.H index d899bf7e8002dd1f546a2f83db063843862d7edd..4190da217de98747a0adb28f2934921117a7d7e0 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.H +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizer.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshOptimizer @@ -63,18 +62,18 @@ class meshOptimizer { // Private data //- reference to the mesh - polyMeshGen& mesh_; - - //- location of vertex (internal, boundary, edge, corner) + polyMeshGen& mesh_; + + //- location of vertex (internal, boundary, edge, corner) List<direction> vertexLocation_; - - //- mesh surface - mutable meshSurfaceEngine* msePtr_; + + //- mesh surface + mutable meshSurfaceEngine* msePtr_; // Private member functions - //- return mesh surface - const meshSurfaceEngine& meshSurface() const; - void clearSurface(); + //- return mesh surface + const meshSurfaceEngine& meshSurface() const; + void clearSurface(); //- find problematic faces label findBadFaces(labelHashSet&, const boolList&) const; @@ -94,36 +93,36 @@ class meshOptimizer // Private member functions //- smooth the node using the laplacian smoother //- new position is the average of the neighbouring vertices - void laplacian(const labelListPMG&, const label); - void laplacianSurface(const labelListPMG&, const label); + void laplacian(const labelLongList&, const label); + void laplacianSurface(const labelLongList&, const label); void laplacianParallel ( - const labelListPMG& procPoints, + const labelLongList& procPoints, const bool smoothOnlySurfaceNodes = false ); //- smooth the node using the laplacian smoother //- new position is the average of the centres of faces attached //- to the vertex - void laplacianPC(const labelListPMG&, const label); - void laplacianPCParallel(const labelListPMG& procPoints); + void laplacianPC(const labelLongList&, const label); + void laplacianPCParallel(const labelLongList& procPoints); //- smooth the node using the laplacian smoother //- new position is the average of the centres of faces attached //- to the vertex - void laplacianWPC(const labelListPMG&, const label); - void laplacianWPCParallel(const labelListPMG& procPoints); + void laplacianWPC(const labelLongList&, const label); + void laplacianWPCParallel(const labelLongList& procPoints); //- update geometry after smoothing - void updateMeshGeometry(const labelListPMG& smoothPoints); + void updateMeshGeometry(const labelLongList& smoothPoints); //- Disallow default bitwise copy construct laplaceSmoother(const laplaceSmoother&); //- Disallow default bitwise assignment void operator=(const laplaceSmoother&); - + public: // Constructor @@ -176,16 +175,16 @@ class meshOptimizer //- Disallow default bitwise assignment void operator=(const meshOptimizer&); - - // enumerators - enum vertexType_ - { - INSIDE = 1, - BOUNDARY = 2, - EDGE = 4, - CORNER = 8, + + // enumerators + enum vertexType_ + { + INSIDE = 1, + BOUNDARY = 2, + EDGE = 4, + CORNER = 8, PARALLELBOUNDARY = 16 - }; + }; public: @@ -203,15 +202,15 @@ public: //- smooth surface vertices void optimizeSurface(const meshOctree&); - //- performs mesh untangling based on detected negative normals - void untangleMeshFV(); + //- performs mesh untangling based on detected negative normals + void untangleMeshFV(); //- performs mesh optimisation for faces with high non-orthogonality //- and skewness void optimizeLowQualityFaces(); - //- final optimisation - void optimizeMeshFV(); + //- final optimisation + void optimizeMeshFV(); }; diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePoint.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePoint.C index 0c12907ca279af9777ce2af5c2c83afc2d47a862..595bc201ba3cc5df38c88416329191b85c9b2096 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePoint.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePoint.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,7 +30,9 @@ Description #include "polyMeshGenAddressing.H" #include "meshSurfaceEngine.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGSmooth @@ -44,7 +45,7 @@ namespace Foam void meshOptimizer::laplaceSmoother::laplacian ( - const labelListPMG& smoothPoints, + const labelLongList& smoothPoints, const label nIterations ) { @@ -53,166 +54,174 @@ void meshOptimizer::laplaceSmoother::laplacian for(label iterationI=0;iterationI<nIterations;++iterationI) { - labelListPMG procPoints; - + labelLongList procPoints; + forAll(smoothPoints, i) { const label pointI = smoothPoints[i]; - + if( vertexLocation_[pointI] & PARALLELBOUNDARY ) { procPoints.append(pointI); - + continue; } - + vector newP(vector::zero); - + const label nPointPoints = pPoints.sizeOfRow(pointI); - + if( nPointPoints == 0 ) return; - + for(label pI=0;pI<nPointPoints;++pI) newP += points[pPoints(pointI, pI)]; - + newP /= pPoints.sizeOfRow(pointI); points[pointI] = newP; } - + laplacianParallel(procPoints, false); } - + updateMeshGeometry(smoothPoints); } void meshOptimizer::laplaceSmoother::laplacianSurface ( - const labelListPMG& smoothPoints, + const labelLongList& smoothPoints, const label nIterations ) { - const VRWGraph& pPoints = mesh_.addressingData().pointPoints(); + const VRWGraph& pPoints = mesh_.addressingData().pointPoints(); pointFieldPMG& points = mesh_.points(); for(label iterationI=0;iterationI<nIterations;++iterationI) { - labelListPMG procPoints; - + labelLongList procPoints; + forAll(smoothPoints, i) { const label pointI = smoothPoints[i]; - + if( vertexLocation_[pointI] & PARALLELBOUNDARY ) { procPoints.append(pointI); - + continue; } - + vector newP(vector::zero); - + label counter(0); forAllRow(pPoints, pointI, pI) { const label pLabel = pPoints(pointI, pI); if( vertexLocation_[pLabel] & INSIDE ) continue; - + newP += points[pLabel]; ++counter; } - + if( counter != 0 ) { newP /= counter; points[pointI] = newP; } } - + laplacianParallel(smoothPoints, true); } - + updateMeshGeometry(smoothPoints); } void meshOptimizer::laplaceSmoother::laplacianPC ( - const labelListPMG& smoothPoints, + const labelLongList& smoothPoints, const label nIterations ) { const VRWGraph& pointCells = mesh_.addressingData().pointCells(); const vectorField& centres = mesh_.addressingData().cellCentres(); pointFieldPMG& points = mesh_.points(); - + for(label iterationI=0;iterationI<nIterations;++iterationI) { - labelListPMG procPoints; - + labelLongList procPoints; + + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 20) + # endif forAll(smoothPoints, i) { const label pointI = smoothPoints[i]; - + if( pointCells.sizeOfRow(pointI) == 0 ) continue; - + if( vertexLocation_[pointI] & PARALLELBOUNDARY ) { + # ifdef USE_OMP # pragma omp critical + # endif procPoints.append(pointI); - + continue; } - + point newP(vector::zero); forAllRow(pointCells, pointI, pcI) newP += centres[pointCells(pointI, pcI)]; - + newP /= pointCells.sizeOfRow(pointI); - + points[pointI] = newP; } - + laplacianPCParallel(procPoints); - + updateMeshGeometry(smoothPoints); } } void meshOptimizer::laplaceSmoother::laplacianWPC ( - const labelListPMG& smoothPoints, + const labelLongList& smoothPoints, const label nIterations ) { const VRWGraph& pointCells = mesh_.addressingData().pointCells(); const vectorField& centres = mesh_.addressingData().cellCentres(); const scalarField& volumes = mesh_.addressingData().cellVolumes(); - + pointFieldPMG& points = mesh_.points(); - + for(label iterationI=0;iterationI<nIterations;++iterationI) { - labelListPMG procPoints; - + labelLongList procPoints; + + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 20) + # endif forAll(smoothPoints, i) { const label pointI = smoothPoints[i]; - + if( pointCells.sizeOfRow(pointI) == 0 ) continue; - + if( vertexLocation_[pointI] & PARALLELBOUNDARY ) { + # ifdef USE_OMP # pragma omp critical + # endif procPoints.append(pointI); - + continue; } - + point newP(vector::zero); scalar sumWeights(0.0); forAllRow(pointCells, pointI, pcI) @@ -222,83 +231,85 @@ void meshOptimizer::laplaceSmoother::laplacianWPC newP += w * centres[cellI]; sumWeights += w; } - + newP /= sumWeights; points[pointI] = newP; } - + laplacianWPCParallel(procPoints); - + updateMeshGeometry(smoothPoints); } } void meshOptimizer::laplaceSmoother::updateMeshGeometry ( - const labelListPMG& smoothPoints + const labelLongList& smoothPoints ) { const cellListPMG& cells = mesh_.cells(); const VRWGraph& pointCells = mesh_.addressingData().pointCells(); - + boolList chF(mesh_.faces().size(), false); - + + # ifdef USE_OMP # pragma omp parallel for if( smoothPoints.size() > 100 ) \ schedule(dynamic, 20) + # endif forAll(smoothPoints, i) { const label pointI = smoothPoints[i]; - + forAllRow(pointCells, pointI, pcI) { const cell& c = cells[pointCells(pointI, pcI)]; - + forAll(c, fI) chF[c[fI]] = true; } } - + //- make sure that neighbouring processors get the same information - const PtrList<writeProcessorPatch>& pBnd = mesh_.procBoundaries(); + const PtrList<processorBoundaryPatch>& pBnd = mesh_.procBoundaries(); forAll(pBnd, patchI) { const label start = pBnd[patchI].patchStart(); const label size = pBnd[patchI].patchSize(); - - labelListPMG sendData; + + labelLongList sendData; for(label faceI=0;faceI<size;++faceI) { if( chF[start+faceI] ) sendData.append(faceI); } - + OPstream toOtherProc ( Pstream::blocking, pBnd[patchI].neiProcNo(), sendData.byteSize() ); - + toOtherProc << sendData; } - + forAll(pBnd, patchI) { labelList receivedData; - + IPstream fromOtherProc ( Pstream::blocking, pBnd[patchI].neiProcNo() ); - + fromOtherProc >> receivedData; - + const label start = pBnd[patchI].patchStart(); forAll(receivedData, i) chF[start+receivedData[i]] = true; } - + //- update geometry information const_cast<polyMeshGenAddressing&> ( @@ -329,12 +340,12 @@ meshOptimizer::laplaceSmoother::~laplaceSmoother() void meshOptimizer::laplaceSmoother::optimizeLaplacian(const label nIterations) { - labelListPMG smoothPoints; - + labelLongList smoothPoints; + forAll(vertexLocation_, pointI) if( vertexLocation_[pointI] & INSIDE ) smoothPoints.append(pointI); - + laplacian(smoothPoints, nIterations); } @@ -361,12 +372,12 @@ void meshOptimizer::laplaceSmoother::optimizeLaplacianPC const label nIterations ) { - labelListPMG smoothPoints; - + labelLongList smoothPoints; + forAll(vertexLocation_, pointI) if( vertexLocation_[pointI] & INSIDE ) smoothPoints.append(pointI); - + laplacianPC(smoothPoints, nIterations); } @@ -384,12 +395,12 @@ void meshOptimizer::laplaceSmoother::optimizeLaplacianWPC const label nIterations ) { - labelListPMG smoothPoints; - + labelLongList smoothPoints; + forAll(vertexLocation_, pointI) if( vertexLocation_[pointI] & INSIDE ) smoothPoints.append(pointI); - + laplacianWPC(smoothPoints, nIterations); } diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePointParallel.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePointParallel.C index 3dcef4d66329ce15b6bf3643a287ebb6acd7f0f6..efe18c04ddaeb4fb4288ecedcfe87f72def6385c 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePointParallel.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizePointParallel.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -47,7 +46,7 @@ namespace Foam void meshOptimizer::laplaceSmoother::laplacianParallel ( - const labelListPMG& procPoints, + const labelLongList& procPoints, const bool smoothOnlySurfaceNodes ) { @@ -62,47 +61,47 @@ void meshOptimizer::laplaceSmoother::laplacianParallel pointFieldPMG& points = mesh_.points(); //- exchange data between processors - const labelListPMG& globalPointLabel = addressing.globalPointLabel(); + const labelLongList& globalPointLabel = addressing.globalPointLabel(); const VRWGraph& pointAtProcs = addressing.pointAtProcs(); const Map<label>& globalToLocal = addressing.globalToLocalPointAddressing(); //- create storage for the data - std::map<label, labelledPoint> localData; + std::map<label, labelledPoint> localData; //- create data which shall be exchanged with other processors std::map<label, LongList<refLabelledPoint> > exchangeData; forAll(procPoints, pI) { - const label pointI = procPoints[pI]; - - localData.insert(std::make_pair(pointI, labelledPoint(0,vector::zero))); - labelledPoint& lpd = localData[pointI]; - + const label pointI = procPoints[pI]; + + localData.insert(std::make_pair(pointI, labelledPoint(0,vector::zero))); + labelledPoint& lpd = localData[pointI]; + forAllRow(pPoints, pointI, ppI) { const label nei = pPoints(pointI, ppI); if( smoothOnlySurfaceNodes && (vertexLocation_[nei] & INSIDE) ) continue; - - if( pointAtProcs.sizeOfRow(nei) != 0 ) - { - label pMin(Pstream::nProcs()); - forAllRow(pointAtProcs, nei, procI) - { - const label procJ = pointAtProcs(nei, procI); - if( (procJ < pMin) && pointAtProcs.contains(pointI, procJ) ) - pMin = procJ; - } - - if( pMin != Pstream::myProcNo() ) - continue; - } - - ++lpd.pointLabel(); - lpd.coordinates() += points[nei]; + + if( pointAtProcs.sizeOfRow(nei) != 0 ) + { + label pMin(Pstream::nProcs()); + forAllRow(pointAtProcs, nei, procI) + { + const label procJ = pointAtProcs(nei, procI); + if( (procJ < pMin) && pointAtProcs.contains(pointI, procJ) ) + pMin = procJ; + } + + if( pMin != Pstream::myProcNo() ) + continue; + } + + ++lpd.pointLabel(); + lpd.coordinates() += points[nei]; } - + forAllRow(pointAtProcs, pointI, procI) { const label neiProc = pointAtProcs(pointI, procI); @@ -118,8 +117,8 @@ void meshOptimizer::laplaceSmoother::laplacianParallel } //- add data to the list which will be sent to other processor - LongList<refLabelledPoint>& dts = exchangeData[neiProc]; - dts.append(refLabelledPoint(globalPointLabel[pointI], lpd)); + LongList<refLabelledPoint>& dts = exchangeData[neiProc]; + dts.append(refLabelledPoint(globalPointLabel[pointI], lpd)); } } @@ -152,32 +151,32 @@ void meshOptimizer::laplaceSmoother::laplacianParallel points[pointI] = newP; } } - - # ifdef DEBUGSmooth - //- check - std::map<label, LongList<labelledPoint> > check; - forAll(procPoints, pI) - { - const label pointI = procPoints[pI]; - - forAllRow(pointAtProcs, pointI, i) - { - const label procI = pointAtProcs(pointI, i); - if( procI == Pstream::myProcNo() ) - continue; - if( check.find(procI) == check.end() ) - { - check.insert(std::make_pair(procI, LongList<labelledPoint>())); - } - - LongList<labelledPoint>& data = check[procI]; - data.append(labelledPoint(globalPointLabel[pointI],points[pointI])); - } - } - + + # ifdef DEBUGSmooth + //- check + std::map<label, LongList<labelledPoint> > check; + forAll(procPoints, pI) + { + const label pointI = procPoints[pI]; + + forAllRow(pointAtProcs, pointI, i) + { + const label procI = pointAtProcs(pointI, i); + if( procI == Pstream::myProcNo() ) + continue; + if( check.find(procI) == check.end() ) + { + check.insert(std::make_pair(procI, LongList<labelledPoint>())); + } + + LongList<labelledPoint>& data = check[procI]; + data.append(labelledPoint(globalPointLabel[pointI],points[pointI])); + } + } + LongList<labelledPoint> data; help::exchangeMap(check, data); - + forAll(data, i) { const label pointI = globalToLocal[data[i].pointLabel()]; @@ -186,12 +185,12 @@ void meshOptimizer::laplaceSmoother::laplacianParallel Pout << "Crap " << globalPointLabel[pointI] << " coordinates " << points[pointI] << " point there " << data[i] << endl; } - # endif + # endif } void meshOptimizer::laplaceSmoother::laplacianPCParallel ( - const labelListPMG& procPoints + const labelLongList& procPoints ) { if( !Pstream::parRun() ) @@ -206,30 +205,30 @@ void meshOptimizer::laplaceSmoother::laplacianPCParallel pointFieldPMG& points = mesh_.points(); //- exchange data between processors - const labelListPMG& globalPointLabel = addressing.globalPointLabel(); + const labelLongList& globalPointLabel = addressing.globalPointLabel(); const VRWGraph& pointAtProcs = addressing.pointAtProcs(); const Map<label>& globalToLocal = addressing.globalToLocalPointAddressing(); //- create storage for the data - std::map<label, labelledPoint> localData; + std::map<label, labelledPoint> localData; //- create data which shall be exchanged with other processors std::map<label, LongList<refLabelledPoint> > exchangeData; forAll(procPoints, pI) { - const label pointI = procPoints[pI]; - - localData.insert(std::make_pair(pointI, labelledPoint(0,vector::zero))); - labelledPoint& lpd = localData[pointI]; - + const label pointI = procPoints[pI]; + + localData.insert(std::make_pair(pointI, labelledPoint(0,vector::zero))); + labelledPoint& lpd = localData[pointI]; + forAllRow(pCells, pointI, pcI) { const label cellI = pCells(pointI, pcI); - - ++lpd.pointLabel(); - lpd.coordinates() += centres[cellI]; + + ++lpd.pointLabel(); + lpd.coordinates() += centres[cellI]; } - + forAllRow(pointAtProcs, pointI, procI) { const label neiProc = pointAtProcs(pointI, procI); @@ -245,8 +244,8 @@ void meshOptimizer::laplaceSmoother::laplacianPCParallel } //- add data to the list which will be sent to other processor - LongList<refLabelledPoint>& dts = exchangeData[neiProc]; - dts.append(refLabelledPoint(globalPointLabel[pointI], lpd)); + LongList<refLabelledPoint>& dts = exchangeData[neiProc]; + dts.append(refLabelledPoint(globalPointLabel[pointI], lpd)); } } @@ -279,32 +278,32 @@ void meshOptimizer::laplaceSmoother::laplacianPCParallel points[pointI] = newP; } } - - # ifdef DEBUGSmooth - //- check - std::map<label, LongList<labelledPoint> > check; - forAll(procPoints, pI) - { - const label pointI = procPoints[pI]; - - forAllRow(pointAtProcs, pointI, i) - { - const label procI = pointAtProcs(pointI, i); - if( procI == Pstream::myProcNo() ) - continue; - if( check.find(procI) == check.end() ) - { - check.insert(std::make_pair(procI, LongList<labelledPoint>())); - } - - LongList<labelledPoint>& data = check[procI]; - data.append(labelledPoint(globalPointLabel[pointI],points[pointI])); - } - } - + + # ifdef DEBUGSmooth + //- check + std::map<label, LongList<labelledPoint> > check; + forAll(procPoints, pI) + { + const label pointI = procPoints[pI]; + + forAllRow(pointAtProcs, pointI, i) + { + const label procI = pointAtProcs(pointI, i); + if( procI == Pstream::myProcNo() ) + continue; + if( check.find(procI) == check.end() ) + { + check.insert(std::make_pair(procI, LongList<labelledPoint>())); + } + + LongList<labelledPoint>& data = check[procI]; + data.append(labelledPoint(globalPointLabel[pointI],points[pointI])); + } + } + LongList<labelledPoint> data; help::exchangeMap(check, data); - + forAll(data, i) { const label pointI = globalToLocal[data[i].pointLabel()]; @@ -313,12 +312,12 @@ void meshOptimizer::laplaceSmoother::laplacianPCParallel Pout << "Crap " << globalPointLabel[pointI] << " coordinates " << points[pointI] << " point there " << data[i] << endl; } - # endif + # endif } void meshOptimizer::laplaceSmoother::laplacianWPCParallel ( - const labelListPMG& procPoints + const labelLongList& procPoints ) { if( !Pstream::parRun() ) @@ -334,20 +333,20 @@ void meshOptimizer::laplaceSmoother::laplacianWPCParallel pointFieldPMG& points = mesh_.points(); //- exchange data between processors - const labelListPMG& globalPointLabel = addressing.globalPointLabel(); + const labelLongList& globalPointLabel = addressing.globalPointLabel(); const VRWGraph& pointAtProcs = addressing.pointAtProcs(); const Map<label>& globalToLocal = addressing.globalToLocalPointAddressing(); //- create storage for the data - std::map<label, labelledPointScalar> localData; + std::map<label, labelledPointScalar> localData; //- create data which shall be exchanged with other processors std::map<label, LongList<labelledPointScalar> > exchangeData; forAll(procPoints, pI) { - const label pointI = procPoints[pI]; - - localData.insert + const label pointI = procPoints[pI]; + + localData.insert ( std::make_pair ( @@ -355,17 +354,17 @@ void meshOptimizer::laplaceSmoother::laplacianWPCParallel labelledPointScalar(globalPointLabel[pointI], vector::zero, 0.) ) ); - labelledPointScalar& lps = localData[pointI]; - + labelledPointScalar& lps = localData[pointI]; + forAllRow(pCells, pointI, pcI) { const label cellI = pCells(pointI, pcI); - - const scalar w = Foam::max(volumes[cellI], VSMALL); - lps.coordinates() += w * centres[cellI]; + + const scalar w = Foam::max(volumes[cellI], VSMALL); + lps.coordinates() += w * centres[cellI]; lps.scalarValue() += w; } - + forAllRow(pointAtProcs, pointI, procI) { const label neiProc = pointAtProcs(pointI, procI); @@ -381,8 +380,8 @@ void meshOptimizer::laplaceSmoother::laplacianWPCParallel } //- add data to the list which will be sent to other processor - LongList<labelledPointScalar>& dts = exchangeData[neiProc]; - dts.append(lps); + LongList<labelledPointScalar>& dts = exchangeData[neiProc]; + dts.append(lps); } } @@ -415,32 +414,32 @@ void meshOptimizer::laplaceSmoother::laplacianWPCParallel points[pointI] = newP; } } - - # ifdef DEBUGSmooth - //- check - std::map<label, LongList<labelledPoint> > check; - forAll(procPoints, pI) - { - const label pointI = procPoints[pI]; - - forAllRow(pointAtProcs, pointI, i) - { - const label procI = pointAtProcs(pointI, i); - if( procI == Pstream::myProcNo() ) - continue; - if( check.find(procI) == check.end() ) - { - check.insert(std::make_pair(procI, LongList<labelledPoint>())); - } - - LongList<labelledPoint>& data = check[procI]; - data.append(labelledPoint(globalPointLabel[pointI],points[pointI])); - } - } - + + # ifdef DEBUGSmooth + //- check + std::map<label, LongList<labelledPoint> > check; + forAll(procPoints, pI) + { + const label pointI = procPoints[pI]; + + forAllRow(pointAtProcs, pointI, i) + { + const label procI = pointAtProcs(pointI, i); + if( procI == Pstream::myProcNo() ) + continue; + if( check.find(procI) == check.end() ) + { + check.insert(std::make_pair(procI, LongList<labelledPoint>())); + } + + LongList<labelledPoint>& data = check[procI]; + data.append(labelledPoint(globalPointLabel[pointI],points[pointI])); + } + } + LongList<labelledPoint> data; help::exchangeMap(check, data); - + forAll(data, i) { const label pointI = globalToLocal[data[i].pointLabel()]; @@ -449,7 +448,7 @@ void meshOptimizer::laplaceSmoother::laplacianWPCParallel Pout << "Crap " << globalPointLabel[pointI] << " coordinates " << points[pointI] << " point there " << data[i] << endl; } - # endif + # endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizeSurface.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizeSurface.C index bd4b563db92e2c7b5a94bc831ac686562b891b72..30bd6a4bd768abae4007c8b00b946c2aa8ce09e1 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizeSurface.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/meshOptimizerOptimizeSurface.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -45,15 +44,15 @@ namespace Foam void meshOptimizer::optimizeSurface(const meshOctree& octree) { Info << "Optimizing positions of surface nodes" << endl; - - meshSurfaceEngine& mse = const_cast<meshSurfaceEngine&>(meshSurface()); - meshSurfaceOptimizer surfaceOptimizer(mse, octree); + + meshSurfaceEngine& mse = const_cast<meshSurfaceEngine&>(meshSurface()); + meshSurfaceOptimizer surfaceOptimizer(mse, octree); - surfaceOptimizer.optimizeSurface(); + surfaceOptimizer.optimizeSurface(); meshSurfaceMapper(mse, octree).mapVerticesOntoSurfacePatches(); - - clearSurface(); + + clearSurface(); Info << "Finished optimizing positions of surface nodes" << endl; } diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/optimizeMeshFV.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/optimizeMeshFV.C index d564e5e9ddf7e972a9257295d996eef4a6f71c17..2ab2988b35e26237eb942bec588221acf56ba9bf 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/optimizeMeshFV.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/optimizeMeshFV.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,11 +36,6 @@ Description //#define DEBUGSmooth # ifdef DEBUGSmooth -#include "writeMeshEnsight.H" -#include "writeMeshFLMA.H" -#include "partTetMeshSimplex.H" -#include "writeSimplexFLMA.H" -#include "writeMeshFPMA.H" #include "helperFunctions.H" #include "polyMeshGenModifier.H" # endif @@ -55,22 +49,20 @@ namespace Foam void meshOptimizer::untangleMeshFV() { - Info << "Starting untangling the mesh" << endl; - - # ifdef DEBUGSmooth - partTetMesh tm(mesh_); - forAll(tm.tets(), tetI) - if( tm.tets()[tetI].mag(tm.points()) < 0.0 ) - Info << "Tet " << tetI << " is inverted!" << endl; - polyMeshGen tetPolyMesh(mesh_.returnTime()); - tm.createPolyMesh(tetPolyMesh); + Info << "Starting untangling the mesh" << endl; + + # ifdef DEBUGSmooth + partTetMesh tm(mesh_); + forAll(tm.tets(), tetI) + if( tm.tets()[tetI].mag(tm.points()) < 0.0 ) + Info << "Tet " << tetI << " is inverted!" << endl; + polyMeshGen tetPolyMesh(mesh_.returnTime()); + tm.createPolyMesh(tetPolyMesh); polyMeshGenModifier(tetPolyMesh).removeUnusedVertices(); - forAll(tm.smoothVertex(), pI) - if( !tm.smoothVertex()[pI] ) - Info << "Point " << pI << " cannot be moved!" << endl; - //writeMeshEnsight(tetPolyMesh, "tetMesh"); - writeMeshFLMA(tetPolyMesh, "tetMesh"); - + forAll(tm.smoothVertex(), pI) + if( !tm.smoothVertex()[pI] ) + Info << "Point " << pI << " cannot be moved!" << endl; + const VRWGraph& pTets = tm.pointTets(); forAll(pTets, pointI) { @@ -78,97 +70,95 @@ void meshOptimizer::untangleMeshFV() forAllRow(pTets, pointI, i) if( tets[pTets(pointI, i)].whichPosition(pointI) < 0 ) FatalError << "Wrong partTet" << abort(FatalError); - + partTetMeshSimplex simplex(tm, pointI); - word name("simplex"+help::scalarToText(pointI)); - writeSimplexFLMA(simplex, name); } - - boolList boundaryVertex(tetPolyMesh.points().size(), false); - const labelList& neighbour = tetPolyMesh.neighbour(); - forAll(neighbour, faceI) - if( neighbour[faceI] == -1 ) - { - const face& f = tetPolyMesh.faces()[faceI]; - - forAll(f, pI) - boundaryVertex[f[pI]] = true; - } - - forAll(boundaryVertex, pI) - { - if( boundaryVertex[pI] && tm.smoothVertex()[pI] ) - FatalErrorIn - ( - "void meshOptimizer::untangleMeshFV()" - ) << "Boundary vertex should not be moved!" << abort(FatalError); - } - # endif - - label nBadFaces, nGlobalIter(0), nIter; + + boolList boundaryVertex(tetPolyMesh.points().size(), false); + const labelList& neighbour = tetPolyMesh.neighbour(); + forAll(neighbour, faceI) + if( neighbour[faceI] == -1 ) + { + const face& f = tetPolyMesh.faces()[faceI]; + + forAll(f, pI) + boundaryVertex[f[pI]] = true; + } + + forAll(boundaryVertex, pI) + { + if( boundaryVertex[pI] && tm.smoothVertex()[pI] ) + FatalErrorIn + ( + "void meshOptimizer::untangleMeshFV()" + ) << "Boundary vertex should not be moved!" << abort(FatalError); + } + # endif + + label nBadFaces, nGlobalIter(0), nIter; const label maxNumGlobalIterations(10); - - const faceListPMG& faces = mesh_.faces(); - boolList changedFace(faces.size(), true); - + + const faceListPMG& faces = mesh_.faces(); + boolList changedFace(faces.size(), true); + labelHashSet badFaces; - - do - { - nIter = 0; - + + do + { + nIter = 0; + label minNumBadFaces(10 * faces.size()), minIter(-1); - do - { - nBadFaces = findBadFaces(badFaces, changedFace); - + do + { + nBadFaces = findBadFaces(badFaces, changedFace); + Info << "Iteration " << nIter << ". Number of bad faces is " << nBadFaces << endl; - - //- perform optimisation - if( nBadFaces == 0 ) - break; - + + //- perform optimisation + if( nBadFaces == 0 ) + break; + if( nBadFaces < minNumBadFaces ) { minNumBadFaces = nBadFaces; minIter = nIter; } - - partTetMesh tetMesh(mesh_, badFaces, (nGlobalIter / 5) + 1); + + partTetMesh tetMesh(mesh_, badFaces, (nGlobalIter / 5) + 1); tetMeshOptimisation tmo(tetMesh); - + tmo.optimiseUsingKnuppMetric(); - + tmo.optimiseUsingMeshUntangler(); - + tmo.optimiseUsingVolumeOptimizer(); - - tetMesh.updateOrigMesh(&changedFace); - - } while( (nIter < minIter+5) && (++nIter < 50) ); - - if( (nBadFaces == 0) || (++nGlobalIter >= maxNumGlobalIterations) ) - break; - + + tetMesh.updateOrigMesh(&changedFace); + + } while( (nIter < minIter+5) && (++nIter < 50) ); + + if( (nBadFaces == 0) || (++nGlobalIter >= maxNumGlobalIterations) ) + break; + // move boundary vertices nIter = 0; - - do - { - nBadFaces = findBadFaces(badFaces, changedFace); - + + do + { + nBadFaces = findBadFaces(badFaces, changedFace); + Info << "Iteration " << nIter << ". Number of bad faces is " << nBadFaces << endl; - - //- perform optimisation - if( nBadFaces == 0 ) - break; - - partTetMesh tetMesh(mesh_, badFaces, 0); + + //- perform optimisation + if( nBadFaces == 0 ) + break; + + partTetMesh tetMesh(mesh_, badFaces, 0); tetMeshOptimisation tmo(tetMesh); - + if( nGlobalIter < 2 ) { //- the point stays in the plane determined by the point normal @@ -184,70 +174,69 @@ void meshOptimizer::untangleMeshFV() //- move boundary points without any constraints tmo.optimiseBoundaryVolumeOptimizer(false); } - - tetMesh.updateOrigMesh(&changedFace); - - } while( ++nIter < 2 ); - } - while( nBadFaces ); - - Info << "Finished untangling the mesh" << endl; + + tetMesh.updateOrigMesh(&changedFace); + + } while( ++nIter < 2 ); + } + while( nBadFaces ); + + Info << "Finished untangling the mesh" << endl; } void meshOptimizer::optimizeLowQualityFaces() { label nBadFaces, nIter(0); - - const faceListPMG& faces = mesh_.faces(); - boolList changedFace(faces.size(), true); - + + const faceListPMG& faces = mesh_.faces(); + boolList changedFace(faces.size(), true); + label minNumBadFaces(10 * faces.size()), minIter(-1); do { labelHashSet lowQualityFaces; nBadFaces = findLowQualityFaces(lowQualityFaces, changedFace); - + changedFace = false; forAllConstIter(labelHashSet, lowQualityFaces, it) changedFace[it.key()] = true; - + Info << "Iteration " << nIter << ". Number of bad faces is " << nBadFaces << endl; - + //- perform optimisation if( nBadFaces == 0 ) break; - + if( nBadFaces < minNumBadFaces ) { minNumBadFaces = nBadFaces; minIter = nIter; } - + partTetMesh tetMesh(mesh_, lowQualityFaces, 2); - + tetMeshOptimisation tmo(tetMesh); - + tmo.optimiseUsingKnuppMetric(); - + tmo.optimiseUsingMeshUntangler(); - + tmo.optimiseUsingVolumeOptimizer(); tetMesh.updateOrigMesh(&changedFace); } while( (nIter < minIter+2) && (++nIter < 10) ); } - + void meshOptimizer::optimizeMeshFV() { Info << "Starting smoothing the mesh" << endl; - + laplaceSmoother lps(mesh_, vertexLocation_); - lps.optimizeLaplacianPC(2); - lps.optimizeLaplacianWPC(3); - - untangleMeshFV(); + lps.optimizeLaplacianPC(5); + + untangleMeshFV(); Info << "Finished smoothing the mesh" << endl; } diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.C index 609816e26e994213afb17b8bbcdd9403f114385e..0bb115b88d740c396bc2dfb324e7d19c692859d5 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -80,9 +79,9 @@ void knuppMetric::evaluateGradients(vector& grad, tensor& gradGrad) const gradGrad += gfx * gfx; } } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + knuppMetric::knuppMetric(partTetMeshSimplex& simplex) : simplexSmoother(simplex), @@ -93,15 +92,15 @@ knuppMetric::knuppMetric(partTetMeshSimplex& simplex) { forAll(tets_, tetI) { - const partTet& pt = tets_[tetI]; - const triangle<point, point> tri - ( - points_[pt.a()], - points_[pt.b()], - points_[pt.c()] - ); + const partTet& pt = tets_[tetI]; + const triangle<point, point> tri + ( + points_[pt.a()], + points_[pt.b()], + points_[pt.c()] + ); - const vector n = tri.normal(); + const vector n = tri.normal(); const scalar d = mag(n); if( d > VSMALL ) @@ -113,7 +112,7 @@ knuppMetric::knuppMetric(partTetMeshSimplex& simplex) beta_ = 0.01 * bb_.mag(); } - + knuppMetric::~knuppMetric() { @@ -190,7 +189,7 @@ void knuppMetric::optimizeNodePosition(const scalar tolObsolete) # ifdef DEBUGSmooth Info << "Second grad " << gradGradF << endl; - Info << "inv(gradGradF, determinant) " << inv(gradGradF, determinant) << endl; + Info << "inv(gradGradF, determinant) " << inv(gradGradF, determinant) << endl; Info << "Gradient " << gradF << endl; Info << "Determinant " << determinant << endl; Info << "Displacement " << disp << endl; @@ -198,25 +197,25 @@ void knuppMetric::optimizeNodePosition(const scalar tolObsolete) # endif - scalar relax(0.8); - label nLoops(0); - while( func > lastFunc ) - { - p_ = pOrig - relax * disp; - relax *= 0.5; - func = evaluateMetric(); - - if( func < lastFunc ) - continue; - - //- it seems that this direction is wrong - if( ++nLoops == 5 ) - { - p_ = pOrig; - disp = vector::zero; - func = 0.0; - } - } + scalar relax(0.8); + label nLoops(0); + while( func > lastFunc ) + { + p_ = pOrig - relax * disp; + relax *= 0.5; + func = evaluateMetric(); + + if( func < lastFunc ) + continue; + + //- it seems that this direction is wrong + if( ++nLoops == 5 ) + { + p_ = pOrig; + disp = vector::zero; + func = 0.0; + } + } lastFunc = func; } diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.H b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.H index f87f20a55f784fc38b0e31ffdfe95290ea14166b..3971c869e43758ef74b07354345efe71994135e7 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.H +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/knuppMetric/knuppMetric.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class knuppMetric Description Mesh smoothing using Knupp's metric. The metric is non-zero for inverted - tets only + tets only SourceFiles knuppMetric.C @@ -57,8 +56,8 @@ class knuppMetric public simplexSmoother { // Private data - //- free vertex - point& p_; + //- free vertex + point& p_; //- normals of triangles forming the outer hull DynList<vector, 64> normals_; @@ -79,15 +78,15 @@ class knuppMetric public: - knuppMetric(partTetMeshSimplex& simplex); + knuppMetric(partTetMeshSimplex& simplex); - // Destructor - ~knuppMetric(); + // Destructor + ~knuppMetric(); - // Member functions - //- find the best position such that all tets making a simplex - //- have a positive volume - void optimizeNodePosition(const scalar tol = 0.001); + // Member functions + //- find the best position such that all tets making a simplex + //- have a positive volume + void optimizeNodePosition(const scalar tol = 0.001); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.C index 9fe498077727bc35cfa4d8dc1a7e5fe8d57dcff1..ea78ed86f2dfa39dcb4226028d0e9cf1d416b564 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,15 +40,15 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // meshUntangler::meshUntangler ( - partTetMeshSimplex& simplex + partTetMeshSimplex& simplex ) : - simplexSmoother(simplex) + simplexSmoother(simplex) { } @@ -60,47 +59,47 @@ meshUntangler::~meshUntangler() void meshUntangler::optimizeNodePosition(const scalar tol) { - # ifdef DEBUGSmooth - Info << "Untangling point " << pointI_ << endl; - # endif - - cutRegion cr(bb_); - - forAll(tets_, tetI) - { - const partTet& tet = tets_[tetI]; - vector n - ( - (points_[tet.b()] - points_[tet.a()]) ^ - (points_[tet.c()] - points_[tet.a()]) - ); - - if( mag(n) < VSMALL ) continue; - - plane pl(points_[tet.a()], n); - - # ifdef DEBUGSmooth - Info << "tet.a() " << tet.a() << endl; - Info << "Cutting plane ref point " << pl.refPoint() << endl; - Info << "Cutting plane normal " << pl.normal() << endl; - # endif - - cr.planeCut(pl); - } - - if( cr.points().size() ) - { - point p(vector::zero); - - const DynList<point, 64>& pts = cr.points(); - forAll(pts, pI) - p += pts[pI]; - - p /= pts.size(); - - # ifdef DEBUGSmooth - Info << "Corners of the feasible region " << pts << endl; - # endif + # ifdef DEBUGSmooth + Info << "Untangling point " << pointI_ << endl; + # endif + + cutRegion cr(bb_); + + forAll(tets_, tetI) + { + const partTet& tet = tets_[tetI]; + vector n + ( + (points_[tet.b()] - points_[tet.a()]) ^ + (points_[tet.c()] - points_[tet.a()]) + ); + + if( mag(n) < VSMALL ) continue; + + plane pl(points_[tet.a()], n); + + # ifdef DEBUGSmooth + Info << "tet.a() " << tet.a() << endl; + Info << "Cutting plane ref point " << pl.refPoint() << endl; + Info << "Cutting plane normal " << pl.normal() << endl; + # endif + + cr.planeCut(pl); + } + + if( cr.points().size() ) + { + point p(vector::zero); + + const DynList<point, 64>& pts = cr.points(); + forAll(pts, pI) + p += pts[pI]; + + p /= pts.size(); + + # ifdef DEBUGSmooth + Info << "Corners of the feasible region " << pts << endl; + # endif for(direction i=0;i<vector::nComponents;++i) { @@ -108,9 +107,9 @@ void meshUntangler::optimizeNodePosition(const scalar tol) if( (val != val) || ((val - val) != (val - val)) ) return; } - + points_[pointI_] = p; - } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.H b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.H index 55f6515137d5658d2f6e98f0bc1e646b8c04eb9e..3f52735685c5b7381eb4a0152cad5c270e09791c 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.H +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntangler.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshUntangler Description Mesh smoothing without any topological changes. The vertex is put - into the centre of the convex feasible region. + into the centre of the convex feasible region. SourceFiles meshUntangler.C @@ -52,93 +51,93 @@ class partTetMeshSimplex; /*---------------------------------------------------------------------------*\ Class meshUntangler Declaration \*---------------------------------------------------------------------------*/ - + class meshUntangler : public simplexSmoother { - // Private nested classes - - class cutRegion - { - // Private data - DynList<point, 64>* pointsPtr_; - DynList<edge, 128>* edgesPtr_; - DynList<DynList<label, 8>, 64>* facesPtr_; - - //- helper data - DynList<point, 64>* cPtsPtr_; - DynList<edge, 128>* cEdgesPtr_; - DynList<DynList<label, 8>, 64>* cFacesPtr_; - - DynList<label, 64> newVertexLabel_; - DynList<scalar, 64> vertexDistance_; - DynList<direction, 64> vertexTypes_; - DynList<label, 128> newEdgeLabel_; - label origNumVertices_; - - scalar tol_; - bool valid_; - - // Private member functions - bool findNewVertices(const plane& plane); - void findNewEdges(); - void findNewFaces(); - - //- tie break to resolve problems due to truncation - //- errors - void tieBreak(const DynList<label, 8>& f); - - //- remove coincident vertices to improve tie breaking - void removeCoincidentVertices(); - - void createInitialConfiguration(const boundBox&); - - // Enumerations - enum vTypes - { - NONE = 0, - KEEP = 1, - INPLANE = 2, - USED = 4 - }; - - public: - - // Constructor - //- Construct from boundBox - cutRegion(const boundBox&); - - // Destructor - ~cutRegion(); - - // Member functions - //- return the vertices of the feasible region - inline const DynList<point, 64>& points() const - { - return *pointsPtr_; - } - - //- cut the region woth the plane - void planeCut(const plane& plane); - - //- export the feasible region as polyMeshGen - void createPolyMeshFromRegion(polyMeshGen&) const; - }; - - public: - + // Private nested classes + + class cutRegion + { + // Private data + DynList<point, 64>* pointsPtr_; + DynList<edge, 128>* edgesPtr_; + DynList<DynList<label, 8>, 64>* facesPtr_; + + //- helper data + DynList<point, 64>* cPtsPtr_; + DynList<edge, 128>* cEdgesPtr_; + DynList<DynList<label, 8>, 64>* cFacesPtr_; + + DynList<label, 64> newVertexLabel_; + DynList<scalar, 64> vertexDistance_; + DynList<direction, 64> vertexTypes_; + DynList<label, 128> newEdgeLabel_; + label origNumVertices_; + + scalar tol_; + bool valid_; + + // Private member functions + bool findNewVertices(const plane& plane); + void findNewEdges(); + void findNewFaces(); + + //- tie break to resolve problems due to truncation + //- errors + void tieBreak(const DynList<label, 8>& f); + + //- remove coincident vertices to improve tie breaking + void removeCoincidentVertices(); + + void createInitialConfiguration(const boundBox&); + + // Enumerations + enum vTypes + { + NONE = 0, + KEEP = 1, + INPLANE = 2, + USED = 4 + }; + + public: + + // Constructor + //- Construct from boundBox + cutRegion(const boundBox&); + + // Destructor + ~cutRegion(); + + // Member functions + //- return the vertices of the feasible region + inline const DynList<point, 64>& points() const + { + return *pointsPtr_; + } + + //- cut the region woth the plane + void planeCut(const plane& plane); + + //- export the feasible region as polyMeshGen + void createPolyMeshFromRegion(polyMeshGen&) const; + }; + + public: + // Constructor //- Construct from partTetMeshSimplex meshUntangler(partTetMeshSimplex& simplex); - - // Destructor - ~meshUntangler(); - - // Member functions - //- improve the position the the node by putting it + + // Destructor + ~meshUntangler(); + + // Member functions + //- improve the position the the node by putting it //- into the feasible region - void optimizeNodePosition(const scalar tol = 0.001); + void optimizeNodePosition(const scalar tol = 0.001); }; diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegion.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegion.C index 78b7fd7f4489604b47a9471e665aa7a2b58d2cd4..d127a9f97b888747c0357296f9ec1481042322b1 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegion.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegion.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -38,254 +37,252 @@ Description #ifdef DEBUGSmooth #include "Time.H" #include "objectRegistry.H" -#include "writeMeshEnsight.H" #endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void meshUntangler::cutRegion::createInitialConfiguration ( - const boundBox& bb + const boundBox& bb ) -{ - pointsPtr_ = new DynList<point, 64>(); - DynList<point, 64>& bVertices = *pointsPtr_; - edgesPtr_ = new DynList<edge, 128>(); - DynList<edge, 128>& bEdges = *edgesPtr_; - facesPtr_ = new DynList<DynList<label, 8>, 64>(); - DynList<DynList<label, 8>, 64>& bFaces = *facesPtr_; - - //- set vertices - const point c = (bb.max() + bb.min()) / 2.0; - const point vec = (bb.max() - bb.min()) / 2.0; - bVertices.append - ( - point(c.x() - vec.x(), c.y() - vec.y(), c.z() - vec.z()) - ); - bVertices.append - ( - point(c.x() + vec.x(), c.y() - vec.y(), c.z() - vec.z()) - ); - bVertices.append - ( - point(c.x() + vec.x(), c.y() + vec.y(), c.z() - vec.z()) - ); - bVertices.append - ( - point(c.x() - vec.x(), c.y() + vec.y(), c.z() - vec.z()) - ); - bVertices.append - ( - point(c.x() - vec.x(), c.y() - vec.y(), c.z() + vec.z()) - ); - bVertices.append - ( - point(c.x() + vec.x(), c.y() - vec.y(), c.z() + vec.z()) - ); - bVertices.append - ( - point(c.x() + vec.x(), c.y() + vec.y(), c.z() + vec.z()) - ); - bVertices.append - ( - point(c.x() - vec.x(), c.y() + vec.y(), c.z() + vec.z()) - ); - - //- set edges - - //- edges in x direction - bEdges.append(edge(0, 1)); - bEdges.append(edge(3, 2)); - bEdges.append(edge(7, 6)); - bEdges.append(edge(4, 5)); - - //- edges in y direction - bEdges.append(edge(1, 2)); - bEdges.append(edge(0, 3)); - bEdges.append(edge(4, 7)); - bEdges.append(edge(5, 6)); - - //- edges in z direction - bEdges.append(edge(0, 4)); - bEdges.append(edge(1, 5)); - bEdges.append(edge(2, 6)); - bEdges.append(edge(3, 7)); - - //- set faces - DynList<label, 8> f; - f.setSize(4); - - //- faces in x direction - f[0] = 5; - f[1] = 11; - f[2] = 6; - f[3] = 8; - bFaces.append(f); - f[0] = 4; - f[1] = 10; - f[2] = 7; - f[3] = 9; - bFaces.append(f); - //- faces in y direction - f[0] = 0; - f[1] = 8; - f[2] = 3; - f[3] = 9; - bFaces.append(f); - f[0] = 1; - f[1] = 11; - f[2] = 2; - f[3] = 10; - bFaces.append(f); - //- faces in z direction - f[0] = 0; - f[1] = 4; - f[2] = 1; - f[3] = 5; - bFaces.append(f); - f[0] = 3; - f[1] = 7; - f[2] = 2; - f[3] = 6; - bFaces.append(f); - - # ifdef DEBUGSmooth - Info << "Original vertices " << *pointsPtr_ << endl; - Info << "Original edges " << *edgesPtr_ << endl; - Info << "Original faces " << *facesPtr_ << endl; - # endif +{ + pointsPtr_ = new DynList<point, 64>(); + DynList<point, 64>& bVertices = *pointsPtr_; + edgesPtr_ = new DynList<edge, 128>(); + DynList<edge, 128>& bEdges = *edgesPtr_; + facesPtr_ = new DynList<DynList<label, 8>, 64>(); + DynList<DynList<label, 8>, 64>& bFaces = *facesPtr_; + + //- set vertices + const point c = (bb.max() + bb.min()) / 2.0; + const point vec = (bb.max() - bb.min()) / 2.0; + bVertices.append + ( + point(c.x() - vec.x(), c.y() - vec.y(), c.z() - vec.z()) + ); + bVertices.append + ( + point(c.x() + vec.x(), c.y() - vec.y(), c.z() - vec.z()) + ); + bVertices.append + ( + point(c.x() + vec.x(), c.y() + vec.y(), c.z() - vec.z()) + ); + bVertices.append + ( + point(c.x() - vec.x(), c.y() + vec.y(), c.z() - vec.z()) + ); + bVertices.append + ( + point(c.x() - vec.x(), c.y() - vec.y(), c.z() + vec.z()) + ); + bVertices.append + ( + point(c.x() + vec.x(), c.y() - vec.y(), c.z() + vec.z()) + ); + bVertices.append + ( + point(c.x() + vec.x(), c.y() + vec.y(), c.z() + vec.z()) + ); + bVertices.append + ( + point(c.x() - vec.x(), c.y() + vec.y(), c.z() + vec.z()) + ); + + //- set edges + + //- edges in x direction + bEdges.append(edge(0, 1)); + bEdges.append(edge(3, 2)); + bEdges.append(edge(7, 6)); + bEdges.append(edge(4, 5)); + + //- edges in y direction + bEdges.append(edge(1, 2)); + bEdges.append(edge(0, 3)); + bEdges.append(edge(4, 7)); + bEdges.append(edge(5, 6)); + + //- edges in z direction + bEdges.append(edge(0, 4)); + bEdges.append(edge(1, 5)); + bEdges.append(edge(2, 6)); + bEdges.append(edge(3, 7)); + + //- set faces + DynList<label, 8> f; + f.setSize(4); + + //- faces in x direction + f[0] = 5; + f[1] = 11; + f[2] = 6; + f[3] = 8; + bFaces.append(f); + f[0] = 4; + f[1] = 10; + f[2] = 7; + f[3] = 9; + bFaces.append(f); + //- faces in y direction + f[0] = 0; + f[1] = 8; + f[2] = 3; + f[3] = 9; + bFaces.append(f); + f[0] = 1; + f[1] = 11; + f[2] = 2; + f[3] = 10; + bFaces.append(f); + //- faces in z direction + f[0] = 0; + f[1] = 4; + f[2] = 1; + f[3] = 5; + bFaces.append(f); + f[0] = 3; + f[1] = 7; + f[2] = 2; + f[3] = 6; + bFaces.append(f); + + # ifdef DEBUGSmooth + Info << "Original vertices " << *pointsPtr_ << endl; + Info << "Original edges " << *edgesPtr_ << endl; + Info << "Original faces " << *facesPtr_ << endl; + # endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + meshUntangler::cutRegion::cutRegion(const boundBox& bb) : - pointsPtr_(NULL), - edgesPtr_(NULL), - facesPtr_(NULL), - cPtsPtr_(NULL), - cEdgesPtr_(NULL), - cFacesPtr_(NULL), - newVertexLabel_(), - vertexDistance_(), - vertexTypes_(), - newEdgeLabel_(), - origNumVertices_(), - tol_(SMALL * bb.mag()), - valid_(true) + pointsPtr_(NULL), + edgesPtr_(NULL), + facesPtr_(NULL), + cPtsPtr_(NULL), + cEdgesPtr_(NULL), + cFacesPtr_(NULL), + newVertexLabel_(), + vertexDistance_(), + vertexTypes_(), + newEdgeLabel_(), + origNumVertices_(), + tol_(SMALL * bb.mag()), + valid_(true) { - createInitialConfiguration(bb); + createInitialConfiguration(bb); } meshUntangler::cutRegion::~cutRegion() { - deleteDemandDrivenData(pointsPtr_); - deleteDemandDrivenData(edgesPtr_); - deleteDemandDrivenData(facesPtr_); - deleteDemandDrivenData(cPtsPtr_); - deleteDemandDrivenData(cEdgesPtr_); - deleteDemandDrivenData(cFacesPtr_); + deleteDemandDrivenData(pointsPtr_); + deleteDemandDrivenData(edgesPtr_); + deleteDemandDrivenData(facesPtr_); + deleteDemandDrivenData(cPtsPtr_); + deleteDemandDrivenData(cEdgesPtr_); + deleteDemandDrivenData(cFacesPtr_); } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshUntangler::cutRegion::planeCut(const plane& plane) { - if( !valid_ ) - return; - - # ifdef DEBUGSmooth - if( cFacesPtr_ || cPtsPtr_ || cEdgesPtr_ ) - { - FatalErrorIn - ( - "void meshUntangler::" - "cutRegion::planeCut(const plane& plane)" - ) << "Pointers should not be allocated!" << abort(FatalError); - } - - Foam::Time runTime - ( - Foam::Time::controlDictName, - "../.", - "testSmoothing" - ); - - objectRegistry oR(runTime); - - polyMeshGen pmg - ( - oR - ); - this->createPolyMeshFromRegion(pmg); - writeMeshEnsight(pmg, "feasibleRegion"); - # endif - - if( findNewVertices(plane) ) - { - findNewEdges(); - - findNewFaces(); - - if( !valid_ ) return; - - deleteDemandDrivenData(pointsPtr_); - pointsPtr_ = cPtsPtr_; - cPtsPtr_ = NULL; - - deleteDemandDrivenData(edgesPtr_); - edgesPtr_ = cEdgesPtr_; - cEdgesPtr_ = NULL; - - deleteDemandDrivenData(facesPtr_); - facesPtr_ = cFacesPtr_; - cFacesPtr_ = NULL; - } + if( !valid_ ) + return; + + # ifdef DEBUGSmooth + if( cFacesPtr_ || cPtsPtr_ || cEdgesPtr_ ) + { + FatalErrorIn + ( + "void meshUntangler::" + "cutRegion::planeCut(const plane& plane)" + ) << "Pointers should not be allocated!" << abort(FatalError); + } + + Foam::Time runTime + ( + Foam::Time::controlDictName, + "../.", + "testSmoothing" + ); + + objectRegistry oR(runTime); + + polyMeshGen pmg + ( + oR + ); + this->createPolyMeshFromRegion(pmg); + # endif + + if( findNewVertices(plane) ) + { + findNewEdges(); + + findNewFaces(); + + if( !valid_ ) return; + + deleteDemandDrivenData(pointsPtr_); + pointsPtr_ = cPtsPtr_; + cPtsPtr_ = NULL; + + deleteDemandDrivenData(edgesPtr_); + edgesPtr_ = cEdgesPtr_; + cEdgesPtr_ = NULL; + + deleteDemandDrivenData(facesPtr_); + facesPtr_ = cFacesPtr_; + cFacesPtr_ = NULL; + } } void meshUntangler::cutRegion::createPolyMeshFromRegion ( - polyMeshGen& mesh + polyMeshGen& mesh ) const { - polyMeshGenModifier meshModifier(mesh); - pointFieldPMG& points = meshModifier.pointsAccess(); - points.setSize(pointsPtr_->size()); - forAll(points, pI) - points[pI] = (*pointsPtr_)[pI]; - - faceListPMG& faces = meshModifier.facesAccess(); - cellListPMG& cells = meshModifier.cellsAccess(); - cells.setSize(1); - cells[0].setSize(facesPtr_->size()); - faces.setSize(facesPtr_->size()); - - const DynList<edge, 128>& edges = *edgesPtr_; - const DynList<DynList<label, 8>, 64>& fcs = *facesPtr_; - forAll(faces, fI) - { - DynList<edge> fEdges; - const DynList<label, 8>& f = fcs[fI]; - forAll(f, eI) - fEdges.append(edges[f[eI]]); - - Info << "Edges forming face " << fI << " are " << fEdges << endl; - labelListList sf = sortEdgesIntoChains(fEdges).sortedChains(); - if( sf.size() != 1 ) - FatalErrorIn - ( - "void meshOptimizer::meshUntangler::" - "cutRegion::createPolyMeshFromRegion(polyMesgGen&)" - ) << "More than one face created!" << abort(FatalError); - - faces[fI] = face(sf[0]); - cells[0][fI] = fI; - } + polyMeshGenModifier meshModifier(mesh); + pointFieldPMG& points = meshModifier.pointsAccess(); + points.setSize(pointsPtr_->size()); + forAll(points, pI) + points[pI] = (*pointsPtr_)[pI]; + + faceListPMG& faces = meshModifier.facesAccess(); + cellListPMG& cells = meshModifier.cellsAccess(); + cells.setSize(1); + cells[0].setSize(facesPtr_->size()); + faces.setSize(facesPtr_->size()); + + const DynList<edge, 128>& edges = *edgesPtr_; + const DynList<DynList<label, 8>, 64>& fcs = *facesPtr_; + forAll(faces, fI) + { + DynList<edge> fEdges; + const DynList<label, 8>& f = fcs[fI]; + forAll(f, eI) + fEdges.append(edges[f[eI]]); + + Info << "Edges forming face " << fI << " are " << fEdges << endl; + labelListList sf = sortEdgesIntoChains(fEdges).sortedChains(); + if( sf.size() != 1 ) + FatalErrorIn + ( + "void meshOptimizer::meshUntangler::" + "cutRegion::createPolyMeshFromRegion(polyMesgGen&)" + ) << "More than one face created!" << abort(FatalError); + + faces[fI] = face(sf[0]); + cells[0][fI] = fI; + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionEdges.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionEdges.C index bc2e6d0d0b87f89d326107dfbe11e1194e66d2bb..727df86f43d83d9919173b423f61da687495fabb 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionEdges.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,81 +34,81 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshUntangler::cutRegion::findNewEdges() { - #ifdef DEBUGSmooth - Info << "Creating new edgesPtr_" << endl; - #endif - - cEdgesPtr_ = new DynList<edge, 128>(); - DynList<edge, 128>& cEdges = *cEdgesPtr_; - - const DynList<point, 64>& pts = *pointsPtr_; - const DynList<edge, 128>& edges = *edgesPtr_; - - newEdgeLabel_.setSize(edges.size()); - newEdgeLabel_ = -1; + #ifdef DEBUGSmooth + Info << "Creating new edgesPtr_" << endl; + #endif + + cEdgesPtr_ = new DynList<edge, 128>(); + DynList<edge, 128>& cEdges = *cEdgesPtr_; + + const DynList<point, 64>& pts = *pointsPtr_; + const DynList<edge, 128>& edges = *edgesPtr_; + + newEdgeLabel_.setSize(edges.size()); + newEdgeLabel_ = -1; - forAll(edges, eI) - { - const edge& e = edges[eI]; - const label start = e.start(); - const label end = e.end(); - const label newStartLabel = newVertexLabel_[start]; - const label newEndLabel = newVertexLabel_[end]; - - if( (newStartLabel != -1) && (newEndLabel != -1) ) - { - newEdgeLabel_[eI] = cEdges.size(); - cEdges.append(edge(newStartLabel, newEndLabel)); - } - else if( (newEndLabel != -1) && (vertexTypes_[end] & KEEP) ) - { - //- start edge vertex is not visible, but the other one is - newEdgeLabel_[eI] = cEdges.size(); - cEdges.append(edge(newEndLabel, cPtsPtr_->size())); - - const scalar t = - -vertexDistance_[start] / - (vertexDistance_[end] - vertexDistance_[start]); - - const point newP = (1.0 - t) * pts[start] + t * pts[end]; - cPtsPtr_->append(newP); - } - else if( (newStartLabel != -1) && (vertexTypes_[start] & KEEP) ) - { - //- end edge vertex is not visible, but the other one is - newEdgeLabel_[eI] = cEdges.size(); - cEdges.append(edge(newStartLabel, cPtsPtr_->size())); - - const scalar t = - -vertexDistance_[end] / - (vertexDistance_[start] - vertexDistance_[end]); - - const point newP = (1.0 - t) * pts[end] + t * pts[start]; - cPtsPtr_->append(newP); - } - - # ifdef DEBUGSmooth - if( newEdgeLabel_[eI] != -1 ) - { - Info << nl << "Edge " << eI << "consisting of " << e - << " has been replaced with edge " << newEdgeLabel_[eI] << " " - << cEdges[newEdgeLabel_[eI]] << endl; - } - else - { - Info << "Edge " << e << " has been deleted!" << endl; - } - # endif - } - - #ifdef DEBUGSmooth - Info << "Found " << cEdges.size() << " new edges" << endl; - #endif + forAll(edges, eI) + { + const edge& e = edges[eI]; + const label start = e.start(); + const label end = e.end(); + const label newStartLabel = newVertexLabel_[start]; + const label newEndLabel = newVertexLabel_[end]; + + if( (newStartLabel != -1) && (newEndLabel != -1) ) + { + newEdgeLabel_[eI] = cEdges.size(); + cEdges.append(edge(newStartLabel, newEndLabel)); + } + else if( (newEndLabel != -1) && (vertexTypes_[end] & KEEP) ) + { + //- start edge vertex is not visible, but the other one is + newEdgeLabel_[eI] = cEdges.size(); + cEdges.append(edge(newEndLabel, cPtsPtr_->size())); + + const scalar t = + -vertexDistance_[start] / + (vertexDistance_[end] - vertexDistance_[start]); + + const point newP = (1.0 - t) * pts[start] + t * pts[end]; + cPtsPtr_->append(newP); + } + else if( (newStartLabel != -1) && (vertexTypes_[start] & KEEP) ) + { + //- end edge vertex is not visible, but the other one is + newEdgeLabel_[eI] = cEdges.size(); + cEdges.append(edge(newStartLabel, cPtsPtr_->size())); + + const scalar t = + -vertexDistance_[end] / + (vertexDistance_[start] - vertexDistance_[end]); + + const point newP = (1.0 - t) * pts[end] + t * pts[start]; + cPtsPtr_->append(newP); + } + + # ifdef DEBUGSmooth + if( newEdgeLabel_[eI] != -1 ) + { + Info << nl << "Edge " << eI << "consisting of " << e + << " has been replaced with edge " << newEdgeLabel_[eI] << " " + << cEdges[newEdgeLabel_[eI]] << endl; + } + else + { + Info << "Edge " << e << " has been deleted!" << endl; + } + # endif + } + + #ifdef DEBUGSmooth + Info << "Found " << cEdges.size() << " new edges" << endl; + #endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionFaces.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionFaces.C index 6f511a46ccd2cef8dd14e977008121695f6fd1ef..f6e814c6c827fe21bf6b73f4fe6ab31d42108bb4 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionFaces.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,178 +38,178 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshUntangler::cutRegion::findNewFaces() { - #ifdef DEBUGSmooth - Info << "Finding new faces " << endl; - #endif - - bool finished; - do - { - finished = true; - - const DynList<DynList<label, 8>, 64>& fcs = *facesPtr_; - DynList<edge, 128>& cEdges = *cEdgesPtr_; - - cFacesPtr_ = new DynList<DynList<label, 8>, 64>(); - DynList<DynList<label, 8>, 64>& cFaces = *cFacesPtr_; - - DynList<label, 8> faceInPlane; - - DynList<label, 64> pointUsage; - pointUsage.setSize(cPtsPtr_->size()); - - forAll(fcs, fI) - { - const DynList<label, 8>& f = fcs[fI]; - - # ifdef DEBUGSmooth - Info << "Creating new face from face " << fI - << " consisting of edges " << f << endl; - # endif - - pointUsage = 0; - - DynList<label, 8> newFace(f.size()+1); - - forAll(f, eI) - { - # ifdef DEBUGSmooth - const DynList<edge>& edges = *edgesPtr_; - Info << "Vertex types for face edge " << eI << " are " - << label(vertexTypes_[edges[f[eI]].start()]) << " and " - << label(vertexTypes_[edges[f[eI]].end()]) << endl; - # endif - - const label edgeLabel = newEdgeLabel_[f[eI]]; - - if( edgeLabel != -1 ) - { - # ifdef DEBUGSmooth - Info << "Orig edge " << eI << " " << edges[f[eI]] - << " is replaced with " << cEdges[edgeLabel] << endl; - # endif - - const edge& e = cEdges[edgeLabel]; - ++pointUsage[e[0]]; - ++pointUsage[e[1]]; - newFace.append(edgeLabel); - } - } - - if( newFace.size() > 1 ) - { - DynList<label, 4> newEdge(2); - forAll(pointUsage, pI) - if( pointUsage[pI] == 1 ) - newEdge.append(pI); - - if( newEdge.size() == 2 ) - { - # ifdef DEBUGSmooth - Info << "Storing new edge " << newEdge << endl; - # endif - - newFace.append(cEdges.size()); - cEdges.append(edge(newEdge[0], newEdge[1])); - } - else if( newEdge.size() > 2 ) - { - # ifdef DEBUGSmooth - Info << "New edge " << newEdge << endl; - # endif - - tieBreak(f); - if( !valid_ ) return; - finished = false; - break; - - FatalErrorIn - ( - "void meshUntangler::cutRegion::findNewFaces()" - ) << "Edge has more than two nodes!" - << abort(FatalError); - } - - cFaces.append(newFace); - } - } - - if( !finished ) continue; - - //- find edges which form the faceInPlane - DynList<label, 128> edgeUsage; - edgeUsage.setSize(cEdges.size()); - edgeUsage = 0; - forAll(cFaces, fI) - { - const DynList<label, 8>& f = cFaces[fI]; - - forAll(f, eI) - ++edgeUsage[f[eI]]; - } - - forAll(edgeUsage, eI) - if( edgeUsage[eI] == 1 ) - faceInPlane.append(eI); - - if( faceInPlane.size() > 2 ) - { - # ifdef DEBUGSmooth - Info << "Adding face in plane " << faceInPlane << endl; - Info << "Face in plane consists of edges " << endl; - forAll(faceInPlane, eI) - Info << "Edge " << eI << " is " - << cEdges[faceInPlane[eI]] << endl; - # endif - - cFaces.append(faceInPlane); - } - - # ifdef DEBUGSmooth - Info << "cEdges " << cEdges << endl; - Info << "Number of faces before cutting " << fcs.size() << endl; - Info << "Found " << cFaces.size() << " new faces" << endl; - forAll(fcs, fI) - { - Info << "Old face " << fI << " contains edges " << fcs[fI] << endl; - } - - forAll(cFaces, fI) - { - Info << "New face " << fI << " contains edges " << cFaces[fI] << endl; - } - - //- test if the region is closed - List<DynList<label, 4> > eFaces(cEdges.size()); - forAll(cFaces, fI) - { - const DynList<label, 8>& f = cFaces[fI]; - forAll(f, eI) - eFaces[f[eI]].append(fI); - } - - if( eFaces.size() > 5 ) - forAll(eFaces, fI) - if( eFaces[fI].size() != 2 ) - { - Info << "eFaces " << eFaces << endl; - Info << "cEdges " << cEdges << endl; - Info << "cFaces " << cFaces << endl; - - FatalErrorIn - ( - "void meshOptimizer::meshUntangler::" - "cutRegion::findNewFaces()" - ) << "Cell is not topologically closed!" << abort(FatalError); - } - # endif - - } while( !finished ); + #ifdef DEBUGSmooth + Info << "Finding new faces " << endl; + #endif + + bool finished; + do + { + finished = true; + + const DynList<DynList<label, 8>, 64>& fcs = *facesPtr_; + DynList<edge, 128>& cEdges = *cEdgesPtr_; + + cFacesPtr_ = new DynList<DynList<label, 8>, 64>(); + DynList<DynList<label, 8>, 64>& cFaces = *cFacesPtr_; + + DynList<label, 8> faceInPlane; + + DynList<label, 64> pointUsage; + pointUsage.setSize(cPtsPtr_->size()); + + forAll(fcs, fI) + { + const DynList<label, 8>& f = fcs[fI]; + + # ifdef DEBUGSmooth + Info << "Creating new face from face " << fI + << " consisting of edges " << f << endl; + # endif + + pointUsage = 0; + + DynList<label, 8> newFace; + + forAll(f, eI) + { + # ifdef DEBUGSmooth + const DynList<edge>& edges = *edgesPtr_; + Info << "Vertex types for face edge " << eI << " are " + << label(vertexTypes_[edges[f[eI]].start()]) << " and " + << label(vertexTypes_[edges[f[eI]].end()]) << endl; + # endif + + const label edgeLabel = newEdgeLabel_[f[eI]]; + + if( edgeLabel != -1 ) + { + # ifdef DEBUGSmooth + Info << "Orig edge " << eI << " " << edges[f[eI]] + << " is replaced with " << cEdges[edgeLabel] << endl; + # endif + + const edge& e = cEdges[edgeLabel]; + ++pointUsage[e[0]]; + ++pointUsage[e[1]]; + newFace.append(edgeLabel); + } + } + + if( newFace.size() > 1 ) + { + DynList<label, 4> newEdge; + forAll(pointUsage, pI) + if( pointUsage[pI] == 1 ) + newEdge.append(pI); + + if( newEdge.size() == 2 ) + { + # ifdef DEBUGSmooth + Info << "Storing new edge " << newEdge << endl; + # endif + + newFace.append(cEdges.size()); + cEdges.append(edge(newEdge[0], newEdge[1])); + } + else if( newEdge.size() > 2 ) + { + # ifdef DEBUGSmooth + Info << "New edge " << newEdge << endl; + # endif + + tieBreak(f); + if( !valid_ ) return; + finished = false; + break; + + FatalErrorIn + ( + "void meshUntangler::cutRegion::findNewFaces()" + ) << "Edge has more than two nodes!" + << abort(FatalError); + } + + cFaces.append(newFace); + } + } + + if( !finished ) continue; + + //- find edges which form the faceInPlane + DynList<label, 128> edgeUsage; + edgeUsage.setSize(cEdges.size()); + edgeUsage = 0; + forAll(cFaces, fI) + { + const DynList<label, 8>& f = cFaces[fI]; + + forAll(f, eI) + ++edgeUsage[f[eI]]; + } + + forAll(edgeUsage, eI) + if( edgeUsage[eI] == 1 ) + faceInPlane.append(eI); + + if( faceInPlane.size() > 2 ) + { + # ifdef DEBUGSmooth + Info << "Adding face in plane " << faceInPlane << endl; + Info << "Face in plane consists of edges " << endl; + forAll(faceInPlane, eI) + Info << "Edge " << eI << " is " + << cEdges[faceInPlane[eI]] << endl; + # endif + + cFaces.append(faceInPlane); + } + + # ifdef DEBUGSmooth + Info << "cEdges " << cEdges << endl; + Info << "Number of faces before cutting " << fcs.size() << endl; + Info << "Found " << cFaces.size() << " new faces" << endl; + forAll(fcs, fI) + { + Info << "Old face " << fI << " contains edges " << fcs[fI] << endl; + } + + forAll(cFaces, fI) + { + Info << "New face " << fI << " contains edges " << cFaces[fI] << endl; + } + + //- test if the region is closed + List<DynList<label, 4> > eFaces(cEdges.size()); + forAll(cFaces, fI) + { + const DynList<label, 8>& f = cFaces[fI]; + forAll(f, eI) + eFaces[f[eI]].append(fI); + } + + if( eFaces.size() > 5 ) + forAll(eFaces, fI) + if( eFaces[fI].size() != 2 ) + { + Info << "eFaces " << eFaces << endl; + Info << "cEdges " << cEdges << endl; + Info << "cFaces " << cFaces << endl; + + FatalErrorIn + ( + "void meshOptimizer::meshUntangler::" + "cutRegion::findNewFaces()" + ) << "Cell is not topologically closed!" << abort(FatalError); + } + # endif + + } while( !finished ); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionPoints.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionPoints.C index b1a08b8d25984e2aa3754fee78a6187f80869d33..1b2d7c7d5fda1558f79b918b6330dfa1ea006c08 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionPoints.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionPoints.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -38,157 +37,156 @@ Description #ifdef DEBUGSmooth #include "Time.H" #include "objectRegistry.H" -#include "writeMeshEnsight.H" #endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + bool meshUntangler::cutRegion::findNewVertices ( - const plane& plane + const plane& plane ) { - #ifdef DEBUGSmooth - Info << "Finding new vertices" << endl; - #endif - - const DynList<point, 64>& points = *pointsPtr_; - - newVertexLabel_.setSize(points.size()); - newVertexLabel_ = -1; - - vertexDistance_.setSize(points.size()); - - vertexTypes_.setSize(points.size()); - vertexTypes_ = direction(NONE); - - origNumVertices_ = 0; - - cPtsPtr_ = new DynList<point, 64>(); - - const point& rp = plane.refPoint(); - const vector& n = plane.normal(); - forAll(points, pI) - { - const point& p = points[pI]; - vertexDistance_[pI] = ((p - rp) & n); - - if( vertexDistance_[pI] > tol_ ) - { - cPtsPtr_->append(p); - newVertexLabel_[pI] = origNumVertices_++; - vertexTypes_[pI] |= KEEP; - } - else if( vertexDistance_[pI] >= -tol_ ) - { - cPtsPtr_->append(p); - newVertexLabel_[pI] = origNumVertices_++; - vertexTypes_[pI] |= INPLANE; - vertexDistance_[pI] = 0.0; - } - } - - #ifdef DEBUGSmooth - Info << "tolerance " << tol_ << endl; - Info << "New number of vertices is " << origNumVertices_ << endl; - forAll(points, pI) - Info << "Original vertex " << pI << " is " << points[pI] - << ". Vertex distance from plane is " << vertexDistance_[pI] - << " and its new label is " << newVertexLabel_[pI] << endl; - #endif - - if( origNumVertices_ < points.size() ) - { - return true; - } - else - { - deleteDemandDrivenData(cPtsPtr_); - - return false; - } + #ifdef DEBUGSmooth + Info << "Finding new vertices" << endl; + #endif + + const DynList<point, 64>& points = *pointsPtr_; + + newVertexLabel_.setSize(points.size()); + newVertexLabel_ = -1; + + vertexDistance_.setSize(points.size()); + + vertexTypes_.setSize(points.size()); + vertexTypes_ = direction(NONE); + + origNumVertices_ = 0; + + cPtsPtr_ = new DynList<point, 64>(); + + const point& rp = plane.refPoint(); + const vector& n = plane.normal(); + forAll(points, pI) + { + const point& p = points[pI]; + vertexDistance_[pI] = ((p - rp) & n); + + if( vertexDistance_[pI] > tol_ ) + { + cPtsPtr_->append(p); + newVertexLabel_[pI] = origNumVertices_++; + vertexTypes_[pI] |= KEEP; + } + else if( vertexDistance_[pI] >= -tol_ ) + { + cPtsPtr_->append(p); + newVertexLabel_[pI] = origNumVertices_++; + vertexTypes_[pI] |= INPLANE; + vertexDistance_[pI] = 0.0; + } + } + + #ifdef DEBUGSmooth + Info << "tolerance " << tol_ << endl; + Info << "New number of vertices is " << origNumVertices_ << endl; + forAll(points, pI) + Info << "Original vertex " << pI << " is " << points[pI] + << ". Vertex distance from plane is " << vertexDistance_[pI] + << " and its new label is " << newVertexLabel_[pI] << endl; + #endif + + if( origNumVertices_ < points.size() ) + { + return true; + } + else + { + deleteDemandDrivenData(cPtsPtr_); + + return false; + } } void meshUntangler::cutRegion::removeCoincidentVertices() { - const DynList<point, 64>& points = *pointsPtr_; - DynList<edge, 128>& edges = *edgesPtr_; - DynList<label, 64> newLabelForPoint; - newLabelForPoint.setSize(points.size()); - newLabelForPoint = -1; - - bool found(false); - forAll(points, pI) - { - if( newLabelForPoint[pI] != -1 ) continue; - for(label pJ=pI+1;pJ<points.size();++pJ) - if( mag(points[pJ] - points[pI]) < tol_ ) - { - # ifdef DEBUGSmooth - Info << "Vertices " << pI << " and " << pJ - << " are too close" << endl; - # endif - - newLabelForPoint[pJ] = pI; - found = true; - } - } - - if( !found ) - return; - - forAll(edges, eI) - { - edge& e = edges[eI]; - if( newLabelForPoint[e.start()] != -1 ) - e.start() = newLabelForPoint[e.start()]; - if( newLabelForPoint[e.end()] != -1 ) - e.end() = newLabelForPoint[e.end()]; - } - - //- remove edges which contain the same vertex - newEdgeLabel_ = -1; - label edgeLabel(0); - - cEdgesPtr_ = new DynList<edge, 128>(); - forAll(edges, eI) - if( edges[eI].start() != edges[eI].end() ) - { - cEdgesPtr_->append(edges[eI]); - newEdgeLabel_[eI] = edgeLabel++; - } - - deleteDemandDrivenData(edgesPtr_); - edgesPtr_ = cEdgesPtr_; - cEdgesPtr_ = NULL; - - //- renumber faces - const DynList<DynList<label, 8>, 64>& faces = *facesPtr_; - cFacesPtr_ = new DynList<DynList<label, 8>, 64>(); - forAll(faces, fI) - { - const DynList<label, 8>& f = faces[fI]; - - DynList<label, 8> nf(f.size()); - - forAll(f, eI) - if( newEdgeLabel_[f[eI]] != -1 ) - nf.append(newEdgeLabel_[f[eI]]); - - if( nf.size() > 2 ) - { - cFacesPtr_->append(nf); - } - } - - deleteDemandDrivenData(facesPtr_); - facesPtr_ = cFacesPtr_; - cFacesPtr_ = NULL; + const DynList<point, 64>& points = *pointsPtr_; + DynList<edge, 128>& edges = *edgesPtr_; + DynList<label, 64> newLabelForPoint; + newLabelForPoint.setSize(points.size()); + newLabelForPoint = -1; + + bool found(false); + forAll(points, pI) + { + if( newLabelForPoint[pI] != -1 ) continue; + for(label pJ=pI+1;pJ<points.size();++pJ) + if( mag(points[pJ] - points[pI]) < tol_ ) + { + # ifdef DEBUGSmooth + Info << "Vertices " << pI << " and " << pJ + << " are too close" << endl; + # endif + + newLabelForPoint[pJ] = pI; + found = true; + } + } + + if( !found ) + return; + + forAll(edges, eI) + { + edge& e = edges[eI]; + if( newLabelForPoint[e.start()] != -1 ) + e.start() = newLabelForPoint[e.start()]; + if( newLabelForPoint[e.end()] != -1 ) + e.end() = newLabelForPoint[e.end()]; + } + + //- remove edges which contain the same vertex + newEdgeLabel_ = -1; + label edgeLabel(0); + + cEdgesPtr_ = new DynList<edge, 128>(); + forAll(edges, eI) + if( edges[eI].start() != edges[eI].end() ) + { + cEdgesPtr_->append(edges[eI]); + newEdgeLabel_[eI] = edgeLabel++; + } + + deleteDemandDrivenData(edgesPtr_); + edgesPtr_ = cEdgesPtr_; + cEdgesPtr_ = NULL; + + //- renumber faces + const DynList<DynList<label, 8>, 64>& faces = *facesPtr_; + cFacesPtr_ = new DynList<DynList<label, 8>, 64>(); + forAll(faces, fI) + { + const DynList<label, 8>& f = faces[fI]; + + DynList<label, 8> nf; + + forAll(f, eI) + if( newEdgeLabel_[f[eI]] != -1 ) + nf.append(newEdgeLabel_[f[eI]]); + + if( nf.size() > 2 ) + { + cFacesPtr_->append(nf); + } + } + + deleteDemandDrivenData(facesPtr_); + facesPtr_ = cFacesPtr_; + cFacesPtr_ = NULL; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionTieBreak.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionTieBreak.C index 7ff9e46ae31dd2809fcab0614b932c75b29fa675..bd0b305b3297f815b8d6236c26e8e749e9fd06a6 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionTieBreak.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/meshUntangler/meshUntanglerCutRegionTieBreak.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,158 +35,158 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshUntangler::cutRegion::tieBreak(const DynList<label, 8>& f) { - // There must be only one, singly connected region which is cut off - // from the feasible region. This may not be the case if one operates in the - // range of computer tolerances. In order to resolve the tie it is necessary - // to find a single region which will be cut off from the feasible region. - // This will be done by finding the node with the most negative distance, - // and then start marking vertices connected to that vertex via an edge. - - # ifdef DEBUGSmooth - Info << "Starting tie break" << endl; - # endif - - //- delete pointer data - deleteDemandDrivenData(cPtsPtr_); - deleteDemandDrivenData(cEdgesPtr_); - deleteDemandDrivenData(cFacesPtr_); - - //- remove coincident vertices - //removeCoincidentVertices(); - - const DynList<edge, 128>& edges = *edgesPtr_; - - DynList<edge> faceEdges(f.size()); - forAll(f, eI) - faceEdges.append(edges[f[eI]]); - - labelListList fvertices = sortEdgesIntoChains(faceEdges).sortedChains(); - if( fvertices.size() != 1 ) - { - valid_ = false; - return; - - Info << "Face vertices " << fvertices << endl; - FatalErrorIn - ( - "void meshUntangler::cutRegion::tieBreak(const face& f)" - ) << "Number of created faces is not 1 but " - << fvertices.size() << abort(FatalError); - } - - const labelList& fv = fvertices[0]; - - DynList<label, 64> vertexRegion; - vertexRegion.setSize(fv.size()); - vertexRegion = 0; - - label region(1); - forAll(fv, vI) - if( !vertexTypes_[fv[vI]] && !vertexRegion[vI] ) - { - vertexRegion[vI] = region; - - label fcI = fv.fcIndex(vI); - label rcI = fv.rcIndex(vI); - bool found; - do - { - found = false; - if( !vertexTypes_[fv[fcI]] ) - { - vertexRegion[fcI] = region; - fcI = fv.fcIndex(fcI); - found = true; - } - - if( !vertexTypes_[fv[rcI]] ) - { - vertexRegion[rcI] = region; - rcI = fv.rcIndex(rcI); - found = true; - } - } while( found ); - - ++region; - } - - # ifdef DEBUGSmooth - Info << "Tolerance " << tol_ << endl; - Info << "Number of regions " << region-1 << endl; - Info << "Vertex regions " << vertexRegion << endl; - # endif - - if( region > 2 ) - { - //- there are more than two regions which need to be cut off - # ifdef DEBUGSmooth - forAll(fv, vI) - Info << "Distance for vertex " << fv[vI] << " is " - << vertexDistance_[fv[vI]] << endl; - # endif - - //- there should be only one cut-off region - //- there this region will be determined by the most negative - //- distance from plane - scalar minDist(VGREAT); - label minRegion(-1); - forAll(fv, vI) - if( vertexRegion[vI] && (vertexDistance_[fv[vI]] < minDist) ) - { - minDist = vertexDistance_[fv[vI]]; - minRegion = vertexRegion[vI]; - } - - forAll(vertexRegion, vI) - if( vertexRegion[vI] && (vertexRegion[vI] != minRegion) ) - { - vertexTypes_[fv[vI]] |= INPLANE; - } - } - else - { - forAll(fv, vI) - if( - (vertexTypes_[fv[vI]] & INPLANE) && - !vertexRegion[fv.rcIndex(vI)] && - !vertexRegion[fv.fcIndex(vI)] - ) - { - vertexTypes_[fv[vI]] ^= INPLANE; - vertexTypes_[fv[vI]] |= KEEP; - - # ifdef DEBUGSmooth - Info << "Node " << vI << " was INPLANE" << endl; - Info << "New type " << label(vertexTypes_[fv[vI]]) << endl; - # endif - } - } - - # ifdef DEBUGSmooth - forAll(fv, vI) - Info << "Vertex type for vertex " << fv[vI] << " is " - << label(vertexTypes_[fv[vI]]) << endl; - # endif - - //- create new points - const DynList<point, 64>& points = *pointsPtr_; - cPtsPtr_ = new DynList<point, 64>(); - newVertexLabel_ = -1; - origNumVertices_ = 0; - forAll(points, pI) - if( vertexTypes_[pI] ) - { - cPtsPtr_->append(points[pI]); - newVertexLabel_[pI] = origNumVertices_++; - } - - //- find new edges and continue creating faces - findNewEdges(); + // There must be only one, singly connected region which is cut off + // from the feasible region. This may not be the case if one operates in the + // range of computer tolerances. In order to resolve the tie it is necessary + // to find a single region which will be cut off from the feasible region. + // This will be done by finding the node with the most negative distance, + // and then start marking vertices connected to that vertex via an edge. + + # ifdef DEBUGSmooth + Info << "Starting tie break" << endl; + # endif + + //- delete pointer data + deleteDemandDrivenData(cPtsPtr_); + deleteDemandDrivenData(cEdgesPtr_); + deleteDemandDrivenData(cFacesPtr_); + + //- remove coincident vertices + //removeCoincidentVertices(); + + const DynList<edge, 128>& edges = *edgesPtr_; + + DynList<edge> faceEdges; + forAll(f, eI) + faceEdges.append(edges[f[eI]]); + + labelListList fvertices = sortEdgesIntoChains(faceEdges).sortedChains(); + if( fvertices.size() != 1 ) + { + valid_ = false; + return; + + Info << "Face vertices " << fvertices << endl; + FatalErrorIn + ( + "void meshUntangler::cutRegion::tieBreak(const face& f)" + ) << "Number of created faces is not 1 but " + << fvertices.size() << abort(FatalError); + } + + const labelList& fv = fvertices[0]; + + DynList<label, 64> vertexRegion; + vertexRegion.setSize(fv.size()); + vertexRegion = 0; + + label region(1); + forAll(fv, vI) + if( !vertexTypes_[fv[vI]] && !vertexRegion[vI] ) + { + vertexRegion[vI] = region; + + label fcI = fv.fcIndex(vI); + label rcI = fv.rcIndex(vI); + bool found; + do + { + found = false; + if( !vertexTypes_[fv[fcI]] ) + { + vertexRegion[fcI] = region; + fcI = fv.fcIndex(fcI); + found = true; + } + + if( !vertexTypes_[fv[rcI]] ) + { + vertexRegion[rcI] = region; + rcI = fv.rcIndex(rcI); + found = true; + } + } while( found ); + + ++region; + } + + # ifdef DEBUGSmooth + Info << "Tolerance " << tol_ << endl; + Info << "Number of regions " << region-1 << endl; + Info << "Vertex regions " << vertexRegion << endl; + # endif + + if( region > 2 ) + { + //- there are more than two regions which need to be cut off + # ifdef DEBUGSmooth + forAll(fv, vI) + Info << "Distance for vertex " << fv[vI] << " is " + << vertexDistance_[fv[vI]] << endl; + # endif + + //- there should be only one cut-off region + //- there this region will be determined by the most negative + //- distance from plane + scalar minDist(VGREAT); + label minRegion(-1); + forAll(fv, vI) + if( vertexRegion[vI] && (vertexDistance_[fv[vI]] < minDist) ) + { + minDist = vertexDistance_[fv[vI]]; + minRegion = vertexRegion[vI]; + } + + forAll(vertexRegion, vI) + if( vertexRegion[vI] && (vertexRegion[vI] != minRegion) ) + { + vertexTypes_[fv[vI]] |= INPLANE; + } + } + else + { + forAll(fv, vI) + if( + (vertexTypes_[fv[vI]] & INPLANE) && + !vertexRegion[fv.rcIndex(vI)] && + !vertexRegion[fv.fcIndex(vI)] + ) + { + vertexTypes_[fv[vI]] ^= INPLANE; + vertexTypes_[fv[vI]] |= KEEP; + + # ifdef DEBUGSmooth + Info << "Node " << vI << " was INPLANE" << endl; + Info << "New type " << label(vertexTypes_[fv[vI]]) << endl; + # endif + } + } + + # ifdef DEBUGSmooth + forAll(fv, vI) + Info << "Vertex type for vertex " << fv[vI] << " is " + << label(vertexTypes_[fv[vI]]) << endl; + # endif + + //- create new points + const DynList<point, 64>& points = *pointsPtr_; + cPtsPtr_ = new DynList<point, 64>(); + newVertexLabel_ = -1; + origNumVertices_ = 0; + forAll(points, pI) + if( vertexTypes_[pI] ) + { + cPtsPtr_->append(points[pI]); + newVertexLabel_[pI] = origNumVertices_++; + } + + //- find new edges and continue creating faces + findNewEdges(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.C index 287d21a9e3d21f9169f206bc4e1a944151f9a875..44c8d6ae289dad379d320efa2636b95b7840a158 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.H b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.H index ea7f7dc4f17d1882a008bdc5fac8928ad2dee384..c35bba4b8404b1cec42c6be267ea8b2e1e6ed230 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.H +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/quadricMetric/quadricMetric.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class quadricMetric diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.C index 3bd0b16b317fd135267831f1a1b785a729db3492..b0f40bf64829e14d09115d2003e99462a9ab7cc9 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.H b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.H index 3f83381c0808a2109f1974b022f445a6a87aad3d..f2338e00239a616cde40fda2bf2e97033b639d45 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.H +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/simplexSmoother/simplexSmoother.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class simplexSmoother Description Mesh smoothing without any topological changes. The vertex is put into - location which minimises the objective function. + location which minimises the objective function. SourceFiles simplexSmoother.C @@ -53,25 +52,25 @@ class partTetMeshSimplex; /*---------------------------------------------------------------------------*\ Class simplexSmoother Declaration \*---------------------------------------------------------------------------*/ - + //- class for volume optimizer class simplexSmoother { protected: - + // Protected data - //- mesh points - DynList<point, 128>& points_; - - //- list tets around the given vertex - const DynList<partTet, 128>& tets_; - - //- label of the point - const label pointI_; - - //- bound box - boundBox bb_; - + //- mesh points + DynList<point, 128>& points_; + + //- list tets around the given vertex + const DynList<partTet, 128>& tets_; + + //- label of the point + const label pointI_; + + //- bound box + boundBox bb_; + private: // Private member functions @@ -80,19 +79,19 @@ private: //- Disallow default bitwise assignment void operator=(const simplexSmoother&); - - public: - - // Constructor + + public: + + // Constructor //- construct from partTetMeshSimplex simplexSmoother(partTetMeshSimplex& simplex); - - // Destructor - virtual ~simplexSmoother(); - - // Member functions - //- improve the position of the centre node - virtual void optimizeNodePosition(const scalar tol = 0.001) = 0; + + // Destructor + virtual ~simplexSmoother(); + + // Member functions + //- improve the position of the centre node + virtual void optimizeNodePosition(const scalar tol = 0.001) = 0; }; diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.C index 380af374c3c03dcdd40d6d12cc0fd62119da6ead..f1f285676bc94dae51a45593f53530ce59e9f0af 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,142 +42,42 @@ namespace Foam volumeOptimizer::volumeOptimizer(partTetMeshSimplex& simplex) : simplexSmoother(simplex) -{ -} +{} volumeOptimizer::~volumeOptimizer() -{ -} - +{} + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Member functions void volumeOptimizer::optimizeNodePosition(const scalar tol) { - label iter(0); - point& p = points_[pointI_]; if( !bb_.contains(p) ) - p = 0.5 * (bb_.max() + bb_.min()); + p = 0.5 * (bb_.max() + bb_.min()); const scalar scale = 1.0 / bb_.mag(); forAll(points_, pI) points_[pI] *= scale; + bb_.min() *= scale; + bb_.max() *= scale; + + //- find the optimum using divide and conquer + const scalar func = optimiseDivideAndConquer(tol); + const point copyP = p; + + //- check if the location can be improved using the steepest descent + const scalar funcAfter = optimiseSteepestDescent(tol); + + if( funcAfter > func ) + p = copyP; - # ifdef DEBUGSmooth - Info << nl << "Smoothing point " << pointI_ << " with coordinates " << p << endl; - scalar Vmina(VGREAT); - forAll(tets_, tetI) - Vmina = Foam::min(Vmina, tets_[tetI].mag(points_)); - Info << "Vmin before " << Vmina << endl; - # endif - - vector gradF; - vector disp(vector::zero); - tensor gradGradF; - point pOrig; - - scalar funcBefore, funcAfter(evaluateFunc()); - - bool finished; - do - { - finished = false; - pOrig = p; - funcBefore = funcAfter; - - evaluateGradientsExact(gradF, gradGradF); - - const scalar determinant = Foam::det(gradGradF); - if( determinant > SMALL ) - { - disp = (inv(gradGradF, determinant) & gradF); - - p -= disp; - - funcAfter = evaluateFunc(); - - # ifdef DEBUGSmooth - Info << nl << "gradF " << gradF << endl; - Info << "gradGradF " << gradGradF << endl; - Info << "det(gradGradF) " << determinant << endl; - Info << "disp " << disp << endl; - Info << "Func before " << funcBefore << endl; - Info << "Func after " << funcAfter << endl; - # endif - - scalar relax(0.8); - label nLoops(0); - - while( funcAfter > funcBefore ) - { - p = pOrig - relax * disp; - relax *= 0.5; - funcAfter = evaluateFunc(); - - if( funcAfter < funcBefore ) - continue; - - if( ++nLoops == 5 ) - { - //- it seems that this direction is wrong, stop the loop - p = pOrig; - disp = vector::zero; - finished = true; - funcAfter = funcBefore; - } - } - - if( mag(funcBefore - funcAfter) / funcBefore < tol ) - finished = true; - } - else - { - //- move in random direction - //- this is usually needed to move the point off the zero volume - disp = vector::zero; - forAll(tets_, tetI) - { - const partTet& tet = tets_[tetI]; - const scalar Vtri = tet.mag(points_); - - if( Vtri < SMALL ) - { - triangle<point, point> tri - ( - points_[tet.a()], - points_[tet.b()], - points_[tet.c()] - ); - - vector n = tri.normal(); - const scalar d = mag(n); - - if( d > VSMALL ) - disp += 0.01 * (n / d); - } - } - - p += disp; - funcAfter = evaluateFunc(); - } - } while( (++iter < 10) && !finished ); - - # ifdef DEBUGSmooth - scalar Vmin(VGREAT); - forAll(tets_, tetI) - Vmin = Foam::min(Vmin, tets_[tetI].mag(points_)); - - Info << nl << "New coordinates for point " - << pointI_ << " are " << p << endl; - Info << "Num iterations " << iter << " gradient " << gradF << endl; - Info << "Vmin " << Vmin << endl; - # endif - //- scale back to the original size forAll(points_, pI) points_[pI] /= scale; + bb_.min() /= scale; + bb_.max() /= scale; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.H b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.H index 5fcfbcf1ee4ba321251b9fb27738b2c0fc81690a..b95e55236925f9fa51b7a6fdbdd69311aa9d9b39 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.H +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizer.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class volumeOptimizer Description Mesh smoothing without any topological changes. The vertex is put into - location which minimises the objective function. + location which minimises the objective function. SourceFiles volumeOptimizer.C @@ -43,41 +42,47 @@ SourceFiles namespace Foam { - + // Forward declarations class partTetMeshSimplex; /*---------------------------------------------------------------------------*\ Class volumeOptimizer Declaration \*---------------------------------------------------------------------------*/ - + //- class for volume optimizer class volumeOptimizer : public simplexSmoother { - // Private member functions - //- evaluate functional - scalar evaluateFunc() const; - - //- find appropriate value of K - scalar evaluateStabilisationFactor() const; - - //- evaluate gradients of the functional - void evaluateGradientsExact(vector&, tensor&) const; - - public: - - // Constructor + // Private member functions + //- evaluate functional + scalar evaluateFunc() const; + + //- find appropriate value of K + scalar evaluateStabilisationFactor() const; + + //- evaluate gradients of the functional + void evaluateGradientsExact(vector&, tensor&) const; + + //- optimize position using a divide and conquer algorithm + scalar optimiseDivideAndConquer(const scalar tol); + + //- optimise using the steepest descent + scalar optimiseSteepestDescent(const scalar tol); + + public: + + // Constructor //- construct from partTetMeshSimplex volumeOptimizer(partTetMeshSimplex& simplex); - - // Destructor - ~volumeOptimizer(); - - // Member functions - //- find the best position for the node - void optimizeNodePosition(const scalar tol = 0.001); + + // Destructor + ~volumeOptimizer(); + + // Member functions + //- find the best position for the node + void optimizeNodePosition(const scalar tol = 0.001); }; diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizerEvaluateGradients.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizerEvaluateGradients.C index 77c73ac7cd3f0be2133475d27b27a4536f1d8f54..f4e6f1493094a1d14f502c0b6c4ecdbb8f24ca41 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizerEvaluateGradients.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/advancedSmoothers/volumeOptimizer/volumeOptimizerEvaluateGradients.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,153 +41,376 @@ namespace Foam scalar volumeOptimizer::evaluateFunc() const { const scalar K = evaluateStabilisationFactor(); - - scalar func(0.0); - - forAll(tets_, tetI) - { - const partTet& pt = tets_[tetI]; - const tetrahedron<point, point> tet - ( - points_[pt.a()], - points_[pt.b()], - points_[pt.c()], - points_[pt.d()] - ); - - const scalar LSqrTri - ( - magSqr(tet.d() - tet.a()) + - magSqr(tet.d() - tet.b()) + - magSqr(tet.d() - tet.c()) - ); - - const scalar Vtri = tet.mag(); - const scalar Vstab = 0.5 * (Vtri + mag(Vtri)) + K; - - func += LSqrTri / pow(Vstab, 2./3.); - } - - return func; + + scalar func(0.0); + + forAll(tets_, tetI) + { + const partTet& pt = tets_[tetI]; + const tetrahedron<point, point> tet + ( + points_[pt.a()], + points_[pt.b()], + points_[pt.c()], + points_[pt.d()] + ); + + const scalar LSqrTri + ( + magSqr(tet.d() - tet.a()) + + magSqr(tet.d() - tet.b()) + + magSqr(tet.d() - tet.c()) + ); + + const scalar Vtri = tet.mag(); + const scalar stab = sqrt(sqr(Vtri) + K); + const scalar Vstab = 0.5 * (Vtri + stab); + + func += LSqrTri / pow(Vstab, 2./3.); + } + + return func; } scalar volumeOptimizer::evaluateStabilisationFactor() const { - scalar K = 0.0; - - scalar Vmin(VGREAT), LSqMax(0.0); - - forAll(tets_, tetI) - { - const partTet& pt = tets_[tetI]; - const tetrahedron<point, point> tet - ( - points_[pt.a()], - points_[pt.b()], - points_[pt.c()], - points_[pt.d()] - ); - - const scalar Vtri = tet.mag(); - + scalar K = 0.0; + + scalar Vmin(VGREAT), LSqMax(0.0); + + forAll(tets_, tetI) + { + const partTet& pt = tets_[tetI]; + const tetrahedron<point, point> tet + ( + points_[pt.a()], + points_[pt.b()], + points_[pt.c()], + points_[pt.d()] + ); + + const scalar Vtri = tet.mag(); + Vmin = Foam::min(Vmin, Vtri); - + const scalar LSqrTri - ( - magSqr(tet.d() - tet.a()) + - magSqr(tet.d() - tet.b()) + - magSqr(tet.d() - tet.c()) - ); - + ( + magSqr(tet.d() - tet.a()) + + magSqr(tet.d() - tet.b()) + + magSqr(tet.d() - tet.c()) + ); + LSqMax = Foam::max(LSqMax, LSqrTri); - } - - if( Vmin < SMALL * LSqMax ) + } + + if( Vmin < SMALL * LSqMax ) K = SMALL * LSqMax; - - return K; + + return K; } void volumeOptimizer::evaluateGradientsExact ( - vector& gradF, - tensor& gradGradF + vector& gradF, + tensor& gradGradF ) const { - gradF = vector::zero; - gradGradF = tensor::zero; - + gradF = vector::zero; + gradGradF = tensor::zero; + const scalar K = evaluateStabilisationFactor(); - - tensor gradGradLsq(tensor::zero); - gradGradLsq.xx() = 6.0; - gradGradLsq.yy() = 6.0; - gradGradLsq.zz() = 6.0; - - const point& p = points_[pointI_]; - - forAll(tets_, tetI) - { - const partTet& pt = tets_[tetI]; - const tetrahedron<point, point> tet - ( - points_[pt.a()], - points_[pt.b()], - points_[pt.c()], - points_[pt.d()] - ); - - const vector B - ( - (1.0/6.0) * - ( - (tet.b() - tet.a()) ^ - (tet.c() - tet.a()) - ) - ); - - //- add this trihedron to the metric - const scalar LSqrTri - ( - magSqr(tet.d() - tet.a()) + - magSqr(tet.d() - tet.b()) + - magSqr(tet.d() - tet.c()) - ); - - const scalar Vtri = tet.mag(); - - //- evaluate gradients - const scalar Vstab = 0.5 * (Vtri + mag(Vtri)) + K; - - if( Vstab < VSMALL ) - { - Info << "Tet " << tet << endl; - Info << "B " << B << endl; - Info << "Vtri " << Vtri << endl; - IOstream::defaultPrecision(20); - Info << "Vstab " << Vstab << endl; - - FatalErrorIn - ( - "void nodeDisplacementVolumeOptimizer()" - ) << "I cannot continue " << exit(FatalError); - } - - const vector gradLsq = 2. * (3. * p - tet.a() - tet.b() - tet.c()); - const vector gradVstab = 0.5 * (B + Foam::sign(Vtri) * B); - - //- calculate the gradients - const scalar Vs = pow(Vstab, 2./3.) + VSMALL; - const scalar Vs53 = Vs * Vstab + VSMALL; - - gradF += (gradLsq / Vs) - (2./3. * LSqrTri * gradVstab / Vs53); - - //- calculate the second gradient - gradGradF += - 10./9. * LSqrTri * (gradVstab * gradVstab) / (Vstab * Vs53 + VSMALL) - - 2./3. * twoSymm(gradLsq * gradVstab) / Vs53 - + gradGradLsq / Vs; - } + + tensor gradGradLsq(tensor::zero); + gradGradLsq.xx() = 6.0; + gradGradLsq.yy() = 6.0; + gradGradLsq.zz() = 6.0; + + const point& p = points_[pointI_]; + + const scalar C = 2./3. * pow(0.5, 2./3.); + const scalar C1 = C / 3.; + + forAll(tets_, tetI) + { + const partTet& pt = tets_[tetI]; + const tetrahedron<point, point> tet + ( + points_[pt.a()], + points_[pt.b()], + points_[pt.c()], + points_[pt.d()] + ); + + //- calculate the gradient of the volume + const vector gradV + ( + (1.0/6.0) * + ( + (tet.b() - tet.a()) ^ + (tet.c() - tet.a()) + ) + ); + + //- calculate the Frobenius norm + const scalar LSqrTri + ( + magSqr(tet.d() - tet.a()) + + magSqr(tet.d() - tet.b()) + + magSqr(tet.d() - tet.c()) + ); + + //- calculate the volume of the tetrahedron + const scalar Vtri = tet.mag(); + + //- calculate the stabilisation factor for the volume + const scalar stab = sqrt(sqr(Vtri) + K); + + //- evaluate the stabilised volume + const scalar Vs = 0.5 * (Vtri + stab); + + if( Vs < VSMALL ) + { + Info << "Tet " << tet << endl; + Info << "gradV " << gradV << endl; + Info << "Vtri " << Vtri << endl; + IOstream::defaultPrecision(20); + Info << "Vstab " << Vs << endl; + + FatalErrorIn + ( + "void nodeDisplacementVolumeOptimizer()" + ) << "I cannot continue " << exit(FatalError); + } + + //- calculate the gradient of the stabilisation volume + const vector gradStab = Vtri * gradV / stab; + + //- calculate the gradient of the Frobenius norm + const vector gradLsq = 2. * (3. * p - tet.a() - tet.b() - tet.c()); + + //- calculate the gradient of the stabilised volume + const vector gradVs = 0.5 * (gradV + gradStab); + + //- calculate the gradient of the functional + const scalar Vs13 = pow(2. * Vs, 1./3.); + const scalar Vstab = pow(Vs, 2./3.); + const scalar sqrVstab = sqr(Vstab); + const vector gradVstab = C * (2. * gradVs) / Vs13; + + gradF += gradLsq / Vstab - LSqrTri * gradVstab / sqrVstab; + + //- calculate the second gradient of the stabilisation volume + const tensor gradGradStab = + (gradV * gradV) / stab - + sqr(Vtri) * (gradV * gradV) / pow(stab, 3); + + //- calculate the second gradient of the stabilised volume + + const tensor gradGradVstab = + C * (gradGradStab / Vs13) - + C1 * 4. * (gradVs * gradVs) / pow(Vs13, 4); + + //- calculate the second gradient + gradGradF += + gradGradLsq / Vstab - + twoSymm(gradLsq * (gradVstab / sqrVstab)) - + LSqrTri * gradGradVstab / sqrVstab + + 2.0 * LSqrTri * (gradVstab * gradVstab) / (sqrVstab * Vstab); + } +} + +scalar volumeOptimizer::optimiseDivideAndConquer(const scalar tol) +{ + point& pOpt = points_[pointI_]; + + pOpt = 0.5 * (bb_.max() + bb_.min()); + point currCentre = pOpt; + scalar dx = (bb_.max().x() - bb_.min().x()) / 2.0; + scalar dy = (bb_.max().y() - bb_.min().y()) / 2.0; + scalar dz = (bb_.max().z() - bb_.min().z()) / 2.0; + + FixedList<vector, 8> dirVecs; + dirVecs[0] = vector(-1.0, -1.0, -1.0); + dirVecs[1] = vector(1.0, -1.0, -1.0); + dirVecs[2] = vector(-1.0, 1.0, -1.0); + dirVecs[3] = vector(1.0, 1.0, -1.0); + dirVecs[4] = vector(-1.0, -1.0, 1.0); + dirVecs[5] = vector(1.0, -1.0, 1.0); + dirVecs[6] = vector(-1.0, 1.0, 1.0); + dirVecs[7] = vector(1.0, 1.0, 1.0); + + label iter(0); + + //- find the value of the functional in the centre of the bnd box + scalar funcBefore, funcAfter(evaluateFunc()); + + do + { + funcBefore = funcAfter; + + funcAfter = VGREAT; + point minCentre(vector::zero); + + forAll(dirVecs, i) + { + pOpt.x() = currCentre.x() + 0.5 * dirVecs[i].x() * dx; + pOpt.y() = currCentre.y() + 0.5 * dirVecs[i].y() * dy; + pOpt.z() = currCentre.z() + 0.5 * dirVecs[i].z() * dz; + + const scalar func = evaluateFunc(); + + if( func < funcAfter ) + { + minCentre = pOpt; + funcAfter = func; + } + } + + //- set the centre with the minimum value + //- as the centre for future search + currCentre = minCentre; + pOpt = minCentre; + + //- halve the search range + dx *= 0.5; + dy *= 0.5; + dz *= 0.5; + + //- calculate the tolerence + const scalar t = mag(funcAfter - funcBefore) / funcAfter; + + # ifdef DEBUGSmooth + Info << "Point position " << pOpt << endl; + Info << "Func before " << funcBefore << endl; + Info << "Func after " << funcAfter << endl; + Info << "Normalised difference " << t << endl; + # endif + + if( t < tol ) + break; + } while( ++iter < 100 ); + + return funcAfter; +} + +scalar volumeOptimizer::optimiseSteepestDescent(const scalar tol) +{ + label iter(0); + + point& p = points_[pointI_]; + + # ifdef DEBUGSmooth + Info << nl << "Smoothing point " << pointI_ + << " with coordinates " << p << endl; + scalar Vmina(VGREAT); + forAll(tets_, tetI) + Vmina = Foam::min(Vmina, tets_[tetI].mag(points_)); + Info << "Vmin before " << Vmina << endl; + # endif + + vector gradF; + vector disp(vector::zero); + tensor gradGradF; + point pOrig; + + scalar funcBefore, funcAfter(evaluateFunc()); + + bool finished; + do + { + finished = false; + pOrig = p; + funcBefore = funcAfter; + + evaluateGradientsExact(gradF, gradGradF); + + const scalar determinant = Foam::det(gradGradF); + if( determinant > SMALL ) + { + disp = (inv(gradGradF, determinant) & gradF); + + p -= disp; + + funcAfter = evaluateFunc(); + + # ifdef DEBUGSmooth + Info << nl << "gradF " << gradF << endl; + Info << "gradGradF " << gradGradF << endl; + Info << "det(gradGradF) " << determinant << endl; + Info << "disp " << disp << endl; + Info << "Func before " << funcBefore << endl; + Info << "Func after " << funcAfter << endl; + # endif + + scalar relax(0.8); + label nLoops(0); + + while( funcAfter > funcBefore ) + { + p = pOrig - relax * disp; + relax *= 0.5; + funcAfter = evaluateFunc(); + + if( funcAfter < funcBefore ) + continue; + + if( ++nLoops == 5 ) + { + //- it seems that this direction is wrong, stop the loop + p = pOrig; + disp = vector::zero; + finished = true; + funcAfter = funcBefore; + } + } + + if( mag(funcBefore - funcAfter) / funcBefore < tol ) + finished = true; + } + else + { + //- move in random direction + //- this is usually needed to move the point off the zero volume + disp = vector::zero; + forAll(tets_, tetI) + { + const partTet& tet = tets_[tetI]; + const scalar Vtri = tet.mag(points_); + + if( Vtri < SMALL ) + { + triangle<point, point> tri + ( + points_[tet.a()], + points_[tet.b()], + points_[tet.c()] + ); + + vector n = tri.normal(); + const scalar d = mag(n); + + if( d > VSMALL ) + disp += 0.01 * (n / d); + } + } + + p += disp; + funcAfter = evaluateFunc(); + } + } while( (++iter < 100) && !finished ); + + # ifdef DEBUGSmooth + scalar Vmin(VGREAT); + forAll(tets_, tetI) + Vmin = Foam::min(Vmin, tets_[tetI].mag(points_)); + + Info << nl << "New coordinates for point " + << pointI_ << " are " << p << endl; + Info << "Num iterations " << iter << " gradient " << gradF << endl; + Info << "Vmin " << Vmin << endl; + # endif + + return funcAfter; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.C index 1761df874397046d209eebfe7f340afc4557e9ee..167269ff677d1970d2ff9754bb210c1051b9c416 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -38,7 +37,10 @@ Description #include "knuppMetric.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif // #define DEBUGSearch @@ -53,14 +55,12 @@ namespace Foam tetMeshOptimisation::tetMeshOptimisation(partTetMesh& mesh) : tetMesh_(mesh) -{ -} +{} // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // tetMeshOptimisation::~tetMeshOptimisation() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -74,8 +74,10 @@ void tetMeshOptimisation::optimiseUsingKnuppMetric() //- try getting rid of negative volume using the Patrik Knupp's metric //- which gets non-negative contributions from invertex tets, only + # ifdef USE_OMP # pragma omp parallel for if( tets.size() > 100 ) \ schedule(dynamic, 10) + # endif forAll(tets, tetI) { invertedTets[tetI] = false; @@ -91,8 +93,10 @@ void tetMeshOptimisation::optimiseUsingKnuppMetric() //- find the number of inverted tets nNegative = 0; negativeNode = false; + # ifdef USE_OMP # pragma omp parallel for if( tets.size() > 100 ) \ schedule(dynamic, 10) reduction(+ : nNegative) + # endif forAll(invertedTets, tetI) { if( invertedTets[tetI] ) @@ -116,8 +120,11 @@ void tetMeshOptimisation::optimiseUsingKnuppMetric() //- smooth the mesh List<LongList<labelledPoint> > newPositions; + # ifdef USE_OMP # pragma omp parallel if( smoothVertex.size() > 100 ) + # endif { + # ifdef USE_OMP # pragma omp master { newPositions.setSize(omp_get_num_threads()); @@ -126,8 +133,14 @@ void tetMeshOptimisation::optimiseUsingKnuppMetric() # pragma omp barrier LongList<labelledPoint>& np = newPositions[omp_get_thread_num()]; + # else + newPositions.setSize(1); + LongList<labelledPoint>& np = newPositions[0]; + # endif + # ifdef USE_OMP # pragma omp for schedule(dynamic, 10) + # endif forAll(smoothVertex, nodeI) { if( !negativeNode[nodeI] ) @@ -156,8 +169,11 @@ void tetMeshOptimisation::optimiseUsingKnuppMetric() boolList helper(invertedTets.size()); nNegativeBefore = nNegative; nNegative = 0; + + # ifdef USE_OMP # pragma omp parallel for if( tets.size() > 100 ) \ schedule(dynamic, 10) reduction(+ : nNegative) + # endif forAll(tets, tetI) { helper[tetI] = false; @@ -190,8 +206,10 @@ void tetMeshOptimisation::optimiseUsingMeshUntangler() boolList negativeNode(smoothVertex.size()), invertedTets(tets.size()); //- try getting rid of negative volume using the untangler + # ifdef USE_OMP # pragma omp parallel for if( tets.size() > 100 ) \ schedule(dynamic, 10) + # endif forAll(tets, tetI) { invertedTets[tetI] = false; @@ -207,8 +225,10 @@ void tetMeshOptimisation::optimiseUsingMeshUntangler() //- find the number of inverted tets nNegative = 0; negativeNode = false; + # ifdef USE_OMP # pragma omp parallel for if( tets.size() > 100 ) \ schedule(dynamic, 10) reduction(+ : nNegative) + # endif forAll(invertedTets, tetI) { if( invertedTets[tetI] ) @@ -232,8 +252,11 @@ void tetMeshOptimisation::optimiseUsingMeshUntangler() //- smooth the mesh List<LongList<labelledPoint> > newPositions; + # ifdef USE_OMP # pragma omp parallel if( smoothVertex.size() > 100 ) + # endif { + # ifdef USE_OMP # pragma omp master { newPositions.setSize(omp_get_num_threads()); @@ -242,8 +265,14 @@ void tetMeshOptimisation::optimiseUsingMeshUntangler() # pragma omp barrier LongList<labelledPoint>& np = newPositions[omp_get_thread_num()]; + # else + newPositions.setSize(1); + LongList<labelledPoint>& np = newPositions[0]; + # endif + # ifdef USE_OMP # pragma omp for schedule(dynamic, 10) + # endif forAll(smoothVertex, nodeI) { if( !negativeNode[nodeI] ) @@ -272,8 +301,10 @@ void tetMeshOptimisation::optimiseUsingMeshUntangler() boolList helper(invertedTets.size()); nNegativeBefore = nNegative; nNegative = 0; + # ifdef USE_OMP # pragma omp parallel for if( tets.size() > 100 ) \ schedule(dynamic, 10) reduction(+ : nNegative) + # endif forAll(tets, tetI) { helper[tetI] = false; @@ -305,8 +336,11 @@ void tetMeshOptimisation::optimiseUsingVolumeOptimizer() { List<LongList<labelledPoint> > newPositions; + # ifdef USE_OMP # pragma omp parallel if( smoothVertex.size() > 100 ) + # endif { + # ifdef USE_OMP # pragma omp master { newPositions.setSize(omp_get_num_threads()); @@ -315,8 +349,14 @@ void tetMeshOptimisation::optimiseUsingVolumeOptimizer() # pragma omp barrier LongList<labelledPoint>& np = newPositions[omp_get_thread_num()]; + # else + newPositions.setSize(1); + LongList<labelledPoint>& np = newPositions[0]; + # endif + # ifdef USE_OMP # pragma omp for schedule(dynamic, 10) + # endif forAll(smoothVertex, nodeI) if( smoothVertex[nodeI] & partTetMesh::SMOOTH ) { @@ -349,19 +389,31 @@ void tetMeshOptimisation::optimiseBoundaryVolumeOptimizer const LongList<point>& points = tetMesh_.points(); const LongList<direction>& smoothVertex = tetMesh_.smoothVertex(); + # ifdef USE_OMP label nThreads = omp_get_num_procs(); if( smoothVertex.size() < 100 ) nThreads = 1; + # else + const label nThreads(1); + # endif for(label i=0;i<3;++i) { List<LongList<labelledPoint> > newPositions(nThreads); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP LongList<labelledPoint>& np = newPositions[omp_get_thread_num()]; + # else + LongList<labelledPoint>& np = newPositions[0]; + # endif + # ifdef USE_OMP # pragma omp for schedule(dynamic, 5) + # endif forAll(smoothVertex, nodeI) if( smoothVertex[nodeI] & partTetMesh::BOUNDARY ) { @@ -479,20 +531,32 @@ void tetMeshOptimisation::optimiseBoundarySurfaceLaplace() { const LongList<direction>& smoothVertex = tetMesh_.smoothVertex(); + # ifdef USE_OMP label nThreads = omp_get_num_procs(); if( smoothVertex.size() < 1000 ) nThreads = 1; + # else + const label nThreads(1); + # endif for(label i=0;i<3;++i) { List<LongList<labelledPoint> > newPositions(nThreads); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP LongList<labelledPoint>& np = newPositions[omp_get_thread_num()]; + # else + LongList<labelledPoint>& np = newPositions[0]; + # endif + # ifdef USE_OMP # pragma omp for schedule(dynamic, 5) + # endif forAll(smoothVertex, nodeI) { if( smoothVertex[nodeI] & partTetMesh::BOUNDARY ) diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.H b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.H index 5edc32da435b27f4b7a2e95f77b0dddd93e5a6d4..d1892e68d5f62e1bf01b8acdede03b3dd89a2da6 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.H +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisation.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class tetMeshOptimisation @@ -39,7 +38,7 @@ SourceFiles #include "DynList.H" #include "parPartTet.H" #include "boundBox.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "boolList.H" #include <map> @@ -61,7 +60,7 @@ class tetMeshOptimisation { // Private data //- reference to the tet mesh - partTetMesh& tetMesh_; + partTetMesh& tetMesh_; // Private member functions needed for parallel runs //- make sure that all processors have the same points diff --git a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisationParallel.C b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisationParallel.C index 2a70ed3e5511045b7c3cd8f32147137fe00ab7b1..52da933051d8becb3a92e4b45dbbebdc61529cc3 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisationParallel.C +++ b/meshLibrary/utilities/smoothers/geometry/meshOptimizer/tetMeshOptimisation/tetMeshOptimisationParallel.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -47,42 +46,42 @@ void tetMeshOptimisation::unifyNegativePoints(boolList& negativeNode) const //- where they exist const LongList<direction>& smoothVertex = tetMesh_.smoothVertex(); const DynList<label>& neiProcs = tetMesh_.neiProcs(); - const labelListPMG& globalPointLabel = tetMesh_.globalPointLabel(); + const labelLongList& globalPointLabel = tetMesh_.globalPointLabel(); const VRWGraph& pProcs = tetMesh_.pointAtProcs(); const Map<label>& globalToLocal = tetMesh_.globalToLocalPointAddressing(); - const labelListPMG& pAtParallelBoundaries = - tetMesh_.pointsAtProcessorBoundaries(); - - std::map<label, labelListPMG> selectedNegativeNodes; + const labelLongList& pAtParallelBoundaries = + tetMesh_.pointsAtProcessorBoundaries(); + + std::map<label, labelLongList> selectedNegativeNodes; forAll(neiProcs, procI) selectedNegativeNodes.insert ( - std::make_pair(neiProcs[procI], labelListPMG()) + std::make_pair(neiProcs[procI], labelLongList()) ); - + forAll(pAtParallelBoundaries, i) { const label nI = pAtParallelBoundaries[i]; - + if( !negativeNode[nI] ) continue; if( !(smoothVertex[nI] & partTetMesh::PARALLELBOUNDARY) ) continue; - + forAllRow(pProcs, nI, procI) { const label neiProc = pProcs(nI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - + selectedNegativeNodes[neiProc].append(globalPointLabel[nI]); } } - - labelListPMG receivedNodes; + + labelLongList receivedNodes; help::exchangeMap(selectedNegativeNodes, receivedNodes); - + forAll(receivedNodes, i) negativeNode[globalToLocal[receivedNodes[i]]] = true; } @@ -94,16 +93,16 @@ void tetMeshOptimisation::exchangeData ) { const DynList<label>& neiProcs = tetMesh_.neiProcs(); - const labelListPMG& globalPointLabel = tetMesh_.globalPointLabel(); + const labelLongList& globalPointLabel = tetMesh_.globalPointLabel(); const VRWGraph& pProcs = tetMesh_.pointAtProcs(); const Map<label>& globalToLocal = tetMesh_.globalToLocalPointAddressing(); - const labelListPMG& pAtParallelBoundaries = - tetMesh_.pointsAtProcessorBoundaries(); - + const labelLongList& pAtParallelBoundaries = + tetMesh_.pointsAtProcessorBoundaries(); + const LongList<point>& points = tetMesh_.points(); const LongList<direction>& smoothVertex = tetMesh_.smoothVertex(); const LongList<partTet>& tets = tetMesh_.tets(); - + //- create the map holding data which will be sent to other procs std::map<label, LongList<parPartTet> > exchangeData; forAll(neiProcs, procI) @@ -111,41 +110,41 @@ void tetMeshOptimisation::exchangeData ( std::make_pair(neiProcs[procI], LongList<parPartTet>()) ); - - //- create storage in the m map + + //- create storage in the m map m.clear(); - forAll(pAtParallelBoundaries, i) - { - const label pI = pAtParallelBoundaries[i]; - if( !(smoothVertex[pI] & partTetMesh::SMOOTH) ) - continue; + forAll(pAtParallelBoundaries, i) + { + const label pI = pAtParallelBoundaries[i]; + if( !(smoothVertex[pI] & partTetMesh::SMOOTH) ) + continue; if( negativeNodePtr && !(*negativeNodePtr)[pI] ) continue; - - m.insert(std::make_pair(pI, DynList<parPartTet>(12))); - } - - //- store local data into the maps - forAll(tets, tetI) + + m.insert(std::make_pair(pI, DynList<parPartTet>())); + } + + //- store local data into the maps + forAll(tets, tetI) { const partTet& tet = tets[tetI]; - - DynList<label> sendToProcs(3); + + DynList<label> sendToProcs; for(label i=0;i<4;++i) { const label vI = tet[i]; - + if( pProcs.sizeOfRow(vI) == 0 ) continue; if( !(smoothVertex[vI] & partTetMesh::SMOOTH) ) continue; if( negativeNodePtr && !(*negativeNodePtr)[vI] ) continue; - + //- add processor labels forAllRow(pProcs, vI, procI) sendToProcs.appendIfNotIn(pProcs(vI, procI)); - + //- add data into the map of proc bnd points DynList<parPartTet>& data = m[vI]; data.append @@ -159,16 +158,16 @@ void tetMeshOptimisation::exchangeData ) ); } - + if( sendToProcs.size() != 0 ) { - //- add data into the map + //- add data into the map forAll(sendToProcs, procI) { const label neiProc = sendToProcs[procI]; if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append ( parPartTet @@ -182,19 +181,19 @@ void tetMeshOptimisation::exchangeData } } } - + //- exchange data with other processors LongList<parPartTet> receivedData; help::exchangeMap(exchangeData, receivedData); - + forAll(receivedData, i) { const parPartTet& tet = receivedData[i]; - + for(label i=0;i<4;++i) { const label gpI = tet[i].pointLabel(); - + if( globalToLocal.found(gpI) && (smoothVertex[globalToLocal[gpI]] &partTetMesh::SMOOTH) @@ -210,12 +209,12 @@ void tetMeshOptimisation::exchangeData void tetMeshOptimisation::updateBufferLayerPoints() { const LongList<point>& points = tetMesh_.points(); - const labelListPMG& bufferLayerPoints = tetMesh_.bufferLayerPoints(); + const labelLongList& bufferLayerPoints = tetMesh_.bufferLayerPoints(); const VRWGraph& pProcs = tetMesh_.pointAtProcs(); - const labelListPMG& globalPointLabel = tetMesh_.globalPointLabel(); + const labelLongList& globalPointLabel = tetMesh_.globalPointLabel(); const Map<label>& globalToLocal = tetMesh_.globalToLocalPointAddressing(); const DynList<label>& neiProcs = tetMesh_.neiProcs(); - + //- create the map std::map<label, LongList<labelledPoint> > exchangeData; forAll(neiProcs, i) @@ -223,33 +222,33 @@ void tetMeshOptimisation::updateBufferLayerPoints() ( std::make_pair(neiProcs[i], LongList<labelledPoint>()) ); - + //- add points into the map forAll(bufferLayerPoints, pI) { const label pointI = bufferLayerPoints[pI]; - + forAllRow(pProcs, pointI, i) { const label neiProc = pProcs(pointI, i); - + if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append ( labelledPoint(globalPointLabel[pointI], points[pointI]) ); } } - + LongList<labelledPoint> receivedData; help::exchangeMap(exchangeData, receivedData); - + forAll(receivedData, i) { const labelledPoint& lp = receivedData[i]; - + tetMesh_.updateVertex ( globalToLocal[lp.pointLabel()], @@ -267,11 +266,11 @@ void tetMeshOptimisation::unifyCoordinatesParallel const DynList<label>& neiProcs = tetMesh_.neiProcs(); const VRWGraph& pProcs = tetMesh_.pointAtProcs(); const Map<label>& globalToLocal = tetMesh_.globalToLocalPointAddressing(); - const labelListPMG& globalPointLabel = tetMesh_.globalPointLabel(); + const labelLongList& globalPointLabel = tetMesh_.globalPointLabel(); const LongList<direction>& smoothVertex = tetMesh_.smoothVertex(); - const labelListPMG& pAtParallelBoundaries = + const labelLongList& pAtParallelBoundaries = tetMesh_.pointsAtProcessorBoundaries(); - + //- create the map std::map<label, LongList<labelledPoint> > exchangeData; forAll(neiProcs, procI) @@ -279,53 +278,53 @@ void tetMeshOptimisation::unifyCoordinatesParallel ( std::make_pair(neiProcs[procI], LongList<labelledPoint>()) ); - + //- fill in the data std::map<label, labelledPoint> parallelBndPoints; forAll(pAtParallelBoundaries, i) { - const label pI = pAtParallelBoundaries[i]; - + const label pI = pAtParallelBoundaries[i]; + if( !(smoothVertex[pI] & partTetMesh::PARALLELBOUNDARY) ) continue; - + parallelBndPoints[pI] = labelledPoint(1, points[pI]); - + if( negativeNodePtr && !(*negativeNodePtr)[pI] ) continue; - + forAllRow(pProcs, pI, procI) { const label neiProc = pProcs(pI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append ( labelledPoint(globalPointLabel[pI], points[pI]) ); } } - + //- send points to other processors LongList<labelledPoint> receivedData; help::exchangeMap(exchangeData, receivedData); - + //- gather the data forAll(receivedData, i) { const labelledPoint& lp = receivedData[i]; - + std::map<label, labelledPoint>::iterator iter = parallelBndPoints.find(globalToLocal[lp.pointLabel()]); - + if( iter == parallelBndPoints.end() ) continue; - + ++iter->second.pointLabel(); iter->second.coordinates() += lp.coordinates(); } - + //- move the point to the averaged position for ( @@ -335,7 +334,7 @@ void tetMeshOptimisation::unifyCoordinatesParallel ) { const label pI = it->first; - + const point newP = it->second.coordinates() / it->second.pointLabel(); tetMesh_.updateVertex(pI, newP); } diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.C b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.C index f04e3b784194cdd812f2f0bf5df2c6f429c6fa9b..09ab1f6351ce799e9fac6f146f5e8573042c4564 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.C +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,9 +35,314 @@ Description namespace Foam { - + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +scalar surfaceOptimizer::evaluateStabilisationFactor() const +{ + //- find the minimum area + scalar Amin(VGREAT), LsqMax(0.0); + forAll(trias_, triI) + { + const point& p0 = pts_[trias_[triI][0]]; + const point& p1 = pts_[trias_[triI][1]]; + const point& p2 = pts_[trias_[triI][2]]; + + const scalar Atri = + 0.5 * + ( + (p1.x() - p0.x()) * (p2.y() - p0.y()) - + (p2.x() - p0.x()) * (p1.y() - p0.y()) + ); + + # ifdef DEBUGSmooth + Info << "Triangle " << triI << " area " << Atri << endl; + # endif + + const scalar LSqrTri + ( + magSqr(p0 - p1) + + magSqr(p2 - p0) + ); + + Amin = Foam::min(Amin, Atri); + LsqMax = Foam::max(LsqMax, LSqrTri); + } + + # ifdef DEBUGSmooth + Info << "Amin " << Amin << endl; + Info << "LsqMax " << LsqMax << endl; + # endif + + //- K is greater than zero in case the stabilisation is needed + scalar K = 0.0; + if( Amin < SMALL * LsqMax ) + { + K = SMALL * LsqMax; + } + + return K; +} + +scalar surfaceOptimizer::evaluateFunc(const scalar& K) const +{ + scalar func(0.0); + + forAll(trias_, triI) + { + const point& p0 = pts_[trias_[triI][0]]; + const point& p1 = pts_[trias_[triI][1]]; + const point& p2 = pts_[trias_[triI][2]]; + + const scalar Atri = + 0.5 * + ( + (p1.x() - p0.x()) * (p2.y() - p0.y()) - + (p2.x() - p0.x()) * (p1.y() - p0.y()) + ); + + const scalar stab = sqrt(sqr(Atri) + K); + + # ifdef DEBUGSmooth + Info << "Triangle " << triI << " area " << Atri << endl; + # endif + + const scalar LSqrTri + ( + magSqr(p0 - p1) + + magSqr(p2 - p0) + ); + + func += LSqrTri / (0.5 * (Atri + stab)); + } + + return func; +} + +//- evaluate gradients needed for optimisation +void surfaceOptimizer::evaluateGradients +( + const scalar& K, + vector& gradF, + tensor& gradGradF +) const +{ + gradF = vector::zero; + gradGradF = tensor::zero; + + tensor gradGradLt(tensor::zero); + gradGradLt.xx() = 4.0; + gradGradLt.yy() = 4.0; + + forAll(trias_, triI) + { + const point& p0 = pts_[trias_[triI][0]]; + const point& p1 = pts_[trias_[triI][1]]; + const point& p2 = pts_[trias_[triI][2]]; + + if( magSqr(p1 - p2) < VSMALL ) continue; + + const scalar LSqrTri + ( + magSqr(p0 - p1) + + magSqr(p2 - p0) + ); + + const scalar Atri = + 0.5 * + ( + (p1.x() - p0.x()) * (p2.y() - p0.y()) - + (p2.x() - p0.x()) * (p1.y() - p0.y()) + ); + + const scalar stab = sqrt(sqr(Atri) + K); + + const scalar Astab = 0.5 * (Atri + stab); + + const vector gradAtri + ( + 0.5 * (p1.y() - p2.y()), + 0.5 * (p2.x() - p1.x()), + 0.0 + ); + + const vector gradAstab = 0.5 * (gradAtri + Atri * gradAtri / stab); + + const tensor gradGradAstab = + 0.5 * + ( + (gradAtri * gradAtri) / stab - + sqr(Atri) * (gradAtri * gradAtri) / pow(stab, 3) + ); + + const vector gradLt(4.0 * p0 - 2.0 * p1 - 2.0 * p2); + + //- calculate the gradient + const scalar sqrAstab = sqr(Astab); + gradF += gradLt / Astab - (LSqrTri * gradAstab) / sqrAstab; + + //- calculate the second gradient + gradGradF += + gradGradLt / Astab - + twoSymm(gradLt * gradAstab) / sqrAstab - + gradGradAstab * LSqrTri / sqrAstab + + 2.0 * LSqrTri * (gradAstab * gradAstab) / (sqrAstab * Astab); + } + + //- stabilise diagonal terms + if( mag(gradGradF.xx()) < VSMALL ) gradGradF.xx() = VSMALL; + if( mag(gradGradF.yy()) < VSMALL ) gradGradF.yy() = VSMALL; +} + +scalar surfaceOptimizer::optimiseDivideAndConquer(const scalar tol) +{ + point& pOpt = pts_[trias_[0][0]]; + + pOpt = 0.5 * (pMax_ + pMin_); + point currCentre = pOpt; + scalar dx = (pMax_.x() - pMin_.x()) / 2.0; + scalar dy = (pMax_.y() - pMin_.y()) / 2.0; + + FixedList<vector, 4> dirVecs; + dirVecs[0] = vector(-1.0, -1.0, 0.0); + dirVecs[1] = vector(1.0, -1.0, 0.0); + dirVecs[2] = vector(-1.0, 1.0, 0.0); + dirVecs[3] = vector(1.0, 1.0, 0.0); + + label iter(0); + + //- find the value of the functional in the centre of the bnd box + scalar K = evaluateStabilisationFactor(); + scalar funcBefore, funcAfter(evaluateFunc(K)); + + do + { + funcBefore = funcAfter; + + funcAfter = VGREAT; + point minCentre(vector::zero); + + forAll(dirVecs, i) + { + pOpt.x() = currCentre.x() + 0.5 * dirVecs[i].x() * dx; + pOpt.y() = currCentre.y() + 0.5 * dirVecs[i].y() * dy; + + K = evaluateStabilisationFactor(); + const scalar func = evaluateFunc(K); + + if( func < funcAfter ) + { + minCentre = pOpt; + funcAfter = func; + } + } + + //- set the centre with the minimum value + //- as the centre for future search + currCentre = minCentre; + pOpt = minCentre; + + //- halve the search range + dx *= 0.5; + dy *= 0.5; + + //- calculate the tolerence + const scalar t = mag(funcAfter - funcBefore) / funcAfter; + + # ifdef DEBUGSmooth + Info << "Point position " << pOpt << endl; + Info << "Func before " << funcBefore << endl; + Info << "Func after " << funcAfter << endl; + Info << "Normalised difference " << t << endl; + # endif + + if( t < tol ) + break; + } while( ++iter < 100 ); + + return funcAfter; +} + +scalar surfaceOptimizer::optimiseSteepestDescent(const scalar tol) +{ + point& pOpt = pts_[trias_[0][0]]; + + //- find the bounding box + const scalar avgEdge = Foam::mag(pMax_ - pMin_); + + //- find the minimum value on the 5 x 5 raster + scalar K = evaluateStabilisationFactor(); + scalar funcBefore, funcAfter(evaluateFunc(K)); + + //- start with steepest descent optimisation + vector gradF; + tensor gradGradF; + vector disp; + disp.z() = 0.0; + + direction nIterations(0); + do + { + funcBefore = funcAfter; + + evaluateGradients(K, gradF, gradGradF); + + //- store data into a matrix + matrix2D mat; + mat[0][0] = gradGradF.xx(); + mat[0][1] = gradGradF.xy(); + mat[1][0] = gradGradF.yx(); + mat[1][1] = gradGradF.yy(); + FixedList<scalar, 2> source; + source[0] = gradF.x(); + source[1] = gradF.y(); + + //- calculate the determinant + const scalar det = mat.determinant(); + + if( mag(det) < VSMALL ) + { + disp = vector::zero; + } + else + { + disp.x() = mat.solveFirst(source); + disp.y() = mat.solveSecond(source); + + if( mag(disp) > 0.2 * avgEdge ) + { + vector dir = disp / mag(disp); + + disp = dir * 0.2 * avgEdge; + } + } + + # ifdef DEBUGSmooth + Info << "Second gradient " << gradGradF << endl; + Info << "Gradient " << gradF << endl; + Info << "Displacement " << disp << endl; + Info << "K = " << K << endl; + # endif + + pOpt -= disp; + + K = evaluateStabilisationFactor(); + funcAfter = evaluateFunc(K); + + if( mag(funcAfter - funcBefore) / funcBefore < tol ) + break; + + #ifdef DEBUGSmooth + Info << "New coordinates " << pOpt << endl; + # endif + + } while( ++nIterations < 100 ); + + return funcAfter; +} + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + surfaceOptimizer::surfaceOptimizer ( DynList<point>& pts, @@ -46,172 +350,54 @@ surfaceOptimizer::surfaceOptimizer ) : pts_(pts), - trias_(trias) + trias_(trias), + pMin_(), + pMax_() { + pMin_ = pts_[trias_[0][1]]; + pMax_ = pMin_; + + forAll(trias_, triI) + { + const triFace& tf = trias_[triI]; + + for(label i=1;i<3;++i) + { + pMin_ = Foam::min(pMin_, pts_[tf[i]]); + pMax_ = Foam::max(pMax_, pts_[tf[i]]); + } + } } surfaceOptimizer::~surfaceOptimizer() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // point surfaceOptimizer::optimizePoint(const scalar tol) { - scalar avgEdge(0.0); - forAll(trias_, triI) - avgEdge += - mag(pts_[trias_[triI][1]] - pts_[trias_[triI][0]]); - avgEdge /= trias_.size(); - - avgEdge *= tol; - - tensor gradGradLt(tensor::zero); - gradGradLt.xx() = 4.0; - gradGradLt.yy() = 4.0; - - point newPoint(vector::zero); - - vector disp; - disp.z() = 0.0; - direction nIterations(0); - do - { - //- find the minimum area - scalar Amin(SMALL); - forAll(trias_, triI) - { - const point& p0 = pts_[trias_[triI][0]]; - const point& p1 = pts_[trias_[triI][1]]; - const point& p2 = pts_[trias_[triI][2]]; - - const scalar Atri = - 0.5 * - ( - (p1.y() - p2.y()) * p0.x() + - (p2.x() - p1.x()) * p0.y() + - (p1.x() * p2.y() - p2.x() * p1.y()) - ); - - if( Atri < Amin ) - Amin = Atri; - } - - //- K is greater than zero in case the stabilisation is needed - scalar K = 0.0; - if( Amin < SMALL ) - { - K = max(10.0 * sqrt(SMALL * (SMALL - Amin)), K); - if( sqrt(sqr(Amin) + 4.0 * sqr(K)) < (1.0 + SMALL) * mag(Amin) ) - K = max(sqrt(SMALL) * mag(Amin), K); - } - //const scalar K = sqrt(SMALL * (SMALL - Amin)); - - # ifdef DEBUGSmooth - Info << "Point " << bpI << " K = " << K << endl; - # endif - - //- start assembling the system - vector gradF(vector::zero); - tensor gradGradF(tensor::zero); - forAll(trias_, triI) - { - const point& p0 = pts_[trias_[triI][0]]; - const point& p1 = pts_[trias_[triI][1]]; - const point& p2 = pts_[trias_[triI][2]]; - - if( magSqr(p1 - p2) < VSMALL ) continue; - - const scalar LSqrTri - ( - magSqr(p0 - p1) + - magSqr(p1 - p2) + - magSqr(p2 - p0) - ); - - const scalar Atri = - 0.5 * - ( - (p1.y() - p2.y()) * p0.x() + - (p2.x() - p1.x()) * p0.y() + - (p1.x() * p2.y() - p2.x() * p1.y()) - ); - - const scalar stab = sqrt(sqr(Atri) + K); - const scalar Astab = 0.5 * (Atri + stab); - const vector B((p1.y() - p2.y()), (p2.x() - p1.x()), 0.0); - const vector gradAstab = 0.5 * (B + (Atri * B) / stab); - const tensor gradGradAstab = - 0.5 * - ( - (B * B) / stab - - (B * B) * sqr(Atri) / pow(stab, 3) - ); - - const vector gradLt(4 * p0 - 2.0 * p1 - 2.0 * p2); - - //- calculate the gradient - gradF += (gradLt * Astab - LSqrTri * gradAstab) / sqr(Astab); - - //- calculate the second gradient - gradGradF += - gradGradLt / Astab - - 2.0 * symm(gradLt * gradAstab) / sqr(Astab) - - LSqrTri * gradGradAstab / sqr(Astab) + - 2.0 * LSqrTri * (gradAstab * gradAstab) / pow(Astab, 3); - } - - if( mag(gradGradF.xx()) < VSMALL ) gradGradF.xx() = VSMALL; - if( mag(gradGradF.yy()) < VSMALL ) gradGradF.yy() = VSMALL; - - matrix2D mat; - mat[0][0] = gradGradF.xx(); - mat[0][1] = gradGradF.xy(); - mat[1][0] = gradGradF.yx(); - mat[1][1] = gradGradF.yy(); - FixedList<scalar, 2> source; - source[0] = gradF.x(); - source[1] = gradF.y(); - - const scalar det = mat.determinant(); - - if( mag(det) < VSMALL ) - { - disp = vector::zero; - } - else - { - disp.x() = mat.solveFirst(source); - disp.y() = mat.solveSecond(source); - - if( mag(disp) > 0.7 * avgEdge ) - { - vector dir = disp / mag(disp); - - disp = dir * 0.7 * avgEdge; - } - } - - # ifdef DEBUGSmooth - Info << "Second gradient " << gradGradF << endl; - Info << "Gradient " << gradF << endl; - Info << "Displacement " << disp << endl; - # endif - - newPoint -= disp; - pts_[trias_[0][0]] = newPoint; - - #ifdef DEBUGSmooth - Info << "New coordinates " << newPoint << endl; - # endif - - } while( (++nIterations < 100) && (mag(disp) > avgEdge) ); - - //- do not move the vertex if the process has not converged - if( nIterations >= 100 ) - newPoint = vector::zero; - - return newPoint; + const scalar scale = mag(pMax_ - pMin_); + forAll(pts_, i) + pts_[i] /= scale; + pMin_ /= scale; + pMax_ /= scale; + + point& pOpt = pts_[trias_[0][0]]; + + const scalar funcDivide = optimiseDivideAndConquer(tol); + const point newPoint = pOpt; + + const scalar funcSteepest = optimiseSteepestDescent(tol); + + if( funcSteepest > funcDivide ) + pOpt = newPoint; + + forAll(pts_, i) + pts_[i] *= scale; + pMin_ *= scale; + pMax_ *= scale; + + return pOpt; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.H b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.H index c13f5a6e7a619a88fdec9a531b5b445c7ec78b86..f97737fdcaae08ef01089005f248bac5f60995ad 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.H +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/advancedSurfaceSmoothers/surfaceOptimizer/surfaceOptimizer.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class surfaceOptimizer @@ -52,12 +51,34 @@ namespace Foam class surfaceOptimizer { // Private data - //- reference to the simplex points + //- reference to the simplex points DynList<point>& pts_; - + //- reference to the triangles forming a simplex const DynList<triFace>& trias_; + //- min position of the bnd box + point pMin_; + + //- max position of the bnd box + point pMax_; + + // Private member functions + //- evaluate stabilisation factor + scalar evaluateStabilisationFactor() const; + + //- evaluate the functional + scalar evaluateFunc(const scalar& K) const; + + //- evaluate gradients needed for optimisation + void evaluateGradients(const scalar&, vector&, tensor&) const; + + //- optimise point position using the divide and conquer technique + scalar optimiseDivideAndConquer(const scalar tol); + + //- optimise point position via the steepest descent method + scalar optimiseSteepestDescent(const scalar tol); + //- Disallow default bitwise copy construct surfaceOptimizer(const surfaceOptimizer&); @@ -71,7 +92,7 @@ public: //- Construct from transformed points and triangles forming a simplex surfaceOptimizer ( - DynList<point>& pts, + DynList<point>& pts, const DynList<triFace>& trias ); @@ -81,9 +102,9 @@ public: ~surfaceOptimizer(); // Member Functions - - //- optimizes position of a central point in the simplex - point optimizePoint(const scalar tol = 0.1); + + //- optimizes position of a central point in the simplex + point optimizePoint(const scalar tol = 0.1); }; diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.C b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.C index 9f47e44b40df6ab1fcfed27fd32ed3f251369a60..0a7c5f346cabdb1627f55db538c2dab8ead14219 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.C +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,74 +29,132 @@ Description #include "meshSurfaceOptimizer.H" #include "meshSurfaceEngine.H" #include "meshSurfacePartitioner.H" +#include "polyMeshGenChecks.H" #include <map> -// #define DEBUGSearch - // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshSurfaceOptimizer::classifySurfaceVertices() { - meshSurfacePartitioner mPart(surfaceEngine_); - const labelHashSet& corners = mPart.corners(); - const labelHashSet& edgePoints = mPart.edgeNodes(); - + const labelHashSet& corners = partitionerPtr_->corners(); + const labelHashSet& edgePoints = partitionerPtr_->edgePoints(); + //- set all vertices to partition vertexType_ = PARTITION; - + //- set corners forAllConstIter(labelHashSet, corners, it) vertexType_[it.key()] = CORNER; - + //- set edges forAllConstIter(labelHashSet, edgePoints, it) vertexType_[it.key()] = EDGE; - + if( Pstream::parRun() ) { //- mark nodes at parallel boundaries const Map<label>& globalToLocal = surfaceEngine_.globalToLocalBndPointAddressing(); - + forAllConstIter(Map<label>, globalToLocal, iter) { const label bpI = iter(); - + vertexType_[bpI] |= PROCBND; } } } +label meshSurfaceOptimizer::findBadFaces +( + labelHashSet& badFaces, + boolList& changedFace +) const +{ + badFaces.clear(); + + const polyMeshGen& mesh = surfaceEngine_.mesh(); + + polyMeshGenChecks::checkFacePyramids + ( + mesh, + false, + VSMALL, + &badFaces, + &changedFace + ); + + polyMeshGenChecks::checkCellPartTetrahedra + ( + mesh, + false, + VSMALL, + &badFaces, + &changedFace + ); + + polyMeshGenChecks::checkFaceAreas + ( + mesh, + false, + VSMALL, + &badFaces, + &changedFace + ); + + const label nBadFaces = returnReduce(badFaces.size(), sumOp<label>()); + + return nBadFaces; +} + // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // -// Construct from mesh surface and octree meshSurfaceOptimizer::meshSurfaceOptimizer ( - meshSurfaceEngine& surface, + const meshSurfaceEngine& surface, const meshOctree& octree ) : - surfaceEngine_(surface), + surfaceEngine_(surface), meshOctree_(octree), - vertexType_(surface.boundaryPoints().size()), - trianglesPtr_(NULL), - pointTrianglesPtr_(NULL) + vertexType_(surface.boundaryPoints().size()), + partitionerPtr_(new meshSurfacePartitioner(surface)), + deletePartitioner_(true), + triMeshPtr_(NULL) { - classifySurfaceVertices(); + classifySurfaceVertices(); +} + +meshSurfaceOptimizer::meshSurfaceOptimizer +( + const meshSurfacePartitioner& partitioner, + const meshOctree& octree +) +: + surfaceEngine_(partitioner.surfaceEngine()), + meshOctree_(octree), + vertexType_(surfaceEngine_.boundaryPoints().size()), + partitionerPtr_(&partitioner), + deletePartitioner_(false), + triMeshPtr_(NULL) +{ + classifySurfaceVertices(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // meshSurfaceOptimizer::~meshSurfaceOptimizer() { - deleteDemandDrivenData(trianglesPtr_); - deleteDemandDrivenData(pointTrianglesPtr_); + deleteDemandDrivenData(triMeshPtr_); + + if( deletePartitioner_ ) + deleteDemandDrivenData(partitionerPtr_); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.H b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.H index 23d044c5a5cf3fca8602e494dfbfef918ed2c053..a682ce23d3a1c4ed25ec37e1f959fc702da359d6 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.H +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizer.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceOptimizer @@ -38,11 +37,13 @@ SourceFiles #include "polyMeshGen.H" #include "boolList.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "DynList.H" #include "triFace.H" #include "meshSurfaceEngine.H" #include "parTriFace.H" +#include "meshSurfacePartitioner.H" +#include "partTriMesh.H" #include <map> @@ -62,42 +63,51 @@ class plane; class meshSurfaceOptimizer { // Private data - //- reference to the mesh surface - meshSurfaceEngine& surfaceEngine_; - - //- reference to the octree + //- const reference to the mesh surface + const meshSurfaceEngine& surfaceEngine_; + + //- const reference to the octree const meshOctree& meshOctree_; - - //- type of surface vertex - List<direction> vertexType_; - - //- form trihedra - mutable LongList<triFace>* trianglesPtr_; - mutable VRWGraph* pointTrianglesPtr_; + + //- type of surface vertex + List<direction> vertexType_; + + //- surface partitioner + const meshSurfacePartitioner* partitionerPtr_; + const bool deletePartitioner_; + + //- mesh of surface triangles needed for some smoothers + mutable partTriMesh* triMeshPtr_; // Private member functions - //- classify surface vertices as PARTITION, EDGE, CORNER - void classifySurfaceVertices(); - - //- calculate surface triangulation - void calculateTrianglesAndAddressing() const; - inline const LongList<triFace>& triangles() const; - inline const VRWGraph& pointTriangles() const; - - //- find vertices which are inverted - label findInvertedVertices(boolList& smoothVertex) const; - - //- transform into a 2D space in plane - inline bool transformIntoPlane - ( - const label bpI, - const plane& pl, - vector& vecX, - vector& vecY, - DynList<point>& pts, - DynList<triFace>& trias - ) const; - + //- classify surface vertices as PARTITION, EDGE, CORNER + void classifySurfaceVertices(); + + //- calculate surface triangulation + void calculateTrianglesAndAddressing() const; + inline const partTriMesh& triMesh() const; + inline void updateTriMesh(const labelLongList&); + inline void updateTriMesh(); + + //- find vertices which are inverted + //- mark additional layers of vertices near the inverted ones + label findInvertedVertices + ( + boolList& smoothVertex, + const label nAdditionalLayers = 2 + ) const; + + //- transform into a 2D space in plane + inline bool transformIntoPlane + ( + const label bpI, + const plane& pl, + vector& vecX, + vector& vecY, + DynList<point>& pts, + DynList<triFace>& trias + ) const; + //- transform into a 2D space in plane for parallel boundaries inline bool transformIntoPlaneParallel ( @@ -105,11 +115,11 @@ class meshSurfaceOptimizer const plane& pl, const std::map<label, DynList<parTriFace> >& m, vector& vecX, - vector& vecY, - DynList<point>& pts, - DynList<triFace>& trias - ) const; - + vector& vecY, + DynList<point>& pts, + DynList<triFace>& trias + ) const; + //- new position of a node after laplacian smoothing //- the position is the average of neighbouring vertex positions inline point newPositionLaplacian @@ -117,7 +127,7 @@ class meshSurfaceOptimizer const label bpI, const bool transformIntoPlane = true ) const; - + //- new position of a node after laplacian smoothing //- the position is the average of neighbouring face centres inline point newPositionLaplacianFC @@ -125,7 +135,7 @@ class meshSurfaceOptimizer const label bpI, const bool transformIntoPlane = true ) const; - + //- new position of a node after laplacian smoothing //- the position is the weighted average of neighbouring face centres //- the weights are the magnitudes of neighbouring face area vectors @@ -134,23 +144,18 @@ class meshSurfaceOptimizer const label bpI, const bool transformIntoPlane = true ) const; - + //- new position of a node after using surfaceOptimizer inline point newPositionSurfaceOptimizer ( const label bpI, - const scalar tol = 0.001, - const bool transformIntoPlane = true + const scalar tol = 0.001 ) const; - + //- new position of edge vertex //- the position is the average of neighbouring edge vertices - inline point newEdgePositionLaplacian - ( - const label bpI, - const bool transformIntoPlane = true - ) const; - + inline point newEdgePositionLaplacian(const label bpI) const; + //- smooth the node using the laplacian smoother //- new position is the average of the neighbouring vertices void nodeDisplacementLaplacian @@ -158,7 +163,7 @@ class meshSurfaceOptimizer const label bpI, const bool transformIntoPlane = true ) const; - + //- smooth the node using the laplacian smoother //- new position is the average of the centres of faces attached //- to the vertex @@ -167,78 +172,98 @@ class meshSurfaceOptimizer const label bpI, const bool transformIntoPlane = true ) const; - - //- smooth the node using surface optimizer - void nodeDisplacementSurfaceOptimizer - ( - const label bpI, - const scalar tol = 1.0 - ); - - //- smooth edge node - void edgeNodeDisplacement(const label bpI) const; - + + //- smooth the node using surface optimizer + void nodeDisplacementSurfaceOptimizer + ( + const label bpI, + const scalar tol = 1.0 + ); + + //- smooth edge node + void edgeNodeDisplacement(const label bpI) const; + + //- smooth selected edge points + void smoothEdgePoints + ( + const labelLongList& edgePoints, + const labelLongList& procEdgePoints + ); + + //- smooth selected points using laplaceFC + void smoothLaplacianFC + ( + const labelLongList& selectedPoints, + const labelLongList& selectedProcPoints, + const bool transform = true + ); + + //- smooth selected points using surface optimizer + void smoothSurfaceOptimizer(const labelLongList& selectedPoints); + // Functions needed for parallel runs - + //- transfer data between processors void exchangeData ( - const labelListPMG& nodesToSmooth, + const labelLongList& nodesToSmooth, std::map<label, DynList<parTriFace> >& m ) const; - + //- laplacian smoothing of points at processor boundaries //- new position is the average of the neighbouring vertices void nodeDisplacementLaplacianParallel ( - const labelListPMG& nodesToSmooth, + const labelLongList& nodesToSmooth, const bool transformIntoPlane = true ); - + //- laplacian smoothing of points at processor boundaries void nodeDisplacementLaplacianFCParallel ( - const labelListPMG& nodesToSmooth, + const labelLongList& nodesToSmooth, const bool transformIntoPlane = true ); - + //- smooth nodes at processor boundaries using surface optimizer void nodeDisplacementSurfaceOptimizerParallel ( - const labelListPMG& nodesToSmooth + const labelLongList& nodesToSmooth ); - + //- smooth edge nodes at processor boundaries void edgeNodeDisplacementParallel ( - const labelListPMG& nodesToSmooth + const labelLongList& nodesToSmooth ); + //- find invalid faces in the mesh + label findBadFaces(labelHashSet&, boolList&) const; + //- Disallow default bitwise copy construct meshSurfaceOptimizer(const meshSurfaceOptimizer&); //- Disallow default bitwise assignment void operator=(const meshSurfaceOptimizer&); - - // Enumerators - enum vertexTypes - { - PARTITION = 1, - EDGE = 2, - CORNER = 4, + + // Enumerators + enum vertexTypes + { + PARTITION = 1, + EDGE = 2, + CORNER = 4, PROCBND = 8 - }; + }; public: // Constructors //- Construct from mesh surface and octree - meshSurfaceOptimizer - ( - meshSurfaceEngine& surface, - const meshOctree& octree - ); + meshSurfaceOptimizer(const meshSurfaceEngine&, const meshOctree&); + + //- Construct from partitioner and octree + meshSurfaceOptimizer(const meshSurfacePartitioner&, const meshOctree&); // Destructor @@ -246,11 +271,28 @@ public: ~meshSurfaceOptimizer(); // Member Functions - //- optimisation before the edges and corners are created - void preOptimizeSurface(); + //- runs a surface smoother on the selected boundary points + bool untangleSurface + ( + const labelLongList& activeBoundaryPoints, + const label nAdditionalLayers = 0 + ); + + //- checks for invertex surface elements and tries to untangle them + //- it tries to keep the points on the surface for a couple + //- of iteration and gives up the final iterations + //- by default, it smooths two additional layers of elements + //- around the inverted ones + bool untangleSurface(const label nAdditionalLayers = 2); + + //- optimize boundary nodes after boundary regions are created + void optimizeSurface(const label nIterations = 5); + + //- optimize the surface of a 2D mesh + void optimizeSurface2D(const label nIterations = 5); - //- optimize boundary nodes after boundary regions are created - void optimizeSurface(const label nIterations = 5); + //- untangle the surface of a 2D mesh + void untangleSurface2D(); }; diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerCalculateTrianglesAndAddressing.C b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerCalculateTrianglesAndAddressing.C index 96a9416496b8cb174aac1a9b92c7886420040470..db0fd98c62f5b301b1afb22219a5a95b57924b9e 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerCalculateTrianglesAndAddressing.C +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerCalculateTrianglesAndAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,7 +29,13 @@ Description #include "meshSurfaceOptimizer.H" #include "meshSurfaceEngine.H" -//#define DEBUGSearch +//#define DEBUGTriangulation + +# ifdef DEBUGTriangulation +#include "triSurf.H" +#include "triSurfModifier.H" +#include "helperFunctions.H" +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -41,60 +46,50 @@ namespace Foam void meshSurfaceOptimizer::calculateTrianglesAndAddressing() const { - if( trianglesPtr_ || pointTrianglesPtr_ ) - FatalErrorIn - ( - "void meshSurfaceOptimizer::calculateTrianglesAndAddressing() const" - ) << "Addressing is already calculated!" << abort(FatalError); - - const faceList::subList& bFaces = surfaceEngine_.boundaryFaces(); - const labelList& bp = surfaceEngine_.bp(); - - triFace triangle; //- helper - - pointTrianglesPtr_ = new VRWGraph(surfaceEngine_.boundaryPoints().size()); - VRWGraph& pointTriangles = *pointTrianglesPtr_; - - trianglesPtr_ = new LongList<triFace>(); - LongList<triFace>& triangles = *trianglesPtr_; - - //- start creating triangles - forAll(bFaces, bfI) - { - const face& bf = bFaces[bfI]; - - forAll(bf, pI) - { - const label nTrias = bf.size() - 2; - triangle[0] = bp[bf[pI]]; - - for(label i=0;i<nTrias;++i) - { - triangle[1] = bp[bf[(pI+i+1)%bf.size()]]; - triangle[2] = bp[bf[(pI+i+2)%bf.size()]]; - - triangles.append(triangle); - } - } - } - - //- create point-triangles addressing - labelList nTriaAtPoint(pointTriangles.size(), 0); - forAll(triangles, triI) - { - const triFace& tria = triangles[triI]; - ++nTriaAtPoint[tria[0]]; - } - - forAll(nTriaAtPoint, bpI) - pointTriangles.setRowSize(bpI, nTriaAtPoint[bpI]); - nTriaAtPoint = 0; - - forAll(triangles, triI) + if( triMeshPtr_ ) + FatalErrorIn + ( + "void meshSurfaceOptimizer::calculateTrianglesAndAddressing() const" + ) << "Addressing is already calculated!" << abort(FatalError); + + triMeshPtr_ = new partTriMesh(*partitionerPtr_); + + # ifdef DEBUGTriangulation + const labelList& sPoints = triMeshPtr_->meshSurfacePointLabelInTriMesh(); + + forAll(sPoints, bpI) { - const triFace& tria = triangles[triI]; - pointTriangles(tria[0], nTriaAtPoint[tria[0]]++) = triI; + triSurf surf; + + const label spI = sPoints[bpI]; + + partTriMeshSimplex simplex(*triMeshPtr_, spI); + + triSurfModifier sMod(surf); + + pointField& pts = sMod.pointsAccess(); + pts.setSize(simplex.pts().size()); + forAll(pts, i) + pts[i] = simplex.pts()[i]; + + LongList<labelledTri>& trias = sMod.facetsAccess(); + trias.setSize(simplex.triangles().size()); + forAll(trias, i) + { + const triFace& t = simplex.triangles()[i]; + trias[i] = labelledTri(t[0], t[1], t[2], 0); + } + + sMod.patchesAccess().setSize(1); + sMod.patchesAccess()[0].name() = "bnd"; + sMod.patchesAccess()[0].geometricType() = "patch"; + + fileName sName("bndPointSimplex_"); + sName += help::scalarToText(bpI); + sName += ".stl"; + surf.writeSurface(sName); } + # endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerI.H b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerI.H index fe9fba11746fbfe9e85487b5ed480fafde7d9377..bc7ad66418e4f7273a9195d67e7b32d0c50943ec 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerI.H +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,9 +30,17 @@ Description #include "plane.H" #include "Map.H" #include "surfaceOptimizer.H" +#include "helperFunctions.H" +#include "partTriMeshSimplex.H" //#define DEBUGSmooth +# ifdef DEBUGSmooth +#include "triSurf.H" +#include "triSurfModifier.H" +#include "helperFunctions.H" +# endif + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam @@ -41,152 +48,187 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -const LongList<triFace>& meshSurfaceOptimizer::triangles() const +inline const partTriMesh& meshSurfaceOptimizer::triMesh() const { - if( !trianglesPtr_ ) - calculateTrianglesAndAddressing(); - - return *trianglesPtr_; + if( !triMeshPtr_ ) + calculateTrianglesAndAddressing(); + + return *triMeshPtr_; } -const VRWGraph& meshSurfaceOptimizer::pointTriangles() const +inline void meshSurfaceOptimizer::updateTriMesh(const labelLongList& selPoints) { - if( !pointTrianglesPtr_ ) - calculateTrianglesAndAddressing(); - - return *pointTrianglesPtr_; + if( !triMeshPtr_ ) + FatalErrorIn + ( + "inline void meshSurfaceOptimizer::updateTriMesh" + "(const labelLongList&)" + ) << "triMeshPtr_ is not allocated " << abort(FatalError); + + triMeshPtr_->updateVertices(selPoints); +} + +inline void meshSurfaceOptimizer::updateTriMesh() +{ + if( !triMeshPtr_ ) + FatalErrorIn + ( + "inline void meshSurfaceOptimizer::updateTriMesh()" + ) << "triMeshPtr_ is not allocated " << abort(FatalError); + + triMeshPtr_->updateVertices(); } inline bool meshSurfaceOptimizer::transformIntoPlane ( - const label bpI, - const plane& pl, - vector& vecX, - vector& vecY, - DynList<point>& pts, - DynList<triFace>& trias + const label bpI, + const plane& pl, + vector& vecX, + vector& vecY, + DynList<point>& pts, + DynList<triFace>& trias ) const { - # ifdef DEBUGSmooth - Info << "Transforming boundary node " << bpI << endl; - # endif - - const pointFieldPMG& points = surfaceEngine_.points(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pPoints = surfaceEngine_.pointPoints(); - const LongList<triFace>& triangles = this->triangles(); - const constRow pTriangles = pointTriangles()[bpI]; - - # ifdef DEBUGSmooth - Info << "Triangles containing this node are " << pTriangles << endl; - # endif - - //- create vecX and vecY - const point& p = points[bPoints[bpI]]; - pts.setSize(0); - bool found(false); - forAllRow(pPoints, bpI, pI) - { - const point sp = pl.nearestPoint(points[bPoints[pPoints(bpI, pI)]]); - const scalar d = mag(sp - p); - if( d > VSMALL ) - { - vecX = sp - p; - vecX /= d; - vecY = pl.normal() ^ vecX; - vecY /= mag(vecY); - found = true; - break; - } - } - - if( !found ) - return false; - - # ifdef DEBUGSmooth - Info << "VecX " << vecX << endl; - Info << "vecY " << vecY << endl; - # endif - - //- transform the vertices - label counter(0); - Map<label> pointMapping; - trias.setSize(pTriangles.size()); - forAll(pTriangles, triI) - { - const triFace& tri = triangles[pTriangles[triI]]; - - forAll(tri, pI) - { - Map<label>::iterator fnd = pointMapping.find(tri[pI]); - if( fnd != pointMapping.end() ) - { - trias[triI][pI] = fnd(); - } - else - { - point pt - ( - ((points[bPoints[tri[pI]]] - p) & vecX), - ((points[bPoints[tri[pI]]] - p) & vecY), - 0.0 - ); - - pts.append(pt); - trias[triI][pI] = counter; - pointMapping.insert(tri[pI], counter); - ++counter; - } - } - } - - # ifdef DEBUGSmooth - Info << "Original triangles " << endl; - forAll(pTriangles, triI) - Info << "Tri " << triI << " is " << triangles[pTriangles[triI]] << endl; - Info << "Transformed triangles are " << trias << endl; - Info << "Transformed vertices " << pts << endl; - # endif - - return found; + # ifdef DEBUGSmooth + Info << "Transforming boundary node " << bpI << endl; + # endif + + const partTriMesh& triMesh = this->triMesh(); + const label triPointI = triMesh.meshSurfacePointLabelInTriMesh()[bpI]; + partTriMeshSimplex simplex(triMesh, triPointI); + + const DynList<point, 32>& sPts = simplex.pts(); + + //- create vecX and vecY + const point& p = simplex.centrePoint(); + pts.setSize(0); + bool found(false); + forAll(sPts, pI) + { + const point sp = pl.nearestPoint(sPts[pI]); + const scalar d = mag(sp - p); + if( d > VSMALL ) + { + vecX = sp - p; + vecX /= d; + vecY = pl.normal() ^ vecX; + vecY /= mag(vecY); + found = true; + break; + } + } + + if( !found ) + return false; + + trias = simplex.triangles(); + + # ifdef DEBUGSmooth + Info << "VecX " << vecX << endl; + Info << "vecY " << vecY << endl; + # endif + + //- transform the vertices + pts.setSize(sPts.size()); + + forAll(sPts, pI) + { + const point pt + ( + ((sPts[pI] - p) & vecX), + ((sPts[pI] - p) & vecY), + 0.0 + ); + + pts[pI] = pt; + } + + # ifdef DEBUGSmooth + Info << "Original triangles " << endl; + forAll(simplex.triangles(), triI) + Info << "Tri " << triI << " is " << simplex.triangles()[triI] << endl; + Info << "Transformed triangles are " << trias << endl; + Info << "Transformed vertices " << pts << endl; + + triSurf surf; + triSurfModifier sMod(surf); + pointField& sPoints = sMod.pointsAccess(); + sPoints.setSize(pts.size()); + forAll(sPoints, i) + sPoints[i] = pts[i]; + LongList<labelledTri>& sTrias = sMod.facetsAccess(); + sTrias.setSize(trias.size()); + forAll(sTrias, i) + { + labelledTri& tf = sTrias[i]; + tf[0] = trias[i][0]; + tf[1] = trias[i][1]; + tf[2] = trias[i][2]; + + tf.region() = 0; + } + sMod.patchesAccess().setSize(1); + sMod.patchesAccess()[0].name() = "bnd"; + sMod.patchesAccess()[0].geometricType() = "patch"; + + fileName sName("bndSimplex_"); + sName += help::scalarToText(bpI); + sName += ".stl"; + surf.writeSurface(sName); + # endif + + return found; } inline bool meshSurfaceOptimizer::transformIntoPlaneParallel ( - const label bpI, - const plane& pl, + const label bpI, + const plane& pl, const std::map<label, DynList<parTriFace> >& m, - vector& vecX, - vector& vecY, - DynList<point>& pts, - DynList<triFace>& trias + vector& vecX, + vector& vecY, + DynList<point>& pts, + DynList<triFace>& trias ) const { - # ifdef DEBUGSmooth - Info << "Transforming boundary node " << bpI << endl; - # endif - - const pointFieldPMG& points = surfaceEngine_.points(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); + /* + # ifdef DEBUGSmooth + Info << "Transforming boundary node at parallel interface " << bpI << endl; + # endif + + const pointFieldPMG& points = surfaceEngine_.points(); + const labelList& bPoints = surfaceEngine_.boundaryPoints(); const labelList& globalPointLabel = surfaceEngine_.globalBoundaryPointLabel(); - + std::map<label, DynList<parTriFace> >::const_iterator pIter = m.find(globalPointLabel[bpI]); + + if( pIter == m.end() ) + { + FatalErrorIn + ( + "(const label, const plane&," + " const std::map<label, DynList<parTriFace> >&," + " vector&, vector&, DynList<point>&, DynList<triFace>&) const" + ) << " Cannot find node " << globalPointLabel[bpI] + << " in the map" << abort(FatalError); + } + const DynList<parTriFace>& pFcs = pIter->second; - # ifdef DEBUGSmooth + # ifdef DEBUGSmooth if( globalPointLabel[bpI] != pFcs[0].globalLabelOfPoint(0) ) FatalError << "Wrong points supplied!" << abort(FatalError); - Info << "Triangles containing this node are " << pFcs << endl; - # endif - - //- create vecX and vecY - const point& p = points[bPoints[bpI]]; - pts.setSize(0); - bool found(false); - + Info << "Triangles containing this node are " << pFcs << endl; + # endif + + //- create vecX and vecY + const point& p = points[bPoints[bpI]]; + pts.setSize(0); + bool found(false); + forAll(pFcs, tI) { const point sp = pl.nearestPoint(pFcs[tI].trianglePoints().centre()); @@ -201,36 +243,38 @@ inline bool meshSurfaceOptimizer::transformIntoPlaneParallel break; } } - - if( !found ) - return false; - - # ifdef DEBUGSmooth - Info << "VecX " << vecX << endl; - Info << "vecY " << vecY << endl; - # endif - - //- transform the vertices - label counter(0); - Map<label> pointMapping; - trias.setSize(pFcs.size()); - + + if( !found ) + return false; + + # ifdef DEBUGSmooth + Info << "VecX " << vecX << endl; + Info << "vecY " << vecY << endl; + # endif + + //- transform the vertices + //label counter(0); + Map<label> pointMapping; + trias.setSize(pFcs.size()); + //- tranfer triangle from other proc first forAll(pFcs, triI) { const parTriFace& tri = pFcs[triI]; - + + triFace& tf = trias[triI]; + for(label pI=0;pI<3;++pI) - { - Map<label>::iterator fnd = + { + const Map<label>::iterator fnd = pointMapping.find(tri.globalLabelOfPoint(pI)); - - if( fnd != pointMapping.end() ) - { - trias[triI][pI] = fnd(); - } - else - { + + if( fnd != pointMapping.end() ) + { + tf[pI] = fnd(); + } + else + { point tp; if( pI == 0 ) { @@ -244,23 +288,25 @@ inline bool meshSurfaceOptimizer::transformIntoPlaneParallel { tp = tri.trianglePoints().c(); } - - point pt - ( - ((tp - p) & vecX), - ((tp - p) & vecY), - 0.0 - ); - - pts.append(pt); - trias[triI][pI] = counter; - pointMapping.insert(tri.globalLabelOfPoint(pI), counter); - ++counter; - } - } + + const point pt + ( + ((tp - p) & vecX), + ((tp - p) & vecY), + 0.0 + ); + + tf[pI] = pts.size(); + pointMapping.insert(tri.globalLabelOfPoint(pI), pts.size()); + pts.append(pt); + } + } } - - return found; + + return found; + */ + + return false; } inline point meshSurfaceOptimizer::newPositionLaplacian @@ -271,16 +317,16 @@ inline point meshSurfaceOptimizer::newPositionLaplacian { const VRWGraph& pPoints = surfaceEngine_.pointPoints(); const pointFieldPMG& points = surfaceEngine_.points(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); + const labelList& bPoints = surfaceEngine_.boundaryPoints(); vector newP(vector::zero); if( transformIntoPlane ) { const vector& pNormal = surfaceEngine_.pointNormals()[bpI]; - + if( magSqr(pNormal) < VSMALL ) return points[bPoints[bpI]]; - + plane pl(points[bPoints[bpI]], pNormal); DynList<point> projectedPoints; @@ -298,10 +344,10 @@ inline point meshSurfaceOptimizer::newPositionLaplacian { forAllRow(pPoints, bpI, pI) newP += points[bPoints[pPoints(bpI, pI)]]; - + newP /= pPoints.sizeOfRow(bpI); } - + return newP; } @@ -314,38 +360,38 @@ inline point meshSurfaceOptimizer::newPositionLaplacianFC const VRWGraph& pointFaces = surfaceEngine_.pointFaces(); const pointFieldPMG& points = surfaceEngine_.points(); const vectorField& faceCentres = surfaceEngine_.faceCentres(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + vector newP(vector::zero); if( transformIntoPlane ) { const vector& pNormal = surfaceEngine_.pointNormals()[bpI]; - + if( magSqr(pNormal) < VSMALL ) return points[bPoints[bpI]]; - + plane pl(points[bPoints[bpI]], pNormal); - + DynList<point> projectedPoints; projectedPoints.setSize(pointFaces.sizeOfRow(bpI)); forAllRow(pointFaces, bpI, pfI) projectedPoints[pfI] = pl.nearestPoint(faceCentres[pointFaces(bpI, pfI)]); - + forAll(projectedPoints, pI) newP += projectedPoints[pI]; - + newP /= projectedPoints.size(); } else { forAllRow(pointFaces, bpI, pfI) newP += faceCentres[pointFaces(bpI, pfI)]; - + newP /= pointFaces.sizeOfRow(bpI); } - + return newP; } @@ -359,25 +405,25 @@ inline point meshSurfaceOptimizer::newPositionLaplacianWFC const pointFieldPMG& points = surfaceEngine_.points(); const vectorField& faceAreas = surfaceEngine_.faceNormals(); const vectorField& faceCentres = surfaceEngine_.faceCentres(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + vector newP(vector::zero); if( transformIntoPlane ) { const vector& pNormal = surfaceEngine_.pointNormals()[bpI]; - + if( magSqr(pNormal) < VSMALL ) return points[bPoints[bpI]]; - + plane pl(points[bPoints[bpI]], pNormal); - + DynList<point> projectedPoints; projectedPoints.setSize(pointFaces.sizeOfRow(bpI)); forAllRow(pointFaces, bpI, pfI) projectedPoints[pfI] = pl.nearestPoint(faceCentres[pointFaces(bpI, pfI)]); - + scalar sumW(0.0); forAll(projectedPoints, pI) { @@ -386,7 +432,7 @@ inline point meshSurfaceOptimizer::newPositionLaplacianWFC newP += w * projectedPoints[pI]; sumW += w; } - + newP /= Foam::max(sumW, VSMALL); } else @@ -399,97 +445,106 @@ inline point meshSurfaceOptimizer::newPositionLaplacianWFC newP += w * faceCentres[pointFaces(bpI, pfI)]; sumW += w; } - + newP /= Foam::max(sumW, VSMALL); } - + return newP; } inline point meshSurfaceOptimizer::newPositionSurfaceOptimizer ( const label bpI, - const scalar tol, - const bool transformIntoPlane + const scalar tol ) const { const pointFieldPMG& points = surfaceEngine_.points(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - - # ifdef DEBUGSmooth - Info << "Smoothing boundary node " << bpI << endl; - Info << "Node label in the mesh is " << bPoints[bpI] << endl; - Info << "Point coordinates " << points[bPoints[bpI]] << endl; - # endif - - //- project vertices onto the plane - const vector& pNormal = surfaceEngine_.pointNormals()[bpI]; - if( magSqr(pNormal) < VSMALL ) - return points[bPoints[bpI]]; - - const plane pl(points[bPoints[bpI]], pNormal); - - DynList<point> pts; - DynList<triFace> trias; - vector vecX, vecY; + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + + # ifdef DEBUGSmooth + Info << "Smoothing boundary node " << bpI << endl; + Info << "Node label in the mesh is " << bPoints[bpI] << endl; + Info << "Point coordinates " << points[bPoints[bpI]] << endl; + # endif + + //- project vertices onto the plane + const vector& pNormal = surfaceEngine_.pointNormals()[bpI]; + if( magSqr(pNormal) < VSMALL ) + return points[bPoints[bpI]]; + + const plane pl(points[bPoints[bpI]], pNormal); + + DynList<point> pts; + DynList<triFace> trias; + vector vecX, vecY; bool success = this->transformIntoPlane(bpI, pl, vecX, vecY, pts, trias); - if( !success ) - { - Warning << "Cannot transform in plane" << endl; - return points[bPoints[bpI]]; - } - + if( !success ) + { + Warning << "Cannot transform to plane" << endl; + return points[bPoints[bpI]]; + } + surfaceOptimizer so(pts, trias); const point newPoint = so.optimizePoint(tol); - - const point newP - ( - points[bPoints[bpI]] + - vecX * newPoint.x() + - vecY * newPoint.y() - ); - + + const point newP + ( + points[bPoints[bpI]] + + vecX * newPoint.x() + + vecY * newPoint.y() + ); + + if( help::isnan(newP) || help::isinf(newP) ) + { + WarningIn + ( + "inline point meshSurfaceOptimizer::newPositionSurfaceOptimizer" + "(const label, const scalar) const" + ) << "Cannot move point " << bpI << endl; + + return points[bPoints[bpI]]; + } + return newP; } inline point meshSurfaceOptimizer::newEdgePositionLaplacian ( - const label bpI, - const bool transformIntoPlane + const label bpI ) const { - const VRWGraph& pPoints = surfaceEngine_.pointPoints(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pFaces = surfaceEngine_.pointFaces(); - const labelList& facePatch = surfaceEngine_.boundaryFacePatches(); - const pointFieldPMG& points = surfaceEngine_.points(); - - DynList<label> edgePoints(2); - forAllRow(pPoints, bpI, neiI) - if( - (vertexType_[pPoints(bpI, neiI)] & EDGE) || - (vertexType_[pPoints(bpI, neiI)] & CORNER) - ) - edgePoints.append(bPoints[pPoints(bpI, neiI)]); - - if( edgePoints.size() < 2 ) + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + const edgeList& edges = surfaceEngine_.edges(); + const VRWGraph& bpEdges = surfaceEngine_.boundaryPointEdges(); + const pointFieldPMG& points = surfaceEngine_.points(); + + const labelHashSet& featureEdges = partitionerPtr_->featureEdges(); + + DynList<label> edgePoints; + + forAllRow(bpEdges, bpI, i) + { + const label beI = bpEdges(bpI, i); + + if( featureEdges.found(beI) ) + { + edgePoints.append(edges[beI].otherVertex(bPoints[bpI])); + } + } + + if( edgePoints.size() != 2 ) return points[bPoints[bpI]]; - - DynList<label> pointPatches(2); - forAllRow(pFaces, bpI, pfI) - pointPatches.appendIfNotIn(facePatch[pFaces(bpI, pfI)]); - - # ifdef DEBUGSearch - Info << "Edge points " << edgePoints << endl; - Info << "pointPatches " << pointPatches << endl; - # endif - - vector pos(vector::zero); - forAll(edgePoints, epI) - pos += points[edgePoints[epI]]; - - pos /= edgePoints.size(); - + + # ifdef DEBUGSearch + Info << "Edge points " << edgePoints << endl; + # endif + + vector pos(vector::zero); + forAll(edgePoints, epI) + pos += points[edgePoints[epI]]; + + pos /= edgePoints.size(); + return pos; } diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePoint.C b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePoint.C index 0db4c17f7d52ae44c1b8b0c6834d8b77165bd149..d14549851bdc6cc761966b38dba01a63bceded15 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePoint.C +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePoint.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -51,7 +50,7 @@ void meshSurfaceOptimizer::nodeDisplacementLaplacian { const point newP = newPositionLaplacian(bpI, transformIntoPlane); - meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); surfaceModifier.moveBoundaryVertex(bpI, newP); } @@ -63,62 +62,62 @@ void meshSurfaceOptimizer::nodeDisplacementLaplacianFC { const point newP = newPositionLaplacianFC(bpI, transformIntoPlane); - meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); surfaceModifier.moveBoundaryVertex(bpI, newP); } void meshSurfaceOptimizer::nodeDisplacementSurfaceOptimizer ( - const label bpI, - const scalar tol + const label bpI, + const scalar tol ) { - const pointFieldPMG& points = surfaceEngine_.points(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - - # ifdef DEBUGSmooth - Info << "Smoothing boundary node " << bpI << endl; - Info << "Node label in the mesh is " << bPoints[bpI] << endl; - Info << "Point coordinates " << points[bPoints[bpI]] << endl; - # endif - - //- project vertices onto the plane - const vector& pNormal = surfaceEngine_.pointNormals()[bpI]; - if( magSqr(pNormal) < VSMALL ) - return; - - const plane pl(points[bPoints[bpI]], pNormal); - - DynList<point> pts; - DynList<triFace> trias; - vector vecX, vecY; - if( !transformIntoPlane(bpI, pl, vecX, vecY, pts, trias) ) - { - Warning << "Cannot transform in plane" << endl; - return; - } + const pointFieldPMG& points = surfaceEngine_.points(); + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + + # ifdef DEBUGSmooth + Info << "Smoothing boundary node " << bpI << endl; + Info << "Node label in the mesh is " << bPoints[bpI] << endl; + Info << "Point coordinates " << points[bPoints[bpI]] << endl; + # endif + + //- project vertices onto the plane + const vector& pNormal = surfaceEngine_.pointNormals()[bpI]; + if( magSqr(pNormal) < VSMALL ) + return; + + const plane pl(points[bPoints[bpI]], pNormal); + + DynList<point> pts; + DynList<triFace> trias; + vector vecX, vecY; + if( !transformIntoPlane(bpI, pl, vecX, vecY, pts, trias) ) + { + Warning << "Cannot transform into plane" << endl; + return; + } surfaceOptimizer so(pts, trias); point newPoint = so.optimizePoint(tol); - const point newP - ( - points[bPoints[bpI]] + - vecX * newPoint.x() + - vecY * newPoint.y() - ); - - meshSurfaceEngineModifier sm(surfaceEngine_); - sm.moveBoundaryVertex(bpI, newP); + const point newP + ( + points[bPoints[bpI]] + + vecX * newPoint.x() + + vecY * newPoint.y() + ); + + meshSurfaceEngineModifier sm(surfaceEngine_); + sm.moveBoundaryVertex(bpI, newP); } void meshSurfaceOptimizer::edgeNodeDisplacement(const label bpI) const { const pointFieldPMG& points = surfaceEngine_.points(); - const labelList& bPoints = surfaceEngine_.boundaryPoints(); + const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const point pos = newEdgePositionLaplacian(bpI); - const point newP = 0.5 * (pos + points[bPoints[bpI]]); + const point pos = newEdgePositionLaplacian(bpI); + const point newP = 0.5 * (pos + points[bPoints[bpI]]); # ifdef DEBUGSearch Info << "New position for point is " << newP << endl; diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePointParallel.C b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePointParallel.C index 7b52a433d498766bdab95e7b4477822fe3be84aa..ab9b0192c48d74d5bb6648cc217e6418051cc3b5 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePointParallel.C +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizePointParallel.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,9 +32,9 @@ Description #include "meshSurfaceMapper.H" #include "surfaceOptimizer.H" #include "refLabelledPoint.H" -#include "helperFunctionsPar.H" +#include "helperFunctions.H" -// #define DEBUGSearch +//#define DEBUGSearch // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -46,75 +45,72 @@ namespace Foam void meshSurfaceOptimizer::nodeDisplacementLaplacianParallel ( - const labelListPMG& nodesToSmooth, + const labelLongList& nodesToSmooth, const bool transformIntoPlane ) { if( returnReduce(nodesToSmooth.size(), sumOp<label>()) == 0 ) return; - //- update vertex normals - meshSurfaceEngineModifier(surfaceEngine_).updateVertexNormals(); - - //- create storage for data - std::map<label, labelledPoint> localData; - + //- create storage for data + std::map<label, labelledPoint> localData; + //- exchange data with other processors std::map<label, LongList<refLabelledPoint> > exchangeData; - + const pointField& points = surfaceEngine_.points(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pPoints = surfaceEngine_.pointPoints(); + const VRWGraph& pPoints = surfaceEngine_.pointPoints(); const vectorField& pNormals = surfaceEngine_.pointNormals(); const labelList& globalPointLabel = surfaceEngine_.globalBoundaryPointLabel(); - const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); - const Map<label>& globalToLocal = - surfaceEngine_.globalToLocalBndPointAddressing(); - + const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndPointAddressing(); + //- perform smoothing forAll(nodesToSmooth, pI) { const label bpI = nodesToSmooth[pI]; - + if( magSqr(pNormals[bpI]) < VSMALL ) continue; - + const plane pl(points[bPoints[bpI]], pNormals[bpI]); - + //- project points onto the plane - localData.insert(std::make_pair(bpI, labelledPoint(0, vector::zero))); - labelledPoint& lpd = localData[bpI]; - - forAllRow(pPoints, bpI, ppI) - { - const label nei = pPoints(bpI, ppI); - - if( bpAtProcs.sizeOfRow(nei) != 0 ) - { - label pMin(Pstream::nProcs()); - forAllRow(bpAtProcs, nei, procI) - { - const label procJ = bpAtProcs(nei, procI); - if( (procJ < pMin) && bpAtProcs.contains(bpI, procJ) ) - pMin = procJ; - } - - if( pMin != Pstream::myProcNo() ) - continue; - } - - const point& p = points[bPoints[nei]]; - ++lpd.pointLabel(); - lpd.coordinates() += transformIntoPlane?pl.nearestPoint(p):p; + localData.insert(std::make_pair(bpI, labelledPoint(0, vector::zero))); + labelledPoint& lpd = localData[bpI]; + + forAllRow(pPoints, bpI, ppI) + { + const label nei = pPoints(bpI, ppI); + + if( bpAtProcs.sizeOfRow(nei) != 0 ) + { + label pMin(Pstream::nProcs()); + forAllRow(bpAtProcs, nei, procI) + { + const label procJ = bpAtProcs(nei, procI); + if( (procJ < pMin) && bpAtProcs.contains(bpI, procJ) ) + pMin = procJ; + } + + if( pMin != Pstream::myProcNo() ) + continue; + } + + const point& p = points[bPoints[nei]]; + ++lpd.pointLabel(); + lpd.coordinates() += transformIntoPlane?pl.nearestPoint(p):p; } - - forAllRow(bpAtProcs, bpI, procI) + + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + if( exchangeData.find(neiProc) == exchangeData.end() ) { exchangeData.insert @@ -122,108 +118,102 @@ void meshSurfaceOptimizer::nodeDisplacementLaplacianParallel std::make_pair(neiProc, LongList<refLabelledPoint>()) ); } - + //- add data to the list which will be sent to other processor - LongList<refLabelledPoint>& dts = exchangeData[neiProc]; - dts.append(refLabelledPoint(globalPointLabel[bpI], lpd)); + LongList<refLabelledPoint>& dts = exchangeData[neiProc]; + dts.append(refLabelledPoint(globalPointLabel[bpI], lpd)); } - } - - //- exchange data with other processors + } + + //- exchange data with other processors LongList<refLabelledPoint> receivedData; help::exchangeMap(exchangeData, receivedData); - + forAll(receivedData, i) { const refLabelledPoint& lp = receivedData[i]; const label bpI = globalToLocal[lp.objectLabel()]; - + labelledPoint& lpd = localData[bpI]; - + lpd.pointLabel() += lp.lPoint().pointLabel(); lpd.coordinates() += lp.lPoint().coordinates(); } - forAll(nodesToSmooth, pI) - { - const label bpI = nodesToSmooth[pI]; - - if( localData.find(bpI) == localData.end() ) - continue; - + forAll(nodesToSmooth, pI) + { + const label bpI = nodesToSmooth[pI]; + + if( localData.find(bpI) == localData.end() ) + continue; + //- create new point position const labelledPoint& lp = localData[bpI]; - const point newP = lp.coordinates() / lp.pointLabel(); - + const point newP = lp.coordinates() / lp.pointLabel(); + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); - surfaceModifier.moveBoundaryVertex + surfaceModifier.moveBoundaryVertexNoUpdate ( bpI, newP ); } - - //- update vertex normals - meshSurfaceEngineModifier(surfaceEngine_).updateVertexNormals(); } void meshSurfaceOptimizer::nodeDisplacementLaplacianFCParallel ( - const labelListPMG& nodesToSmooth, + const labelLongList& nodesToSmooth, const bool transformIntoPlane ) { if( returnReduce(nodesToSmooth.size(), sumOp<label>()) == 0 ) return; - //- update vertex normals - meshSurfaceEngineModifier(surfaceEngine_).updateVertexNormals(); - - //- create storage for data - std::map<label, labelledPoint> localData; - + //- create storage for data + std::map<label, labelledPoint> localData; + //- exchange data with other processors std::map<label, LongList<refLabelledPoint> > exchangeData; - + const pointField& points = surfaceEngine_.points(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pFaces = surfaceEngine_.pointFaces(); + const VRWGraph& pFaces = surfaceEngine_.pointFaces(); const vectorField& faceCentres = surfaceEngine_.faceCentres(); const vectorField& pNormals = surfaceEngine_.pointNormals(); - + const labelList& globalPointLabel = surfaceEngine_.globalBoundaryPointLabel(); - const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); - const Map<label>& globalToLocal = - surfaceEngine_.globalToLocalBndPointAddressing(); - + const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndPointAddressing(); + //- perform smoothing forAll(nodesToSmooth, pI) { const label bpI = nodesToSmooth[pI]; - + if( magSqr(pNormals[bpI]) < VSMALL ) continue; - + const plane pl(points[bPoints[bpI]], pNormals[bpI]); - + //- project points onto the plane - localData.insert(std::make_pair(bpI, labelledPoint(0, vector::zero))); - labelledPoint& lpd = localData[bpI]; - - forAllRow(pFaces, bpI, pfI) - { - const point& p = faceCentres[pFaces(bpI, pfI)]; - ++lpd.pointLabel(); - lpd.coordinates() += transformIntoPlane?pl.nearestPoint(p):p; + localData.insert(std::make_pair(bpI, labelledPoint(0, vector::zero))); + labelledPoint& lpd = localData[bpI]; + + forAllRow(pFaces, bpI, pfI) + { + const point& p = faceCentres[pFaces(bpI, pfI)]; + ++lpd.pointLabel(); + lpd.coordinates() += transformIntoPlane?pl.nearestPoint(p):p; } - - forAllRow(bpAtProcs, bpI, procI) + + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + if( exchangeData.find(neiProc) == exchangeData.end() ) { exchangeData.insert @@ -231,122 +221,154 @@ void meshSurfaceOptimizer::nodeDisplacementLaplacianFCParallel std::make_pair(neiProc, LongList<refLabelledPoint>()) ); } - + //- add data to the list which will be sent to other processor - LongList<refLabelledPoint>& dts = exchangeData[neiProc]; - dts.append(refLabelledPoint(globalPointLabel[bpI], lpd)); + LongList<refLabelledPoint>& dts = exchangeData[neiProc]; + dts.append(refLabelledPoint(globalPointLabel[bpI], lpd)); } - } - - //- exchange data with other processors + } + + //- exchange data with other processors LongList<refLabelledPoint> receivedData; help::exchangeMap(exchangeData, receivedData); - + forAll(receivedData, i) { const refLabelledPoint& lp = receivedData[i]; const label bpI = globalToLocal[lp.objectLabel()]; - + labelledPoint& lpd = localData[bpI]; - + lpd.pointLabel() += lp.lPoint().pointLabel(); lpd.coordinates() += lp.lPoint().coordinates(); } - forAll(nodesToSmooth, pI) - { - const label bpI = nodesToSmooth[pI]; - - if( localData.find(bpI) == localData.end() ) - continue; - + pointField newPositions(nodesToSmooth.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(nodesToSmooth, pI) + { + const label bpI = nodesToSmooth[pI]; + + if( localData.find(bpI) == localData.end() ) + { + newPositions[pI] = points[bPoints[bpI]]; + continue; + } + //- create new point position const labelledPoint& lp = localData[bpI]; - const point newP = lp.coordinates() / lp.pointLabel(); - - meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); - surfaceModifier.moveBoundaryVertex + const point newP = lp.coordinates() / lp.pointLabel(); + + newPositions[pI] = newP; + } + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(newPositions, pI) + { + surfaceModifier.moveBoundaryVertexNoUpdate ( - bpI, - newP + nodesToSmooth[pI], + newPositions[pI] ); } - - //- update vertex normals - meshSurfaceEngineModifier(surfaceEngine_).updateVertexNormals(); } void meshSurfaceOptimizer::nodeDisplacementSurfaceOptimizerParallel ( - const labelListPMG& nodesToSmooth + const labelLongList& nodesToSmooth ) { if( returnReduce(nodesToSmooth.size(), sumOp<label>()) == 0 ) return; - - //- update vertex normals + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); - surfaceModifier.updateVertexNormals(); - + //- exchange data with other processors std::map<label, DynList<parTriFace> > m; exchangeData(nodesToSmooth, m); - + const pointField& points = surfaceEngine_.points(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); const vectorField& pNormals = surfaceEngine_.pointNormals(); - + //- perform smoothing + pointField newPositions(nodesToSmooth.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 10) + # endif forAll(nodesToSmooth, pI) { const label bpI = nodesToSmooth[pI]; - + if( magSqr(pNormals[bpI]) < VSMALL ) + { + newPositions[pI] = points[bPoints[bpI]]; continue; - + } + plane pl(points[bPoints[bpI]], pNormals[bpI]); point vecX, vecY; DynList<point> pts; DynList<triFace> trias; - + if( !transformIntoPlaneParallel(bpI, pl, m, vecX, vecY, pts, trias) ) + { + newPositions[pI] = points[bPoints[bpI]]; continue; - + } + surfaceOptimizer so(pts, trias); point newPoint = so.optimizePoint(0.001); - + const point newP ( points[bPoints[bpI]] + vecX * newPoint.x() + vecY * newPoint.y() ); - - surfaceModifier.moveBoundaryVertex + + if( help::isnan(newP) || help::isinf(newP) ) + { + newPositions[pI] = points[bPoints[bpI]]; + } + else + { + newPositions[pI] = newP; + } + } + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(newPositions, pI) + surfaceModifier.moveBoundaryVertexNoUpdate ( - bpI, - newP + nodesToSmooth[pI], + newPositions[pI] ); - } - + //- make sure that moved points have the same coordinates on all processors surfaceModifier.syncVerticesAtParallelBoundaries(nodesToSmooth); - - //- update vertex normals - surfaceModifier.updateVertexNormals(); } void meshSurfaceOptimizer::edgeNodeDisplacementParallel ( - const labelListPMG& nodesToSmooth + const labelLongList& nodesToSmooth ) { - std::map<label, DynList<labelledPoint> > mPts; - + std::map<label, DynList<labelledPoint, 2> > mPts; + //- insert labels into the map const labelList& globalPointLabel = surfaceEngine_.globalBoundaryPointLabel(); - + forAll(nodesToSmooth, nI) { mPts.insert @@ -354,23 +376,27 @@ void meshSurfaceOptimizer::edgeNodeDisplacementParallel std::make_pair ( globalPointLabel[nodesToSmooth[nI]], - DynList<labelledPoint>(2) + DynList<labelledPoint, 2>() ) ); } - + //- add local edge points const pointField& points = surfaceEngine_.points(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pPoints = surfaceEngine_.pointPoints(); + const edgeList& edges = surfaceEngine_.edges(); + const VRWGraph& bpEdges = surfaceEngine_.boundaryPointEdges(); + const labelList& bp = surfaceEngine_.bp(); + forAll(nodesToSmooth, nI) { const label bpI = nodesToSmooth[nI]; - DynList<labelledPoint>& neiPoints = mPts[globalPointLabel[bpI]]; - - forAllRow(pPoints, bpI, ppI) + DynList<labelledPoint, 2>& neiPoints = mPts[globalPointLabel[bpI]]; + + forAllRow(bpEdges, bpI, epI) { - const label pI = pPoints(bpI, ppI); + const edge& e = edges[bpEdges(bpI, epI)]; + const label pI = bp[e.otherVertex(bPoints[bpI])]; if( vertexType_[pI] & (EDGE+CORNER) ) { neiPoints.append @@ -380,34 +406,36 @@ void meshSurfaceOptimizer::edgeNodeDisplacementParallel } } } - + //- start preparing data which can be exchanged with other processors const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); - + std::map<label, LongList<refLabelledPoint> > mProcs; forAll(neiProcs, procI) { const label neiProc = neiProcs[procI]; - + if( neiProc == Pstream::myProcNo() ) continue; - + mProcs.insert(std::make_pair(neiProc, LongList<refLabelledPoint>())); } forAll(nodesToSmooth, nI) { const label bpI = nodesToSmooth[nI]; - - const DynList<labelledPoint>& neiPoints = mPts[globalPointLabel[bpI]]; + + const DynList<labelledPoint, 2>& neiPoints = + mPts[globalPointLabel[bpI]]; + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - + forAll(neiPoints, npI) { LongList<refLabelledPoint>& neiProcPts = mProcs[neiProc]; @@ -418,59 +446,73 @@ void meshSurfaceOptimizer::edgeNodeDisplacementParallel } } } - + //- exchange data with other processors LongList<refLabelledPoint> receivedData; help::exchangeMap(mProcs, receivedData); - + forAll(receivedData, prI) { const refLabelledPoint& lp = receivedData[prI]; - DynList<labelledPoint>& lPts = mPts[lp.objectLabel()]; + DynList<labelledPoint, 2>& lPts = mPts[lp.objectLabel()]; lPts.appendIfNotIn(receivedData[prI].lPoint()); } - + //- Finally, the data is ready to start smoothing meshSurfaceEngineModifier sm(surfaceEngine_); - forAll(nodesToSmooth, nI) + + pointField newPositions(nodesToSmooth.size()); + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(nodesToSmooth, pI) { - const label bpI = nodesToSmooth[nI]; - - const DynList<labelledPoint>& nPts = mPts[globalPointLabel[bpI]]; + const label bpI = nodesToSmooth[pI]; + + const DynList<labelledPoint, 2>& nPts = mPts[globalPointLabel[bpI]]; point newP(vector::zero); forAll(nPts, ppI) newP += nPts[ppI].coordinates(); - - if( nPts.size() > 1 ) + + if( nPts.size() == 2 ) { newP /= nPts.size(); - sm.moveBoundaryVertex(bpI, newP); + newPositions[pI] = newP; + } + else + { + newPositions[pI] = points[bPoints[bpI]]; } } - - sm.updateVertexNormals(); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(newPositions, pI) + sm.moveBoundaryVertexNoUpdate(nodesToSmooth[pI], newPositions[pI]); } void meshSurfaceOptimizer::exchangeData ( - const labelListPMG& nodesToSmooth, + const labelLongList& nodesToSmooth, std::map<label, DynList<parTriFace> >& m ) const { + /* const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); - + std::map<label, LongList<parTriFace> > shareData; forAll(neiProcs, procI) { const label neiProc = neiProcs[procI]; - + if( neiProc == Pstream::myProcNo() ) continue; - + shareData.insert(std::make_pair(neiProc, LongList<parTriFace>())); } - + //- create data which will be sent to other processors const pointField& points = surfaceEngine_.points(); const labelList& globalPointLabel = @@ -478,28 +520,28 @@ void meshSurfaceOptimizer::exchangeData const labelList& bPoints = surfaceEngine_.boundaryPoints(); const LongList<triFace>& triangles = this->triangles(); const VRWGraph& pTriangles = pointTriangles(); - + m.clear(); std::map<label, DynList<parTriFace> >::iterator pIter; forAll(nodesToSmooth, nI) { const label bpI = nodesToSmooth[nI]; - + pIter = m.find(globalPointLabel[bpI]); if( pIter == m.end() ) { m.insert ( - std::make_pair(globalPointLabel[bpI], DynList<parTriFace>(6)) + std::make_pair(globalPointLabel[bpI], DynList<parTriFace>()) ); - + pIter = m.find(globalPointLabel[bpI]); } - + forAll(pTriangles[bpI], ptI) { const triFace& tri = triangles[pTriangles[bpI][ptI]]; - + parTriFace ptf ( globalPointLabel[tri[0]], @@ -515,44 +557,45 @@ void meshSurfaceOptimizer::exchangeData pIter->second.append(ptf); } - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + LongList<parTriFace>& shData = shareData[neiProc]; - + const DynList<parTriFace>& localData = pIter->second; - + forAll(localData, i) shData.append(localData[i]); } } - + //- send data to other processors LongList<parTriFace> receivedData; help::exchangeMap(shareData, receivedData); - + forAll(receivedData, tI) { const label gpI = receivedData[tI].globalLabelOfPoint(0); - + pIter = m.find(gpI); if( pIter == m.end() ) { FatalErrorIn ( "void meshSurfaceOptimizer::exchangeData(" - "const labelListPMG& nodesToSmooth," + "const labelLongList& nodesToSmooth," "map<label, DynList<parTriFace> >& m" ") const" ) << "Unknown point " << gpI << abort(FatalError); } - + pIter->second.append(receivedData[tI]); } + */ } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizeSurface.C b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizeSurface.C index ca21f7369d5bb96273586cacb94ed778bd074df3..2a2abf07eae5bb73ca972897785b2b6d0fde3849 100644 --- a/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizeSurface.C +++ b/meshLibrary/utilities/smoothers/geometry/meshSurfaceOptimizer/meshSurfaceOptimizerOptimizeSurface.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -34,10 +33,17 @@ Description #include "triangle.H" #include "helperFunctionsPar.H" #include "meshSurfaceMapper.H" +#include "meshSurfaceMapper2D.H" +#include "polyMeshGen2DEngine.H" +#include "polyMeshGenAddressing.H" #include "labelledPoint.H" +#include "FIFOStack.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGSmooth @@ -50,25 +56,26 @@ namespace Foam label meshSurfaceOptimizer::findInvertedVertices ( - boolList& smoothVertex + boolList& smoothVertex, + const label nAdditionalLayers ) const { - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pPoints = surfaceEngine_.pointPoints(); - + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + const VRWGraph& pPoints = surfaceEngine_.pointPoints(); + if( smoothVertex.size() != bPoints.size() ) { smoothVertex.setSize(bPoints.size()); smoothVertex = true; } - - label nInvertedTria(0); - + + label nInvertedTria(0); + //- check the vertices at the surface //- mark the ones where the mesh is tangled - meshSurfaceCheckInvertedVertices vrtCheck(surfaceEngine_, &smoothVertex); + meshSurfaceCheckInvertedVertices vrtCheck(surfaceEngine_, smoothVertex); const labelHashSet& inverted = vrtCheck.invertedVertices(); - + smoothVertex = false; forAll(bPoints, bpI) { @@ -78,23 +85,23 @@ label meshSurfaceOptimizer::findInvertedVertices smoothVertex[bpI] = true; } } - + if( Pstream::parRun() ) reduce(nInvertedTria, sumOp<label>()); - Info << "Number of inverted boundary faces is " << nInvertedTria << endl; - + Info << "Number of inverted boundary faces is " << nInvertedTria << endl; + if( nInvertedTria == 0 ) return 0; - - //- add additional layers around inverted points - for(label i=0;i<2;++i) - { - boolList originallySelected = smoothVertex; - forAll(smoothVertex, bpI) - if( originallySelected[bpI] ) - forAllRow(pPoints, bpI, ppI) - smoothVertex[pPoints(bpI, ppI)] = true; - + + //- add additional layers around inverted points + for(label i=0;i<nAdditionalLayers;++i) + { + boolList originallySelected = smoothVertex; + forAll(smoothVertex, bpI) + if( originallySelected[bpI] ) + forAllRow(pPoints, bpI, ppI) + smoothVertex[pPoints(bpI, ppI)] = true; + if( Pstream::parRun() ) { //- exchange global labels of inverted points @@ -104,319 +111,763 @@ label meshSurfaceOptimizer::findInvertedVertices surfaceEngine_.globalToLocalBndPointAddressing(); const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); - - std::map<label, labelListPMG> shareData; + + std::map<label, labelLongList> shareData; forAll(neiProcs, procI) shareData.insert ( - std::make_pair(neiProcs[procI], labelListPMG()) + std::make_pair(neiProcs[procI], labelLongList()) ); - + forAllConstIter(Map<label>, globalToLocal, iter) { const label bpI = iter(); - + if( !smoothVertex[bpI] ) continue; - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - + shareData[neiProc].append(globalPointLabel[bpI]); } } - + //- exchange data with other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(shareData, receivedData); - + forAll(receivedData, j) { const label bpI = globalToLocal[receivedData[j]]; - + smoothVertex[bpI] = true; } } - } - - return nInvertedTria; + } + + return nInvertedTria; +} + +void meshSurfaceOptimizer::smoothEdgePoints +( + const labelLongList& edgePoints, + const labelLongList& procEdgePoints +) +{ + DynList<LongList<labelledPoint> > newPositions(1); + # ifdef USE_OMP + newPositions.setSize(omp_get_num_procs()); + # endif + + //- smooth edge vertices + # ifdef USE_OMP + # pragma omp parallel num_threads(newPositions.size()) + # endif + { + # ifdef USE_OMP + LongList<labelledPoint>& newPos = + newPositions[omp_get_thread_num()]; + # else + LongList<labelledPoint>& newPos = newPositions[0]; + # endif + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(edgePoints, i) + { + const label bpI = edgePoints[i]; + + if( vertexType_[bpI] & PROCBND ) + continue; + + newPos.append(labelledPoint(bpI, newEdgePositionLaplacian(bpI))); + } + } + + if( Pstream::parRun() ) + edgeNodeDisplacementParallel(procEdgePoints); + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + forAll(newPositions, threadI) + { + const LongList<labelledPoint>& newPos = newPositions[threadI]; + + forAll(newPos, i) + surfaceModifier.moveBoundaryVertexNoUpdate + ( + newPos[i].pointLabel(), + newPos[i].coordinates() + ); + } + + surfaceModifier.updateGeometry(edgePoints); +} + +void meshSurfaceOptimizer::smoothLaplacianFC +( + const labelLongList& selectedPoints, + const labelLongList& selectedProcPoints, + const bool transform +) +{ + DynList<LongList<labelledPoint> > newPositions(1); + # ifdef USE_OMP + newPositions.setSize(omp_get_num_procs()); + # endif + + # ifdef USE_OMP + # pragma omp parallel num_threads(newPositions.size()) + # endif + { + # ifdef USE_OMP + LongList<labelledPoint>& newPos = + newPositions[omp_get_thread_num()]; + # else + LongList<labelledPoint>& newPos = newPositions[0]; + # endif + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(selectedPoints, i) + { + const label bpI = selectedPoints[i]; + + if( vertexType_[bpI] & PROCBND ) + continue; + + newPos.append + ( + labelledPoint(bpI, newPositionLaplacianFC(bpI, transform)) + ); + } + } + + if( Pstream::parRun() ) + nodeDisplacementLaplacianFCParallel(selectedProcPoints, transform); + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + + # ifdef USE_OMP + # pragma omp parallel num_threads(newPositions.size()) + # endif + { + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI = 0; + # endif + + const LongList<labelledPoint>& newPos = newPositions[threadI]; + + forAll(newPos, i) + surfaceModifier.moveBoundaryVertexNoUpdate + ( + newPos[i].pointLabel(), + newPos[i].coordinates() + ); + } + + surfaceModifier.updateGeometry(selectedPoints); } -void meshSurfaceOptimizer::preOptimizeSurface() +void meshSurfaceOptimizer::smoothSurfaceOptimizer +( + const labelLongList& selectedPoints +) { - Info << "Optimizing positions of surface nodes" << endl; + this->triMesh(); + updateTriMesh(selectedPoints); + + pointField newPositions(selectedPoints.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(selectedPoints, i) + { + const label bpI = selectedPoints[i]; + + newPositions[i] = newPositionSurfaceOptimizer(bpI); + } + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 100) + # endif + forAll(newPositions, i) + { + const label bpI = selectedPoints[i]; + + surfaceModifier.moveBoundaryVertexNoUpdate(bpI, newPositions[i]); + } - const labelList& bPoints = surfaceEngine_.boundaryPoints(); + //- update geometry addressing for moved points + surfaceModifier.updateGeometry(selectedPoints); +} + +bool meshSurfaceOptimizer::untangleSurface +( + const labelLongList& selectedBoundaryPoints, + const label nAdditionalLayers +) +{ + Info << "Starting untangling the surface of the volume mesh" << endl; + + bool changed(false); + + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + const pointFieldPMG& points = surfaceEngine_.points(); surfaceEngine_.pointFaces(); surfaceEngine_.faceCentres(); surfaceEngine_.pointPoints(); surfaceEngine_.boundaryFacePatches(); surfaceEngine_.pointNormals(); - this->triangles(); - this->pointTriangles(); - - boolList smoothVertex; - - meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + surfaceEngine_.boundaryPointEdges(); + + if( Pstream::parRun() ) + { + surfaceEngine_.bpAtProcs(); + surfaceEngine_.globalToLocalBndPointAddressing(); + surfaceEngine_.globalBoundaryPointLabel(); + surfaceEngine_.bpNeiProcs(); + } + + boolList smoothVertex(bPoints.size(), false); + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(selectedBoundaryPoints, i) + smoothVertex[selectedBoundaryPoints[i]] = true; + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); meshSurfaceMapper mapper(surfaceEngine_, meshOctree_); - - bool remapVertex(true); - label nInvertedTria; - label nGlobalIter(0); - - labelListPMG procBndNodes, movedPoints; - - do - { - label nIter(0); - - do - { - nInvertedTria = findInvertedVertices(smoothVertex); - - if( nInvertedTria == 0 ) break; - - procBndNodes.clear(); - movedPoints.clear(); - forAll(bPoints, bpI) + + bool remapVertex(true); + label nInvertedTria; + label nGlobalIter(0); + + labelLongList procBndPoints, movedPoints; + labelLongList procEdgePoints, movedEdgePoints; + + label minNumInverted(bPoints.size()); + FIFOStack<label> nInvertedHistory; + pointField minInvertedPoints(bPoints.size()); + + do + { + label nIter(0), nAfterRefresh(0); + + do + { + nInvertedTria = + findInvertedVertices(smoothVertex, nAdditionalLayers); + + if( nInvertedTria == 0 ) break; + + //- find the min number of inverted points and + //- add the last number to the stack + if( nInvertedTria < minNumInverted ) { - if( smoothVertex[bpI] && (vertexType_[bpI] & PARTITION) ) - { - movedPoints.append(bpI); - - if( vertexType_[bpI] & PROCBND ) - { - procBndNodes.append(bpI); - continue; - } - } + minNumInverted = nInvertedTria; + nAfterRefresh = 0; + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 100) + # endif + forAll(bPoints, bpI) + minInvertedPoints[bpI] = points[bPoints[bpI]]; } - - //- use laplacian smoothing - # pragma omp parallel + + //- count the number of iteration after the last minimum occurence + ++nAfterRefresh; + + //- update the stack + nInvertedHistory.push(nInvertedTria); + if( nInvertedHistory.size() > 2 ) + nInvertedHistory.pop(); + + //- check if the number of inverted points reduces + bool minimumInStack(false); + forAllConstIter(FIFOStack<label>, nInvertedHistory, it) + if( it() == minNumInverted ) + minimumInStack = true; + + //- stop if the procedure does not minimise + //- the number of inverted points + if( !minimumInStack || (nAfterRefresh > 2) ) + break; + + //- find points which will be handled by the smoothers + changed = true; + + procBndPoints.clear(); + movedPoints.clear(); + procEdgePoints.clear(); + movedEdgePoints.clear(); + + forAll(bPoints, bpI) { - LongList<labelledPoint> newPos; - - # pragma omp for schedule(guided) - forAll(movedPoints, i) + if( !smoothVertex[bpI] ) + continue; + + if( vertexType_[bpI] & PARTITION ) { - const label bpI = movedPoints[i]; - + movedPoints.append(bpI); + if( vertexType_[bpI] & PROCBND ) - continue; - - newPos.append - ( - labelledPoint(bpI, newPositionLaplacianFC(bpI)) - ); + procBndPoints.append(bpI); } - - forAll(newPos, i) - surfaceModifier.moveBoundaryVertexNoUpdate - ( - newPos[i].pointLabel(), - newPos[i].coordinates() - ); - } - - if( Pstream::parRun() ) - nodeDisplacementLaplacianFCParallel(procBndNodes, true); - - surfaceModifier.updateGeometry(movedPoints); - - //- use surface optimizer - # pragma omp parallel - { - LongList<labelledPoint> newPos; - - # pragma omp for schedule(guided) - forAll(movedPoints, i) + else if( vertexType_[bpI] & EDGE ) { - const label bpI = movedPoints[i]; - + movedEdgePoints.append(bpI); + if( vertexType_[bpI] & PROCBND ) - continue; - - newPos.append - ( - labelledPoint(bpI, newPositionSurfaceOptimizer(bpI)) - ); + procEdgePoints.append(bpI); } - - forAll(newPos, i) - surfaceModifier.moveBoundaryVertexNoUpdate - ( - newPos[i].pointLabel(), - newPos[i].coordinates() - ); } - - if( Pstream::parRun() ) - nodeDisplacementSurfaceOptimizerParallel(procBndNodes); - + + //- smooth edge vertices + smoothEdgePoints(movedEdgePoints, procEdgePoints); + if( remapVertex ) + mapper.mapEdgeNodes(movedEdgePoints); + surfaceModifier.updateGeometry(movedEdgePoints); + + //- use laplacian smoothing + smoothLaplacianFC(movedPoints, procBndPoints); surfaceModifier.updateGeometry(movedPoints); - + + //- use surface optimizer + smoothSurfaceOptimizer(movedPoints); + if( remapVertex ) mapper.mapVerticesOntoSurface(movedPoints); - - } while( nInvertedTria && (++nIter < 20) ); - - if( nInvertedTria ) - { - Info << "Smoothing remaining inverted vertices " << endl; - + + //- update normals and other geometric data + surfaceModifier.updateGeometry(movedPoints); + + } while( nInvertedTria && (++nIter < 20) ); + + if( nInvertedTria > 0 ) + { + //- use the combination with the minimu number of inverted points + meshSurfaceEngineModifier sMod(surfaceEngine_); + forAll(minInvertedPoints, bpI) + sMod.moveBoundaryVertexNoUpdate(bpI, minInvertedPoints[bpI]); + + sMod.updateGeometry(); + } + + if( nInvertedTria ) + { + Info << "Smoothing remaining inverted vertices " << endl; + movedPoints.clear(); - procBndNodes.clear(); - forAll(smoothVertex, bpI) - if( smoothVertex[bpI] ) - { + procBndPoints.clear(); + forAll(smoothVertex, bpI) + if( smoothVertex[bpI] ) + { movedPoints.append(bpI); - + if( vertexType_[bpI] & PROCBND ) - { - procBndNodes.append(bpI); - continue; - } - - nodeDisplacementLaplacianFC(bpI, false); - } - - if( Pstream::parRun() ) - { - nodeDisplacementLaplacianFCParallel(procBndNodes, false); - } - + procBndPoints.append(bpI); + } + + smoothLaplacianFC(movedPoints, procBndPoints, false); + if( remapVertex ) mapper.mapVerticesOntoSurface(movedPoints); - - if( nGlobalIter > 3 ) - remapVertex = false; - } - - } while( nInvertedTria && (++nGlobalIter < 10) ); - - Info << "Finished optimizing positions of surface nodes" << endl; + + //- update normals and other geometric data + surfaceModifier.updateGeometry(movedPoints); + + if( nGlobalIter > 3 ) + remapVertex = false; + } + + } while( nInvertedTria && (++nGlobalIter < 10) ); + + Info << "Finished untangling the surface of the volume mesh" << endl; + + return changed; +} + +bool meshSurfaceOptimizer::untangleSurface(const label nAdditionalLayers) +{ + labelLongList selectedPts(surfaceEngine_.boundaryPoints().size()); + forAll(selectedPts, i) + selectedPts[i] = i; + + return untangleSurface(selectedPts, nAdditionalLayers); } void meshSurfaceOptimizer::optimizeSurface(const label nIterations) { - const labelList& bPoints = surfaceEngine_.boundaryPoints(); - + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + //- needed for parallel execution surfaceEngine_.pointFaces(); surfaceEngine_.faceCentres(); surfaceEngine_.pointPoints(); + surfaceEngine_.boundaryPointEdges(); surfaceEngine_.boundaryFacePatches(); surfaceEngine_.pointNormals(); - - labelListPMG procBndNodes, edgePoints; + surfaceEngine_.boundaryPointEdges(); + + labelLongList procBndPoints, edgePoints; forAll(bPoints, bpI) { if( vertexType_[bpI] & EDGE ) { edgePoints.append(bpI); - + if( vertexType_[bpI] & PROCBND ) - procBndNodes.append(bpI); + procBndPoints.append(bpI); } } - - meshSurfaceMapper mapper(surfaceEngine_, meshOctree_); - - //- optimize edge vertices - Info << "Optimizing edges. Iteration:" << flush; - for(label i=0;i<nIterations;++i) - { - Info << "." << flush; - + + meshSurfaceMapper mapper(*partitionerPtr_, meshOctree_); + + //- optimize edge vertices + Info << "Optimizing edges. Iteration:" << flush; + for(label i=0;i<nIterations;++i) + { + Info << "." << flush; + meshSurfaceEngineModifier bMod(surfaceEngine_); - # pragma omp parallel if( edgePoints.size() > 1000 ) - { - LongList<labelledPoint> newPos; - - # pragma omp for schedule(dynamic, 20) - forAll(edgePoints, epI) - { - const label bpI = edgePoints[epI]; - - if( vertexType_[bpI] & PROCBND ) - continue; - - const point newP = newEdgePositionLaplacian(bpI); - newPos.append(labelledPoint(bpI, newP)); - } - - forAll(newPos, i) - bMod.moveBoundaryVertexNoUpdate - ( - newPos[i].pointLabel(), - newPos[i].coordinates() - ); - } - - bMod.updateGeometry(edgePoints); - - if( Pstream::parRun() ) - { - edgeNodeDisplacementParallel(procBndNodes); - } - + + smoothEdgePoints(edgePoints, procBndPoints); + + //- project vertices back onto the boundary mapper.mapEdgeNodes(edgePoints); - } - Info << endl; - - //- optimize nodes of surface vertices which are not on surface edges - Info << "Optimizing surface vertices. Iteration:"; - for(label i=0;i<nIterations;++i) - { - procBndNodes.clear(); - - Info << "." << flush; + + //- update the geometry information + bMod.updateGeometry(edgePoints); + } + Info << endl; + + //- optimize positions of surface vertices which are not on surface edges + Info << "Optimizing surface vertices. Iteration:"; + for(label i=0;i<nIterations;++i) + { + procBndPoints.clear(); + + pointField newPositions(bPoints.size()); + + Info << "." << flush; meshSurfaceEngineModifier bMod(surfaceEngine_); + # ifdef USE_OMP # pragma omp parallel if( vertexType_.size() > 100 ) + # endif { - LongList<labelledPoint> newPos; - + # ifdef USE_OMP # pragma omp for schedule(dynamic, 10) + # endif forAll(bPoints, bpI) + { if( vertexType_[bpI] & PARTITION ) { if( vertexType_[bpI] & PROCBND ) { + # ifdef USE_OMP # pragma omp critical + # endif { - procBndNodes.append(bpI); + procBndPoints.append(bpI); } - + continue; } - - const point newP = newPositionLaplacianFC(bpI); - newPos.append(labelledPoint(bpI, newP)); + + newPositions[bpI] = newPositionLaplacianFC(bpI, true); } - - forAll(newPos, i) - bMod.moveBoundaryVertexNoUpdate - ( - newPos[i].pointLabel(), - newPos[i].coordinates() - ); + } } - - bMod.updateGeometry(); - + if( Pstream::parRun() ) { - nodeDisplacementLaplacianFCParallel(procBndNodes,true); + nodeDisplacementLaplacianFCParallel(procBndPoints, true); + } + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 100) + # endif + forAll(newPositions, bpI) + { + if( vertexType_[bpI] == PARTITION ) + bMod.moveBoundaryVertexNoUpdate(bpI, newPositions[bpI]); + } + + //- update fields calculated from points + bMod.updateGeometry(); + } + + Info << endl; + + untangleSurface(0); +} + +void meshSurfaceOptimizer::optimizeSurface2D(const label nIterations) +{ + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + const edgeList& edges = surfaceEngine_.edges(); + const labelList& bp = surfaceEngine_.bp(); + + polyMeshGen2DEngine mesh2DEngine + ( + const_cast<polyMeshGen&>(surfaceEngine_.mesh()) + ); + const boolList& zMinPoint = mesh2DEngine.zMinPoints(); + + //- needed for parallel execution + surfaceEngine_.pointFaces(); + surfaceEngine_.faceCentres(); + surfaceEngine_.pointPoints(); + surfaceEngine_.boundaryPointEdges(); + surfaceEngine_.boundaryFacePatches(); + surfaceEngine_.pointNormals(); + + labelLongList procBndPoints, movedPoints, activeEdges, updatePoints; + forAll(edges, beI) + { + const edge& e = edges[beI]; + + if( zMinPoint[e.start()] ^ zMinPoint[e.end()] ) + { + label bpI = bp[e.start()]; + if( !zMinPoint[e.start()] ) + bpI = bp[e.end()]; + + if( vertexType_[bpI] & EDGE ) + { + activeEdges.append(beI); + + updatePoints.append(bp[e.start()]); + updatePoints.append(bp[e.end()]); + + movedPoints.append(bpI); + + if( vertexType_[bpI] & PROCBND ) + procBndPoints.append(bpI); + } } - } - + } + + meshSurfaceMapper2D mapper(surfaceEngine_, meshOctree_); + + //- optimize edge vertices + meshSurfaceEngineModifier bMod(surfaceEngine_); + + Info << "Optimizing edges. Iteration:" << flush; + for(label i=0;i<nIterations;++i) + { + Info << "." << flush; + + smoothEdgePoints(movedPoints, procBndPoints); + + //- move points with maximum z coordinate + mesh2DEngine.correctPoints(); + + //- map boundary edges to the surface + mapper.mapVerticesOntoSurfacePatches(activeEdges); + + //- update normal, centres, etc, after the surface has been modified + bMod.updateGeometry(updatePoints); + } Info << endl; + + //- optimize Pts of surface vertices which are not on surface edges + procBndPoints.clear(); + movedPoints.clear(); + forAll(bPoints, bpI) + if( zMinPoint[bPoints[bpI]] && (vertexType_[bpI] & PARTITION) ) + { + movedPoints.append(bpI); + + if( vertexType_[bpI] & PROCBND ) + procBndPoints.append(bpI); + } + Info << "Optimizing surface vertices. Iteration:"; + for(label i=0;i<nIterations;++i) + { + Info << "." << flush; + + smoothLaplacianFC(movedPoints, procBndPoints, false); + + //- move the points which are not at minimum z coordinate + mesh2DEngine.correctPoints(); + + //- update geometrical data due to movement of vertices + bMod.updateGeometry(); + } + + Info << endl; +} + +void meshSurfaceOptimizer::untangleSurface2D() +{ + const polyMeshGen& mesh = surfaceEngine_.mesh(); + const faceListPMG& faces = mesh.faces(); + const VRWGraph& pointFaces = mesh.addressingData().pointFaces(); + + const labelList& bPoints = surfaceEngine_.boundaryPoints(); + const labelList& bp = surfaceEngine_.bp(); + + polyMeshGen2DEngine mesh2DEngine(const_cast<polyMeshGen&>(mesh)); + const boolList& zMinPoint = mesh2DEngine.zMinPoints(); + const boolList& activeFace = mesh2DEngine.activeFace(); + + //- needed for parallel execution + surfaceEngine_.pointFaces(); + surfaceEngine_.faceCentres(); + surfaceEngine_.pointPoints(); + surfaceEngine_.boundaryPointEdges(); + surfaceEngine_.boundaryFacePatches(); + surfaceEngine_.pointNormals(); + + boolList activeBoundaryPoint(bPoints.size()); + boolList changedFace(activeFace.size(), true); + + label iterationI(0); + do + { + labelHashSet badFaces; + const label nBadFaces = findBadFaces(badFaces, changedFace); + + Info << "Iteration " << iterationI + << ". Number of bad faces " << nBadFaces << endl; + + if( nBadFaces == 0 ) + break; + + //- update active points and faces affected by the movement + //- of active points + activeBoundaryPoint = false; + changedFace = false; + forAllConstIter(labelHashSet, badFaces, it) + { + const face& f = faces[it.key()]; + + forAll(f, pI) + { + if( zMinPoint[f[pI]] ) + { + activeBoundaryPoint[bp[f[pI]]] = true; + + forAllRow(pointFaces, f[pI], pfI) + changedFace[pointFaces(f[pI], pfI)] = true; + } + } + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndPointAddressing(); + const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); + const VRWGraph& bpNeiProcs = surfaceEngine_.bpAtProcs(); + + std::map<label, labelLongList> exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + //- collect active points at inter-processor boundaries + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + if( activeBoundaryPoint[bpI] ) + { + forAllRow(bpNeiProcs, bpI, i) + { + const label neiProc = bpNeiProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append(it.key()); + } + } + } + + //- exchange active points among the processors + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + //- ensure that all processors have the same Pts active + forAll(receivedData, i) + { + const label bpI = globalToLocal[receivedData[i]]; + + //- activate this boundary point + activeBoundaryPoint[bpI] = true; + + //- set the changeFaces for the faces attached to this point + forAllRow(pointFaces, bPoints[bpI], pfI) + changedFace[pointFaces(bPoints[bpI], pfI)] = true; + } + } + + //- apply smoothing to the activated points + meshSurfaceEngineModifier bMod(surfaceEngine_); + + labelLongList movedPts, procBndPts, edgePts, procEdgePts; + forAll(bPoints, bpI) + { + if( !activeBoundaryPoint[bpI] ) + continue; + + if( vertexType_[bpI] & EDGE ) + { + edgePts.append(bpI); + + if( vertexType_[bpI] & PROCBND ) + procEdgePts.append(bpI); + } + else if( vertexType_[bpI] & PARTITION ) + { + movedPts.append(bpI); + + if( vertexType_[bpI] & PROCBND ) + procBndPts.append(bpI); + } + } + + for(label i=0;i<5;++i) + { + smoothEdgePoints(edgePts, procEdgePts); + + bMod.updateGeometry(edgePts); + + smoothSurfaceOptimizer(movedPts); + + bMod.updateGeometry(movedPts); + } + + //- move the points which are not at minimum z coordinate + mesh2DEngine.correctPoints(); + + //- update geometrical data due to movement of vertices + bMod.updateGeometry(); + + //- update cell centres and face centres + const_cast<polyMeshGenAddressing&> + ( + mesh.addressingData() + ).updateGeometry(changedFace); + + } while( ++iterationI < 20 ); + + //- delete invalid data + mesh.clearAddressingData(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.C b/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.C index da774bbc4c120bfda8da6a0f4197fb59723a90dc..090c884400c1d9b51be54f5c57787a4b8b2c0bd5 100644 --- a/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.C +++ b/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,9 @@ Description #include "decomposeFaces.H" #include "decomposeCells.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGCheck @@ -52,40 +53,42 @@ void checkBoundaryFacesSharingTwoEdges::createMeshSurface() const void checkBoundaryFacesSharingTwoEdges::findFacesAtBndEdge() { const meshSurfaceEngine& mse = meshSurface(); - + const labelList& bp = mse.bp(); const edgeList& edges = mse.edges(); const VRWGraph& pointEdges = mse.boundaryPointEdges(); - + const label nIntFaces = mesh_.nInternalFaces(); const faceListPMG& faces = mesh_.faces(); - + //- find the internal faces attached to the boundary points removeBndPoint_.setSize(pointEdges.size()); removeBndPoint_ = true; - + + # ifdef USE_OMP # pragma omp parallel for if( nIntFaces > 100 ) schedule(dynamic, 20) + # endif for(label fI=0;fI<nIntFaces;++fI) { const face& f = faces[fI]; - + forAll(f, pI) { const label bpI = bp[f[pI]]; - + if( bpI < 0 ) continue; - + if( nBndFacesAtBndPoint_[bpI] == 2 ) { const edge ePrev = f.faceEdge(f.rcIndex(pI)); const edge eNext = f.faceEdge(pI); - + bool foundNext(false), foundPrev(false); forAllRow(pointEdges, bpI, peI) { const label beI = pointEdges(bpI, peI); - + if( edges[beI] == ePrev ) { foundPrev = true; @@ -95,7 +98,7 @@ void checkBoundaryFacesSharingTwoEdges::findFacesAtBndEdge() foundNext = true; } } - + if( !(foundPrev && foundNext) ) { removeBndPoint_[bpI] = false; @@ -107,39 +110,41 @@ void checkBoundaryFacesSharingTwoEdges::findFacesAtBndEdge() } } } - + if( Pstream::parRun() ) { //- check processor faces - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - + + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 10) + # endif for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; - + forAll(f, pI) { const label bpI = bp[f[pI]]; - + if( bpI < 0 ) continue; - + if( nBndFacesAtBndPoint_[bpI] == 2 ) { const edge ePrev = f.faceEdge(f.rcIndex(pI)); const edge eNext = f.faceEdge(pI); - + bool foundNext(false), foundPrev(false); forAllRow(pointEdges, bpI, peI) { const label beI = pointEdges(bpI, peI); - + if( edges[beI] == ePrev ) { foundPrev = true; @@ -149,7 +154,7 @@ void checkBoundaryFacesSharingTwoEdges::findFacesAtBndEdge() foundNext = true; } } - + if( !(foundPrev && foundNext) ) removeBndPoint_[bpI] = false; } @@ -160,38 +165,38 @@ void checkBoundaryFacesSharingTwoEdges::findFacesAtBndEdge() } } } - + //- make sure that all processors have the same information const DynList<label>& bpNei = mse.bpNeiProcs(); const VRWGraph& bpAtProcs = mse.bpAtProcs(); const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - - std::map<label, labelListPMG> exchangeData; + + std::map<label, labelLongList> exchangeData; forAll(bpNei, i) - exchangeData.insert(std::make_pair(bpNei[i], labelListPMG())); - + exchangeData.insert(std::make_pair(bpNei[i], labelLongList())); + forAllConstIter(Map<label>, globalToLocal, it) { const label bpI = it(); - + if( removeBndPoint_[bpI] ) continue; - + //- the point shall not be removed forAllRow(bpAtProcs, bpI, i) { const label neiProc = bpAtProcs(bpI, i); if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append(it.key()); } } - + //- exchange data - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); - + //- set remove flag to false forAll(receivedData, i) removeBndPoint_[globalToLocal[receivedData[i]]] = false; @@ -202,44 +207,44 @@ void checkBoundaryFacesSharingTwoEdges::findBndFacesAtBndVertex() { const meshSurfaceEngine& mse = meshSurface(); const VRWGraph& pointFaces = mse.pointFaces(); - + nBndFacesAtBndPoint_.setSize(pointFaces.size()); nBndFacesAtBndPoint_ = 0; - + forAll(nBndFacesAtBndPoint_, bpI) nBndFacesAtBndPoint_[bpI] = pointFaces.sizeOfRow(bpI); - + if( Pstream::parRun() ) { const VRWGraph& bpAtProcs = mse.bpAtProcs(); const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); const DynList<label>& neiProcs = mse.bpNeiProcs(); - + //- create data that shall be exhcnaged - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAll(neiProcs, i) - exchangeData.insert(std::make_pair(neiProcs[i], labelListPMG())); - + exchangeData.insert(std::make_pair(neiProcs[i], labelLongList())); + forAllConstIter(Map<label>, globalToLocal, it) { const label bpI = it(); - + forAllRow(bpAtProcs, bpI, i) { const label neiProc = bpAtProcs(bpI, i); if( neiProc == Pstream::myProcNo() ) continue; - - labelListPMG& data = exchangeData[neiProc]; + + labelLongList& data = exchangeData[neiProc]; data.append(it.key()); data.append(nBndFacesAtBndPoint_[bpI]); } } - + //- exchange data with other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); - + label counter(0); while( counter < receivedData.size() ) { @@ -253,16 +258,18 @@ void checkBoundaryFacesSharingTwoEdges::removeExcessiveVertices() { const labelList& bp = meshSurface().bp(); const faceListPMG& faces = mesh_.faces(); - + //- remove points which can be safely be removed //- internal faces const label nIntFaces = mesh_.nInternalFaces(); - + + # ifdef USE_OMP # pragma omp parallel for if( nIntFaces > 100 ) schedule(dynamic, 10) + # endif for(label faceI=0;faceI<nIntFaces;++faceI) { const face& f = faces[faceI]; - + DynList<label> newF; forAll(f, pI) { @@ -273,10 +280,10 @@ void checkBoundaryFacesSharingTwoEdges::removeExcessiveVertices() (nBndFacesAtBndPoint_[bpI] == 2) ) continue; - + newF.append(f[pI]); } - + if( newF.size() < f.size() ) { face& mf = const_cast<face&>(f); @@ -285,30 +292,32 @@ void checkBoundaryFacesSharingTwoEdges::removeExcessiveVertices() mf[i] = newF[i]; } } - + //- boundary faces forAll(mesh_.boundaries(), patchI) { const label start = mesh_.boundaries()[patchI].patchStart(); const label end = start + mesh_.boundaries()[patchI].patchSize(); - + + # ifdef USE_OMP # pragma omp parallel for if( end - start > 100 ) \ schedule(dynamic, 10) + # endif for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; - + DynList<label> newF; forAll(f, pI) { const label bpI = bp[f[pI]]; - + if( removeBndPoint_[bpI] && (nBndFacesAtBndPoint_[bpI] == 2) ) continue; - + newF.append(f[pI]); } - + if( newF.size() < f.size() ) { face& mf = const_cast<face&>(f); @@ -318,39 +327,41 @@ void checkBoundaryFacesSharingTwoEdges::removeExcessiveVertices() } } } - + //- processor boundaries forAll(mesh_.procBoundaries(), patchI) { - const writeProcessorPatch& patch = mesh_.procBoundaries()[patchI]; + const processorBoundaryPatch& patch = mesh_.procBoundaries()[patchI]; const label start = patch.patchStart(); const label end = start + patch.patchSize(); - + + # ifdef USE_OMP # pragma omp parallel for if( patch.patchSize() > 100 ) \ schedule(dynamic, 10) + # endif for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; - + DynList<label> newF; forAll(f, pI) { const label bpI = bp[f[pI]]; - + if( (bpI >= 0) && removeBndPoint_[bpI] && (nBndFacesAtBndPoint_[bpI] == 2) ) continue; - + newF.append(f[pI]); } - + if( newF.size() < f.size() ) { face& mf = const_cast<face&>(f); mf.setSize(newF.size()); - + if( !patch.owner() && (newF[0] != f[0]) ) { forAll(mf, i) @@ -374,20 +385,22 @@ label checkBoundaryFacesSharingTwoEdges::findBndFacesForDecomposition const meshSurfaceEngine& mse = meshSurface(); const labelList& bp = mse.bp(); const faceList::subList& bFaces = mse.boundaryFaces(); - + label nDecomposed(0); const label nIntFaces = mesh_.nInternalFaces(); - + + # ifdef USE_OMP # pragma omp parallel for if( bFaces.size() > 100 ) \ schedule(dynamic, 10) reduction(+ : nDecomposed) + # endif forAll(bFaces, bfI) { const face& bf = bFaces[bfI]; - + forAll(bf, pI) { const label bpI = bp[bf[pI]]; - + if( nBndFacesAtBndPoint_[bpI] == 2 ) { ++nDecomposed; @@ -395,9 +408,9 @@ label checkBoundaryFacesSharingTwoEdges::findBndFacesForDecomposition } } } - + reduce(nDecomposed, sumOp<label>()); - + return nDecomposed; } @@ -428,15 +441,15 @@ checkBoundaryFacesSharingTwoEdges::~checkBoundaryFacesSharingTwoEdges() void checkBoundaryFacesSharingTwoEdges::findPoints(labelHashSet& badPoints) { badPoints.clear(); - + findBndFacesAtBndVertex(); - + const labelList& bPoints = meshSurface().boundaryPoints(); forAll(nBndFacesAtBndPoint_, bpI) { if( nBndFacesAtBndPoint_[bpI] != 2 ) continue; - + badPoints.insert(bPoints[bpI]); } } @@ -444,23 +457,23 @@ void checkBoundaryFacesSharingTwoEdges::findPoints(labelHashSet& badPoints) bool checkBoundaryFacesSharingTwoEdges::improveTopology() { bool changed(false); - + findBndFacesAtBndVertex(); findFacesAtBndEdge(); removeExcessiveVertices(); - + boolList decomposeFace(mesh_.faces().size(), false); const label nDecomposed = findBndFacesForDecomposition(decomposeFace); - + Info << "Marked " << nDecomposed << " faces for decomposition" << endl; - + if( nDecomposed != 0 ) { //- delete the mesh surface engine deleteDemandDrivenData(meshSurfacePtr_); - + //- find cells which will be decomposed boolList decomposeCell(mesh_.cells().size(), false); const labelList& owner = mesh_.owner(); @@ -469,20 +482,20 @@ bool checkBoundaryFacesSharingTwoEdges::improveTopology() if( decomposeFace[faceI] ) decomposeCell[owner[faceI]]; } - + //- decompose marked faces decomposeFaces(mesh_).decomposeMeshFaces(decomposeFace); - + //- decompose cells VRWGraph pRegions(mesh_.points().size()); decomposeCells dc(mesh_); dc.decomposeMesh(decomposeCell); - + changed = true; } - + polyMeshGenModifier(mesh_).removeUnusedVertices(); - + return changed; } diff --git a/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.H b/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.H index 7a925f1bf4673258ea95941c818cde6c0b045484..23c6f3851ff62770546fb305a4fc23dd700a9b40 100644 --- a/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.H +++ b/meshLibrary/utilities/smoothers/topology/checkBoundaryFacesSharingTwoEdges/checkBoundaryFacesSharingTwoEdges.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class checkBoundaryFacesSharingTwoEdges @@ -59,7 +58,7 @@ class checkBoundaryFacesSharingTwoEdges { // Private data //- Reference to polyMeshGen - polyMeshGen& mesh_; + polyMeshGen& mesh_; //- pointer to meshSurfaceEngine mutable meshSurfaceEngine* meshSurfacePtr_; @@ -118,7 +117,7 @@ public: // Member Functions //- find boundary points connected to two boundary faces, only - void findPoints(labelHashSet& badPoints); + void findPoints(labelHashSet& badPoints); //- find boundary points connected to two boundary faces //- remove points if possible, decompose boundary faces otherwise diff --git a/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.C b/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.C index 4ed98b2ef830c68c49213e741eadf8f4cdf03a33..a67d16d3d68fa24757027df8951dc011359eb593 100644 --- a/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.C +++ b/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.C @@ -1,42 +1,42 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ #include "checkCellConnectionsOverFaces.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "labelledPair.H" -#include "helperFunctionsPar.H" +# ifdef USE_OMP #include <omp.h> +# endif + #include <set> #include <map> #include "helperFunctions.H" -#include "writeMeshFPMA.H" //#define DEBUGCheck @@ -47,790 +47,156 @@ namespace Foam // * * * * * * * * * * Private member functions * * * * * * * * * * * * * * * // -typedef std::pair<label, label> lPair; -typedef std::pair<lPair, lPair> lPairPair; -typedef std::pair<lPair, label> lPairLabel; - -inline Ostream& operator<<(Ostream& os, const lPair& lp) +namespace meshConnectionsHelper { - os << token::BEGIN_LIST; - os << lp.first; - os << token::SPACE; - os << lp.second; - os << token::END_LIST; - - return os; -} -inline Istream& operator>>(Istream& is, lPair& lp) +class meshConnectionsNeighbourOperator { - is.readBegin("lPair"); - - is >> lp.first; - is >> lp.second; - - is.readEnd("lPair"); - is.check("operator>>(Istream&, lPair&"); - - return is; -} + const polyMeshGen& mesh_; -inline Ostream& operator<<(Ostream& os, const lPairPair& lp) -{ - os << token::BEGIN_LIST; - os << lp.first; - os << token::SPACE; - os << lp.second; - os << token::END_LIST; - - return os; -} +public: -inline Istream& operator>>(Istream& is, lPairPair& lp) -{ - is.readBegin("lPairPair"); - - is >> lp.first; - is >> lp.second; - - is.readEnd("lPairPair"); - is.check("operator>>(Istream&, lPairPair&"); - - return is; -} + meshConnectionsNeighbourOperator(const polyMeshGen& mesh) + : + mesh_(mesh) + {} -inline Ostream& operator<<(Ostream& os, const lPairLabel& lp) -{ - os << token::BEGIN_LIST; - os << lp.first; - os << token::SPACE; - os << lp.second; - os << token::END_LIST; - - return os; -} + label size() const + { + return mesh_.cells().size(); + } -inline Istream& operator>>(Istream& is, lPairLabel& lp) -{ - is.readBegin("lPairLabel"); - - is >> lp.first; - is >> lp.second; - - is.readEnd("lPairLabel"); - is.check("operator>>(Istream&, lPairLabel&"); - - return is; -} + void operator()(const label cellI, DynList<label>& neighbourCells) const + { + neighbourCells.clear(); -template<> -inline bool contiguous<lPairPair>() {return true;} + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); -template<> -inline bool contiguous<lPairLabel>() {return true;} + const cell& c = mesh_.cells()[cellI]; -class groupingOp -{ - // Private data - //- map containing group connections - std::map<lPair, std::set<lPair> >& groupMap_; - - // Private member functions - //- sort neighbouring groups - void sortNeighbouringGroups() - { - typedef std::set<lPair> pairSet; - typedef std::map<lPair, pairSet> gMap; - - DynList<lPair> eraseRow; - - for - ( - gMap::reverse_iterator it=groupMap_.rbegin(); - it!=groupMap_.rend(); - ++it - ) - { - const pairSet& neiGroups = it->second; - - gMap::reverse_iterator rIt = it; - for(++rIt;rIt!=groupMap_.rend();++rIt) - { - pairSet& otherGroups = rIt->second; - - if( otherGroups.find(it->first) != otherGroups.end() ) - { - //- add all neighbours of current group to - //- otherGroups - for - ( - pairSet::const_iterator sIter=neiGroups.begin(); - sIter!=neiGroups.end(); - ++sIter - ) - otherGroups.insert(*sIter); - - eraseRow.append(it->first); - } - else - { - for - ( - pairSet::const_iterator sIter=neiGroups.begin(); - sIter!=neiGroups.end(); - ++sIter - ) - { - const lPair& lp = *sIter; - - if( otherGroups.find(lp) != otherGroups.end() ) - { - eraseRow.append(it->first); - otherGroups.insert(it->first); - - pairSet::const_iterator sIt; - for - ( - sIt=neiGroups.begin(); - sIt!=neiGroups.end(); - ++sIt - ) - rIt->second.insert(*sIt); - - break; - } - } - } - } - } - - forAll(eraseRow, rowI) - groupMap_.erase(eraseRow[rowI]); - } - - public: - - // Constructor - //- construct from map - groupingOp(std::map<lPair, std::set<lPair> >& groupMap) - : - groupMap_(groupMap) - { - sortNeighbouringGroups(); - } - - // Public member functions - //- prepare information for sending to other processors - void dataForNeighbourProc - ( - DynList<lPairLabel>& groupLabels, - const label procNo, - const labelList& globalGroupLabel - ) const - { - groupLabels.clear(); - - typedef std::map<lPair, std::set<lPair> > gMap; - typedef std::set<lPair> pairSet; - - pairSet alreadyAdded; - - forAllConstIter(gMap, groupMap_, it) - { - if( it->first.first != Pstream::myProcNo() ) - continue; - - const pairSet& neiGroups = it->second; - - forAllConstIter(pairSet, neiGroups, sIt) - { - if( alreadyAdded.find(*sIt) != alreadyAdded.end() ) - continue; - - groupLabels.append - ( - std::make_pair - ( - *sIt, - globalGroupLabel[it->first.second] - ) - ); - - alreadyAdded.insert(*sIt); - } - } - } - - template<class ListType> - bool updateGlobalGroupLabels - ( - labelList& globalGroupLabel, - const ListType& receivedGroups - ) const - { - bool changed(false); - - forAll(receivedGroups, i) - { - const lPairLabel& lpl = receivedGroups[i]; - - if( lpl.first.first != Pstream::myProcNo() ) - continue; - - if( lpl.second < globalGroupLabel[lpl.first.second] ) - { - globalGroupLabel[lpl.first.second] = lpl.second; - changed = true; - } - } - - if( updateGlobalGroupLabels(globalGroupLabel) ) - changed = true; - - return changed; - } - - bool updateGlobalGroupLabels(labelList& globalGroupLabel) const + forAll(c, fI) { - typedef std::map<lPair, std::set<lPair> > gMap; - typedef std::set<lPair> pairSet; - - bool changed(false); - - forAllConstIter(gMap, groupMap_, it) - { - if( it->first.first != Pstream::myProcNo() ) - continue; - - const label groupI = globalGroupLabel[it->first.second]; - - const pairSet& neiGroups = it->second; - forAllConstIter(pairSet, neiGroups, sIt) - { - if( sIt->first != Pstream::myProcNo() ) - continue; - - if( globalGroupLabel[sIt->second] < groupI ) - { - forAllConstIter(pairSet, neiGroups, sIt2) - { - if( sIt2->first == Pstream::myProcNo() ) - globalGroupLabel[sIt2->second] = - globalGroupLabel[sIt->second]; - } - - changed = true; - } - else if( globalGroupLabel[sIt->second] > groupI ) - { - forAllConstIter(pairSet, neiGroups, sIt2) - { - if( sIt2->first == Pstream::myProcNo() ) - globalGroupLabel[sIt2->second] = groupI; - } - - changed = true; - } - } - } - - return changed; - } - - bool exchangeDataTopToBottom(labelList& globalGroupLabel) const - { - bool changed(false); - - const Pstream::commsStruct& myComm = - Pstream::treeCommunication()[Pstream::myProcNo()]; - - //- propagate data to the processors below - LongList<lPairLabel> propagateData; - - if( myComm.above() != -1 ) - { - List<lPairLabel> receivedGroupLabels; - IPstream fromOtherProc - ( - Pstream::scheduled, - myComm.above() - ); - - fromOtherProc >> receivedGroupLabels; - - forAll(receivedGroupLabels, i) - { - if( - receivedGroupLabels[i].first.first <= - Pstream::myProcNo() - ) - continue; - - propagateData.append(receivedGroupLabels[i]); - } - - bool check = - updateGlobalGroupLabels - ( - globalGroupLabel, - receivedGroupLabels - ); - - if( check ) - changed = true; - } - - forAll(myComm.below(), belowI) - { - //- send the data to the processors below - DynList<lPairLabel> sendGroupLabels; - dataForNeighbourProc - ( - sendGroupLabels, - myComm.below()[belowI], - globalGroupLabel - ); - - forAll(propagateData, i) - sendGroupLabels.append(propagateData[i]); - - OPstream toOtherProc - ( - Pstream::scheduled, - myComm.below()[belowI], - sendGroupLabels.byteSize() - ); - - toOtherProc << sendGroupLabels; - } - - reduce(changed, maxOp<bool>()); - - return changed; - } - - bool exchangeDataBottomToTop(labelList& globalGroupLabel) const - { - bool changed(false); - - const Pstream::commsStruct& myComm = - Pstream::treeCommunication()[Pstream::myProcNo()]; - - //- propagate data to the processors above - LongList<lPairLabel> propagateData; - forAll(myComm.below(), belowI) - { - IPstream fromOtherProc - ( - Pstream::scheduled, - myComm.below()[belowI] - ); - - List<lPairLabel> receivedGroups; - fromOtherProc >> receivedGroups; - - forAll(receivedGroups, i) - { - if( receivedGroups[i].first.first >= Pstream::myProcNo() ) - continue; - - propagateData.append(receivedGroups[i]); - } - - bool check = - updateGlobalGroupLabels - ( - globalGroupLabel, - receivedGroups - ); - if( check ) - changed = true; - } - - if( myComm.above() != -1 ) - { - DynList<lPairLabel> sendData; - dataForNeighbourProc - ( - sendData, - myComm.above(), - globalGroupLabel - ); - - forAll(propagateData, i) - sendData.append(propagateData[i]); - - OPstream toOtherProc - ( - Pstream::scheduled, - myComm.above(), - sendData.byteSize() - ); - - toOtherProc << sendData; - } - - reduce(changed, maxOp<bool>()); - - return changed; - } - - bool exchangeDataNeighbours(labelList& globalGroupLabel) - { - bool changed(false); - - typedef std::map<label, LongList<lPairLabel> > dMap; - dMap exchangeData; - typedef std::map<lPair, std::set<lPair> > gMap; - typedef std::set<lPair> pairSet; - forAllConstIter(gMap, groupMap_, it) - { - if( it->first.first != Pstream::myProcNo() ) - continue; - - const label groupLabel = globalGroupLabel[it->first.second]; - const pairSet& neiGroups = it->second; - forAllConstIter(pairSet, neiGroups, sIt) - { - const label neiProcNo = sIt->first; - - if( neiProcNo == Pstream::myProcNo() ) - continue; - - dMap::iterator mapIt = exchangeData.find(neiProcNo); - if( mapIt == exchangeData.end() ) - { - exchangeData.insert - ( - std::make_pair(neiProcNo, LongList<lPairLabel>()) - ); - mapIt = exchangeData.find(neiProcNo); - } - - mapIt->second.append(lPairLabel(*sIt, groupLabel)); - } - } - - LongList<lPairLabel> receivedGroups; - help::exchangeMap(exchangeData, receivedGroups); - - changed = updateGlobalGroupLabels(globalGroupLabel, receivedGroups); - reduce(changed, maxOp<bool>()); - - return changed; - } -}; + label nei = owner[c[fI]]; -void checkCellConnectionsOverFaces::findCellGroups() -{ - Info << "Checking cell connections" << endl; - - //mesh_.write(); - //returnReduce(1, sumOp<label>()); - //::exit(1); - - const cellListPMG& cells = mesh_.cells(); - const labelList& owner = mesh_.owner(); - const labelList& neighbour = mesh_.neighbour(); - - labelListPMG front, communicationFaces; - label chunkI(0), nChunks, chunkSize; - VRWGraph neighbouringGroups; - - # pragma omp parallel if( cells.size() > 1000 ) \ - private(front, communicationFaces) - { - //- set the number of chunks and their size - //- the number of chunks is greater than the number of threads - //- in order to enhance load balancing - # pragma omp master - { - nChunks = 3 * omp_get_num_threads(); - chunkSize = cells.size() / nChunks + 1; - } - - # pragma omp flush(nChunks, chunkSize) - - # pragma omp barrier - - while( chunkI < nChunks ) - { - label minCell, maxCell; - # pragma omp critical - minCell = chunkI++ * chunkSize; - - if( minCell >= cells.size() ) - break; - - maxCell = Foam::min(cells.size(), minCell + chunkSize); - - for(label cellI=minCell;cellI<maxCell;++cellI) - { - if( cellGroup_[cellI] != -1 ) - continue; - - label groupI; - # pragma omp critical - groupI = nGroups_++; - - front.clear(); - front.append(cellI); - cellGroup_[cellI] = groupI; - - while( front.size() ) - { - const label fLabel = front.removeLastElement(); - - const cell& c = cells[fLabel]; - - forAll(c, fI) - { - label nei = owner[c[fI]]; - if( nei == fLabel ) - nei = neighbour[c[fI]]; - - if( nei < 0 ) - continue; - - if( (nei < minCell) || (nei >= maxCell) ) - { - communicationFaces.append(c[fI]); - } - else if( cellGroup_[nei] == -1 ) - { - cellGroup_[nei] = groupI; - front.append(nei); - } - } - } - } - } - - # pragma omp barrier - - # pragma omp master - { - neighbouringGroups.setSize(nGroups_); - forAll(neighbouringGroups, groupI) - neighbouringGroups.append(groupI, groupI); - } - - # pragma omp barrier - - //- find group to neighbouring groups addressing - forAll(communicationFaces, cfI) - { - const label faceI = communicationFaces[cfI]; - const label groupI = cellGroup_[owner[faceI]]; - const label neiGroup = cellGroup_[neighbour[faceI]]; - - if( (neiGroup >= nGroups_) || (groupI >= nGroups_) ) - FatalError << "neiGroup " << neiGroup - << " groupI " << groupI << " are >= than " - << "nGroups " << nGroups_ << abort(FatalError); - - if( neiGroup != -1 ) - { - # pragma omp critical - { - if( !neighbouringGroups.contains(groupI, neiGroup) ) - neighbouringGroups.append(groupI, neiGroup); - } - } + if( nei == cellI ) + nei = neighbour[c[fI]]; + + if( nei >= 0 ) + neighbourCells.append(nei); } } - - //- check global label for each group - chunkI = 0; - if( Pstream::parRun() ) - { - labelList nGroupsAtProc(Pstream::nProcs()); - nGroupsAtProc[Pstream::myProcNo()] = nGroups_; - - Pstream::gatherList(nGroupsAtProc); - Pstream::scatterList(nGroupsAtProc); - - for(label procI=0;procI<Pstream::myProcNo();++procI) - chunkI += nGroupsAtProc[procI]; - } - - globalGroupLabel_.setSize(nGroups_); - forAll(globalGroupLabel_, i) - globalGroupLabel_[i] = chunkI++; - - //- check global group labels - //- resolve groups for SMP parallelisation - bool changed; - do - { - changed = false; - - forAllReverse(neighbouringGroups, groupI) - { - label minGroup = globalGroupLabel_[groupI]; - - forAllRow(neighbouringGroups, groupI, i) - { - const label currGroup = neighbouringGroups(groupI, i); - minGroup = Foam::min(minGroup, globalGroupLabel_[currGroup]); - } - - forAllRow(neighbouringGroups, groupI, i) - { - const label currGroup = neighbouringGroups(groupI, i); - - if( globalGroupLabel_[currGroup] != minGroup ) - { - globalGroupLabel_[currGroup] = minGroup; - changed = true; - } - } - } - } while( changed ); - if( Pstream::parRun() ) + template<class labelListType> + void collectGroups + ( + std::map<label, DynList<label> >& neiGroups, + const labelListType& elementInGroup, + const DynList<label>& localGroupLabel + ) const { - //- send global group labels - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - - //- create ranges on processor boundaries - //- each pair represent the groups which are neighbours over - //- processor boundaries - std::map<lPair, std::set<lPair> > groupMap; - - //- insert local groups - forAll(neighbouringGroups, groupI) - { - std::set<lPair>& neiGroups = - groupMap[std::make_pair(Pstream::myProcNo(), groupI)]; - forAllRow(neighbouringGroups, groupI, i) - { - neiGroups.insert - ( - std::make_pair - ( - Pstream::myProcNo(), - neighbouringGroups(groupI, i) - ) - ); - } - } - - //- create ranges for sending + const labelList& owner = mesh_.owner(); + + //- send the data to other processors forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); - const label end = start + procBoundaries[patchI].patchSize(); - - LongList<labelledPair> dataToSend; - - label currGroup = cellGroup_[owner[start]]; - label groupStart(0); - for(label faceI=start;faceI<end;++faceI) + const label size = procBoundaries[patchI].patchSize(); + + labelList groupOwner(procBoundaries[patchI].patchSize()); + for(label faceI=0;faceI<size;++faceI) { - if( currGroup != cellGroup_[owner[faceI]] ) + const label groupI = elementInGroup[owner[start+faceI]]; + + if( groupI < 0 ) { - labelPair lp(groupStart, faceI-start); - dataToSend.append(labelledPair(currGroup, lp)); - - currGroup = cellGroup_[owner[faceI]]; - groupStart = faceI - start; + groupOwner[faceI] = -1; + continue; } + + groupOwner[faceI] = localGroupLabel[groupI]; } - - dataToSend.append - ( - labelledPair(currGroup, labelPair(groupStart, end-start)) - ); - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), - dataToSend.byteSize() + groupOwner.byteSize() ); - toOtherProc << dataToSend; + + toOtherProc << groupOwner; } - - //- receive ranges and create neighbour pairs + + //- receive data from other processors forAll(procBoundaries, patchI) { - List<labelledPair> receivedGroups; - - const writeProcessorPatch& procPatch = procBoundaries[patchI]; - + const label start = procBoundaries[patchI].patchStart(); + + labelList receivedData; + IPstream fromOtherProc ( Pstream::blocking, - procPatch.neiProcNo() + procBoundaries[patchI].neiProcNo() ); - fromOtherProc >> receivedGroups; - - const label start = procPatch.patchStart(); - forAll(receivedGroups, i) + + fromOtherProc >> receivedData; + + forAll(receivedData, faceI) { - const label neiGroup = receivedGroups[i].pairLabel(); - const labelPair& pair = receivedGroups[i].pair(); - - label currGroup = cellGroup_[owner[start+pair.first()]]; - for(label fI=pair.first();fI<pair.second();++fI) - { - const label groupI = cellGroup_[owner[start+fI]]; - std::set<lPair>& createdGroupPairs = - groupMap[lPair(Pstream::myProcNo(), currGroup)]; - - if( groupI != currGroup ) - { - createdGroupPairs.insert - ( - lPair(procPatch.neiProcNo(), neiGroup) - ); - currGroup = groupI; - } - } - - groupMap[lPair(Pstream::myProcNo(), currGroup)].insert - ( - lPair(procPatch.neiProcNo(), neiGroup) - ); + if( receivedData[faceI] < 0 ) + continue; + + const label groupI = elementInGroup[owner[start+faceI]]; + + if( groupI < 0 ) + continue; + + DynList<label>& ng = neiGroups[localGroupLabel[groupI]]; + + //- store the connection over the inter-processor boundary + ng.appendIfNotIn(receivedData[faceI]); } } - - //- resolve local groups based on inter-procesor connections - //- if two group of a processor share the same group at some other - //- processor then these two groups are the same group - groupingOp gop(groupMap); - gop.updateGlobalGroupLabels(globalGroupLabel_); - - //- the process of determining global group labels is iterative - //- and is performed in multigrid-like manner - //- a single iteration of the process consists of the following: - //- 1. send data to the processors below in the tree structure - //- 2. Each processor update global group labels based on neighbour data - //- and the group labels received from other processors - //- 3. send data to the processors above in the tree structure - do - { - changed = false; - - if( gop.exchangeDataTopToBottom(globalGroupLabel_) ) - changed = true; - - if( gop.exchangeDataNeighbours(globalGroupLabel_) ) - changed = true; - - if( gop.exchangeDataBottomToTop(globalGroupLabel_) ) - changed = true; - - reduce(changed, maxOp<bool>()); - } while( changed ); } - - nGroups_ = Foam::max(globalGroupLabel_) + 1; - reduce(nGroups_, maxOp<label>()); - - Info << "Finished checking cell connections" << endl; +}; + +class meshConnectionsSelectorOperator +{ + +public: + + meshConnectionsSelectorOperator() + {} + + bool operator()(const label cellI) const + { + return true; + } +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace meshConnectionsHelper + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void checkCellConnectionsOverFaces::findCellGroups() +{ + Info << "Checking cell connections" << endl; + + mesh_.owner(); + nGroups_ = + help::groupMarking + ( + cellGroup_, + meshConnectionsHelper::meshConnectionsNeighbourOperator(mesh_), + meshConnectionsHelper::meshConnectionsSelectorOperator() + ); + + Info << "Finished checking cell connections" << endl; } // * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * * * * * // @@ -840,7 +206,6 @@ checkCellConnectionsOverFaces::checkCellConnectionsOverFaces(polyMeshGen& mesh) : mesh_(mesh), cellGroup_(mesh.cells().size(), -1), - globalGroupLabel_(), nGroups_(0) { findCellGroups(); @@ -849,8 +214,7 @@ checkCellConnectionsOverFaces::checkCellConnectionsOverFaces(polyMeshGen& mesh) // * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * * * * * // checkCellConnectionsOverFaces::~checkCellConnectionsOverFaces() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -860,18 +224,18 @@ bool checkCellConnectionsOverFaces::checkCellGroups() return false; Warning << "Mesh has " << nGroups_ << " unconnected regions" << endl; - + labelList nCellsInGroup(nGroups_, 0); - + forAll(cellGroup_, cI) - ++nCellsInGroup[globalGroupLabel_[cellGroup_[cI]]]; - + ++nCellsInGroup[cellGroup_[cI]]; + if( Pstream::parRun() ) { forAll(nCellsInGroup, groupI) reduce(nCellsInGroup[groupI], sumOp<label>()); } - + //- find groups which has most cells this group will be kept label maxGroup(-1); forAll(nCellsInGroup, groupI) @@ -880,15 +244,15 @@ bool checkCellConnectionsOverFaces::checkCellGroups() maxGroup = nCellsInGroup[groupI]; nGroups_ = groupI; } - + //- remove cells which are not in the group which has max num of cells boolList removeCell(mesh_.cells().size(), false); forAll(cellGroup_, cellI) - if( globalGroupLabel_[cellGroup_[cellI]] != nGroups_ ) + if( cellGroup_[cellI] != nGroups_ ) removeCell[cellI] = true; - + polyMeshGenModifier(mesh_).removeCells(removeCell); - + return true; } diff --git a/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.H b/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.H index 13300e7427a4864d0602447e04dbb83968f1093f..c6a92efc65455b297c62b71876cf53928dcd6160 100644 --- a/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.H +++ b/meshLibrary/utilities/smoothers/topology/checkCellConnectionsOverFaces/checkCellConnectionsOverFaces.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class checkCellConnectionsOverFaces @@ -51,22 +50,19 @@ class checkCellConnectionsOverFaces { // Private data //- Reference to polyMeshGen - polyMeshGen& mesh_; - + polyMeshGen& mesh_; + //- each cell is assigned a group //- cells which can be visited over face neighbours are assigned //- to the same group - labelList cellGroup_; - - //- global group label (needed for parallel execution) - labelList globalGroupLabel_; - + labelList cellGroup_; + //- number of groups label nGroups_; // Private member functions - //- decompose marked cells - void findCellGroups(); + //- decompose marked cells + void findCellGroups(); //- Disallow default bitwise copy construct checkCellConnectionsOverFaces(const checkCellConnectionsOverFaces&); @@ -88,7 +84,7 @@ public: // Member Functions //- check if all cells are connected as a single domain //- return true if the mesh has been changed - bool checkCellGroups(); + bool checkCellGroups(); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.C b/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.C index 4e698d0165dc1c389a191157341f7cd2a9a7689b..4954e16133f157febee8e73a42153fe36e17cefe 100644 --- a/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.C +++ b/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.H b/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.H index b3c3fb861b055c61b232efc08c29e36ba8909d3f..a36666e9e33b27563635ff789e732652406cdb4d 100644 --- a/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.H +++ b/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnections.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class checkIrregularSurfaceConnections @@ -54,7 +53,7 @@ class checkIrregularSurfaceConnections { // Private data //- Reference to polyMeshGen - polyMeshGen& mesh_; + polyMeshGen& mesh_; //- pointer to meshSurfaceEngine mutable meshSurfaceEngine* meshSurfacePtr_; @@ -75,9 +74,9 @@ class checkIrregularSurfaceConnections deleteDemandDrivenData(meshSurfacePtr_); } - //- check if there exist vertices with more than one groups of cells + //- check if there exist vertices with more than one groups of cells //- attached to it - bool checkAndFixCellGroupsAtBndVertices + bool checkAndFixCellGroupsAtBndVertices ( labelHashSet& badVertices, const bool removeConnections = false @@ -122,7 +121,7 @@ public: // Member Functions //- find vertices where the surface is not valid - void checkIrregularVertices(labelHashSet& badVertices); + void checkIrregularVertices(labelHashSet& badVertices); //- find invalid connections and fix them on the fly bool checkAndFixIrregularConnections(); diff --git a/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnectionsFunctions.C b/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnectionsFunctions.C index 94fa6dcd2f765cc66f896f61f9224706dff3fe37..56df4fa23b2fe124faac80ed81d8f13574394ab4 100644 --- a/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnectionsFunctions.C +++ b/meshLibrary/utilities/smoothers/topology/checkIrregularSurfaceConnections/checkIrregularSurfaceConnectionsFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,7 +30,9 @@ Description #include "helperFunctionsPar.H" #include "sortEdgesIntoChains.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGCheck @@ -49,57 +50,59 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices ) { Info << "Checking cells connected to surface vertices" << endl; - + const meshSurfaceEngine& mse = surfaceEngine(); const labelList& bPoints = mse.boundaryPoints(); - + polyMeshGenModifier meshModifier(mesh_); pointFieldPMG& points = meshModifier.pointsAccess(); faceListPMG& faces = meshModifier.facesAccess(); cellListPMG& cells = meshModifier.cellsAccess(); - + const VRWGraph& cellCells = mesh_.addressingData().cellCells(); const VRWGraph& pointCells = mesh_.addressingData().pointCells(); - + boolList parallelBndNode(bPoints.size(), false); if( Pstream::parRun() ) { const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - + forAllConstIter(Map<label>, globalToLocal, it) parallelBndNode[it()] = true; } - + //- check cells connected to surface nodes //- cells connected to a vertex must create a single loop when cells //- are visited over faces from to the other label nBadVertices(0); - DynList<label> frontCells(100); - + DynList<label> frontCells; + const label size = bPoints.size(); + # ifdef USE_OMP # pragma omp parallel for private(frontCells) schedule(dynamic, 1000) + # endif for(label bpI=0;bpI<size;++bpI) { if( parallelBndNode[bpI] ) continue; - + const label pointI = bPoints[bpI]; - + Map<label> cellGroup(pointCells.sizeOfRow(pointI)); - + label nGroup(0); - + forAllRow(pointCells, pointI, cI) { const label cellI = pointCells(pointI, cI); - - if( cellGroup.found(cellI) ) + + if( cellGroup.found(cellI) ) continue; - + cellGroup.insert(cellI, nGroup); frontCells.clear(); frontCells.append(cellI); - + while( frontCells.size() != 0 ) { const label cLabel = frontCells.removeLastElement(); @@ -107,52 +110,54 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices forAllRow(cellCells, cLabel, nI) { const label neiCell = cellCells(cLabel, nI); - + if( cellGroup.found(neiCell) ) continue; - + if( pointCells.contains(pointI, neiCell) ) { cellGroup.insert(neiCell, nGroup); frontCells.append(neiCell); } } - + } - + ++nGroup; } - + if( nGroup != 1 ) { + # ifdef USE_OMP # pragma omp critical + # endif { ++nBadVertices; badVertices.insert(pointI); - + if( removeConnections ) { const label nPoints = points.size(); forAllRow(pointCells, pointI, pcI) { const label cellI = pointCells(pointI, pcI); - + if( cellGroup[cellI] != 0 ) { const cell& c = cells[cellI]; - + forAll(c, fI) { face& f = faces[c[fI]]; - + const label pos = f.which(pointI); - + if( pos > -1 ) f[pos] = nPoints + cellGroup[cellI] - 1; } } } - + for(label i=1;i<nGroup;++i) { const point p = points[pointI]; @@ -162,99 +167,99 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices } } } - + if( Pstream::parRun() ) { //- check if the vertices at processor boundaries //- are connected correctly const labelList& bp = mse.bp(); const label origNumVertices = bp.size(); - + const labelList& owner = mesh_.owner(); const labelList& neighbour = mesh_.neighbour(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - - const labelListPMG& globalCellLabel = + + const labelLongList& globalCellLabel = mesh_.addressingData().globalCellLabel(); - + std::map<label, DynList<edge> > dualEdgesForPoint; std::map<label, DynList<edge> >::iterator bpIter; forAll(parallelBndNode, bpI) { if( !parallelBndNode[bpI] ) continue; - + dualEdgesForPoint.insert ( - std::make_pair(bpI, DynList<edge>(10)) + std::make_pair(bpI, DynList<edge>()) ); } - + //- fill-in dualEdgesForPoint with local data for(label faceI=0;faceI<mesh_.nInternalFaces();++faceI) { const face& f = faces[faceI]; - + forAll(f, pI) { if( f[pI] >= origNumVertices ) continue; - + bpIter = dualEdgesForPoint.find(bp[f[pI]]); if( bpIter != dualEdgesForPoint.end() ) { const label cOwn = globalCellLabel[owner[faceI]]; const label cNei = globalCellLabel[neighbour[faceI]]; - + //- store the edge bpIter->second.append(edge(cOwn, cNei)); } } } - + //- fill-in with data at processor boundaries. Store edges //- on the processor with the lower label not to duplicate the data forAll(procBoundaries, patchI) { if( procBoundaries[patchI].owner() ) continue; - + const label start = procBoundaries[patchI].patchStart(); labelList globalLabels(procBoundaries[patchI].patchSize()); forAll(globalLabels, fI) globalLabels[fI] = globalCellLabel[owner[start+fI]]; - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), globalLabels.byteSize() ); - + toOtherProc << globalLabels; } - + forAll(procBoundaries, patchI) { if( !procBoundaries[patchI].owner() ) continue; - + labelList receivedData; IPstream fromOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo() ); - + fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + forAll(receivedData, i) { const face& f = faces[start+i]; - + forAll(f, pI) { bpIter = dualEdgesForPoint.find(bp[f[pI]]); @@ -267,13 +272,13 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices } } } - + //- exchange data with other processors //- this step supplies all processors with all necessary data const VRWGraph& bpAtProcs = mse.bpAtProcs(); const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; for ( bpIter=dualEdgesForPoint.begin(); @@ -282,18 +287,18 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices ) { const label bpI = bpIter->first; - + forAllRow(bpAtProcs, bpI, i) { const label neiProc = bpAtProcs(bpI, i); if( neiProc == Pstream::myProcNo() ) continue; - + //- edges are sent to other processors as follows //- 1. global point label //- 2. number of edges at node //- 3. labels of edges - labelListPMG& dts = exchangeData[neiProc]; + labelLongList& dts = exchangeData[neiProc]; const DynList<edge>& edges = bpIter->second; dts.append(globalPointLabel[bpI]); dts.append(edges.size()); @@ -304,16 +309,16 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices } } } - - labelListPMG receivedData; + + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); - + label counter = 0; while( counter < receivedData.size() ) { const label bpI = globalToLocal[receivedData[counter++]]; const label nEdges = receivedData[counter++]; - + for(label i=0;i<nEdges;++i) { const label s = receivedData[counter++]; @@ -321,7 +326,7 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices dualEdgesForPoint[bpI].append(edge(s, e)); } } - + # ifdef DEBUGCheck for(label i=0;i<Pstream::nProcs();++i) { @@ -340,11 +345,11 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices << " dual edges " << pEdges << endl; } } - + returnReduce(1, sumOp<label>()); } # endif - + //- Finally, check the number of dual loops processor vertices for ( @@ -360,7 +365,7 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices forAll(pEdges[eI], i) bpEdges[pEdges[eI][i]].append(eI); } - + //- check if all points can be visited via edges counter = 0; Map<label> cellGroup(pEdges.size()); @@ -373,63 +378,63 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices { if( cellGroup.found(it->first) ) continue; - + cellGroup.insert(it->first, counter); frontCells.clear(); frontCells.append(it->first); - + while( frontCells.size() != 0 ) { const label cLabel = frontCells.removeLastElement(); - + const DynList<label>& attachedEdges = bpEdges[cLabel]; forAll(attachedEdges, aeI) { const label oCell = pEdges[attachedEdges[aeI]].otherVertex(cLabel); - + if( cellGroup.found(oCell) ) continue; - + frontCells.append(oCell); cellGroup.insert(oCell, counter); } } - + ++counter; } - + if( counter != 1 ) { ++nBadVertices; badVertices.insert(bPoints[bpIter->first]); - + if( !removeConnections ) continue; - + const label pointI = bPoints[bpIter->first]; const label nPoints = points.size(); forAllRow(pointCells, pointI, pcI) { const label cellI = pointCells(pointI, pcI); - + if( cellGroup[globalCellLabel[cellI]] == 0 ) continue; - + const cell& c = cells[cellI]; - + forAll(c, fI) { face& f = faces[c[fI]]; - + const label pos = f.which(pointI); - + if( pos > -1 ) f[pos] = nPoints + cellGroup[globalCellLabel[cellI]] - 1; } } - + for(label i=1;i<counter;++i) { const point p = points[pointI]; @@ -438,20 +443,20 @@ bool checkIrregularSurfaceConnections::checkAndFixCellGroupsAtBndVertices } } } - + reduce(nBadVertices, sumOp<label>()); - + Info << "Found " << nBadVertices << " problematic vertices" << endl; Info << "Finished checking cells connected to surface vertices" << endl; - + if( nBadVertices != 0 ) { clearMeshEngine(); mesh_.clearAddressingData(); - + return true; } - + return false; } @@ -462,42 +467,42 @@ bool checkIrregularSurfaceConnections::checkEdgeFaceConnections ) { Info << "Checking for non-manifold surface edges" << endl; - + const meshSurfaceEngine& mse = surfaceEngine(); const labelList& bp = mse.bp(); const edgeList& edges = mse.edges(); const VRWGraph& edgeFaces = mse.edgeFaces(); const VRWGraph& pointEdges = mse.boundaryPointEdges(); - + labelHashSet badEdges; - forAll(edgeFaces, edgeI) - if( edgeFaces.sizeOfRow(edgeI) > 2 ) - { + forAll(edgeFaces, edgeI) + if( edgeFaces.sizeOfRow(edgeI) > 2 ) + { badVertices.insert(edges[edgeI].start()); badVertices.insert(edges[edgeI].end()); - + badEdges.insert(edgeI); - } - + } + if( Pstream::parRun() ) { - //- boundary edges at processor boundaries + //- boundary edges at processor boundaries Map<label> numFacesAtEdge; const labelList& globalEdgeLabel = mse.globalBoundaryEdgeLabel(); const Map<label>& globalToLocalEdgeLabel = mse.globalToLocalBndEdgeAddressing(); const VRWGraph& edgesAtProcs = mse.beAtProcs(); - + const DynList<label>& neiProcs = mse.beNeiProcs(); - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAll(neiProcs, procI) exchangeData.insert ( - std::make_pair(neiProcs[procI], labelListPMG()) + std::make_pair(neiProcs[procI], labelLongList()) ); - std::map<label, labelListPMG>::iterator eIter; - + std::map<label, labelLongList>::iterator eIter; + forAll(edgeFaces, eI) { if( edgesAtProcs.sizeOfRow(eI) > 0 ) @@ -507,69 +512,69 @@ bool checkIrregularSurfaceConnections::checkEdgeFaceConnections globalEdgeLabel[eI], edgeFaces.sizeOfRow(eI) ); - + forAllRow(edgesAtProcs, eI, procI) { const label neiProc = edgesAtProcs(eI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - + eIter = exchangeData.find(neiProc); eIter->second.append(globalEdgeLabel[eI]); eIter->second.append(edgeFaces.sizeOfRow(eI)); } } } - + //- send data to other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); - + label counter(0); while( counter < receivedData.size() ) { const label geI = receivedData[counter++]; const label nFaces = receivedData[counter++]; - + numFacesAtEdge[geI] += nFaces; - + if( numFacesAtEdge[geI] > 2 ) { const label edgeI = globalToLocalEdgeLabel[geI]; badVertices.insert(edges[edgeI].start()); badVertices.insert(edges[edgeI].end()); - + badEdges.insert(edgeI); } } } - + const label nBadEdges = returnReduce(badEdges.size(), sumOp<label>()); Info << "Found " << nBadEdges << " non-manifold edges" << endl; Info << "Finished checking for non-manifold surface edges" << endl; - + if( nBadEdges != 0 && removeCells ) { //- remove all cells connected to the selected edge boolList removeCell(mesh_.cells().size(), false); - + const faceListPMG& faces = mesh_.faces(); const labelList& owner = mesh_.owner(); const labelList& neighbour = mesh_.neighbour(); - + forAll(faces, faceI) { const face& f = faces[faceI]; - + forAll(f, pI) { const edge e = f.faceEdge(pI); - + if( (bp[e[0]] != -1) && (bp[e[1]] != -1) ) { const label bpI = bp[e[0]]; - + forAllRow(pointEdges, bpI, peI) { const label edgeI = pointEdges(bpI, peI); @@ -584,13 +589,13 @@ bool checkIrregularSurfaceConnections::checkEdgeFaceConnections } } } - + polyMeshGenModifier(mesh_).removeCells(removeCell); clearMeshEngine(); - + return true; } - + return false; } @@ -601,58 +606,60 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices ) { Info << "Checking faces connections to surface vertices" << endl; - + labelHashSet invalidVertices(100); - + const meshSurfaceEngine& mse = surfaceEngine(); - + const labelList& bPoints = mse.boundaryPoints(); const VRWGraph& pointFaces = mse.pointFaces(); const VRWGraph& faceFaces = mse.faceFaces(); - + boolList parallelBndPoint(bPoints.size(), false); if( Pstream::parRun() ) { const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); - + forAllConstIter(Map<label>, globalToLocal, it) parallelBndPoint[it()] = true; } - + //- check number of face groups - DynList<label> front(100); + DynList<label> front; const label size = pointFaces.size(); + # ifdef USE_OMP # pragma omp parallel for private(front) schedule(dynamic) + # endif for(label bpI=0;bpI<size;++bpI) { if( parallelBndPoint[bpI] ) continue; - + Map<label> faceGroup(pointFaces.sizeOfRow(bpI)); label nGroup(0); - + forAllRow(pointFaces, bpI, pfI) { const label fI = pointFaces(bpI, pfI); - + if( faceGroup.found(fI) ) continue; - + front.clear(); front.append(fI); faceGroup.insert(fI, nGroup); - + while( front.size() != 0 ) { const label fLabel = front.removeLastElement(); - + forAllRow(faceFaces, fLabel, ffI) { const label neiFace = faceFaces(fLabel, ffI); - + if( faceGroup.found(neiFace) ) continue; - + if( pointFaces.contains(bpI, neiFace) ) { front.append(neiFace); @@ -660,45 +667,47 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices } } } - + ++nGroup; } - + if( nGroup != 1 ) { const label pointI = bPoints[bpI]; + # ifdef USE_OMP # pragma omp critical + # endif { badVertices.insert(pointI); invalidVertices.insert(pointI); } } } - + if( Pstream::parRun() ) { //- check connections at parallel vertices //- a connection of two faces over an edge can be represented //- as an edge. A list of edges at a bnd vertex must be connected //- into a single loop, otherwise the surface is ill-connected. - + const labelList& globalPointLabel = mse.globalBoundaryPointLabel(); const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); const VRWGraph& bpAtProcs = mse.bpAtProcs(); const labelList& bp = mse.bp(); - + const edgeList& edges = mse.edges(); const VRWGraph& pointEdges = mse.boundaryPointEdges(); const VRWGraph& edgeFaces = mse.edgeFaces(); - + const labelList& globalFaceLabel = mse.globalBoundaryFaceLabel(); - + const labelList& globalEdgeLabel = mse.globalBoundaryEdgeLabel(); const Map<label>& globalToLocalEdge = mse.globalToLocalBndEdgeAddressing(); const Map<label>& otherFaceAtProc = mse.otherEdgeFaceAtProc(); const DynList<label>& beNeiProcs = mse.beNeiProcs(); - + //- create map of dual edges for boundary points at processor boundaries std::map<label, DynList<edge> > dualEdgesForPoint; std::map<label, DynList<edge> >::iterator bpIter; @@ -706,13 +715,13 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices { if( !parallelBndPoint[bpI] ) continue; - - dualEdgesForPoint.insert(std::make_pair(bpI, DynList<edge>(10))); - + + dualEdgesForPoint.insert(std::make_pair(bpI, DynList<edge>())); + forAllRow(pointEdges, bpI, peI) { const label edgeI = pointEdges(bpI, peI); - + if( edgeFaces.sizeOfRow(edgeI) == 2 ) { //- add local edge @@ -721,21 +730,21 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices globalFaceLabel[edgeFaces(edgeI, 0)], globalFaceLabel[edgeFaces(edgeI, 1)] ); - + dualEdgesForPoint[bpI].append(e); } } } - - std::map<label, labelListPMG> exchangeData; + + std::map<label, labelLongList> exchangeData; //- collect connections over processor edges on the processor with //- the lowest label to avoid duplication of data forAll(beNeiProcs, i) - exchangeData.insert(std::make_pair(beNeiProcs[i], labelListPMG())); + exchangeData.insert(std::make_pair(beNeiProcs[i], labelLongList())); forAllConstIter(Map<label>, otherFaceAtProc, it) { const label beI = it.key(); - + if( it() < Pstream::myProcNo() ) { //- the data is sent as follows: @@ -745,26 +754,26 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices exchangeData[it()].append(globalFaceLabel[edgeFaces(beI, 0)]); } } - - labelListPMG receivedData; + + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); - + label counter(0); while( counter < receivedData.size() ) { const label beI = globalToLocalEdge[receivedData[counter++]]; const label fLabel = receivedData[counter++]; - + const edge& e = edges[beI]; forAll(e, i) { const label bpI = bp[e[i]]; - + const label fLocal = globalFaceLabel[edgeFaces(beI, 0)]; dualEdgesForPoint[bpI].append(edge(fLabel, fLocal)); } } - + //- exchange data with other processors //- this step supplies all processors with all necessary data exchangeData.clear(); @@ -776,18 +785,18 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices ) { const label bpI = bpIter->first; - + forAllRow(bpAtProcs, bpI, i) { const label neiProc = bpAtProcs(bpI, i); if( neiProc == Pstream::myProcNo() ) continue; - + //- edges are sent to other processors as follows //- 1. global point label //- 2. number of edges at node //- 3. labels of edges - labelListPMG& dts = exchangeData[neiProc]; + labelLongList& dts = exchangeData[neiProc]; const DynList<edge>& edges = bpIter->second; dts.append(globalPointLabel[bpI]); dts.append(edges.size()); @@ -798,10 +807,10 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices } } } - + receivedData.clear(); help::exchangeMap(exchangeData, receivedData); - + counter = 0; while( counter < receivedData.size() ) { @@ -814,7 +823,7 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices dualEdgesForPoint[bpI].append(edge(s, e)); } } - + # ifdef DEBUGCheck for(label i=0;i<Pstream::nProcs();++i) { @@ -833,11 +842,11 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices << " dual edges " << pEdges << endl; } } - + returnReduce(1, sumOp<label>()); } # endif - + //- Finally, check the number of dual loops processor vertices for ( @@ -847,14 +856,14 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices ) { const DynList<edge>& pEdges = bpIter->second; - + std::map<label, DynList<label> > bpEdges; forAll(pEdges, eI) { forAll(pEdges[eI], i) bpEdges[pEdges[eI][i]].append(eI); } - + //- check if all points can be visited via edges counter = 0; Map<label> cellGroup(pEdges.size()); @@ -867,32 +876,32 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices { if( cellGroup.found(it->first) ) continue; - + cellGroup.insert(it->first, counter); front.clear(); front.append(it->first); - + while( front.size() != 0 ) { const label cLabel = front.removeLastElement(); - + const DynList<label>& attachedEdges = bpEdges[cLabel]; forAll(attachedEdges, aeI) { const label oCell = pEdges[attachedEdges[aeI]].otherVertex(cLabel); - + if( cellGroup.found(oCell) ) continue; - + front.append(oCell); cellGroup.insert(oCell, counter); } } - + ++counter; } - + if( counter != 1 ) { invalidVertices.insert(bPoints[bpIter->first]); @@ -900,30 +909,30 @@ bool checkIrregularSurfaceConnections::checkFaceGroupsAtBndVertices } } } - + const label nBadVertices = returnReduce(invalidVertices.size(), sumOp<label>()); Info << "Found " << nBadVertices << " invalid connections" << endl; Info << "Finished checking faces connections to surface vertices" << endl; - + if( nBadVertices != 0 && removeCells ) { const VRWGraph& pointCells = mesh_.addressingData().pointCells(); - + boolList removeCell(mesh_.cells().size(), false); - + forAllConstIter(labelHashSet, invalidVertices, it) { forAllRow(pointCells, it.key(), pcI) removeCell[pointCells(it.key(), pcI)] = true; } - + polyMeshGenModifier(mesh_).removeCells(removeCell); clearMeshEngine(); - + return true; } - + return false; } diff --git a/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.C b/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.C index 08131251bc8e35474d1aa49288ab68661881f6d2..ec8224ff1db6932a4b21c6a76b51837e0a8f849d 100644 --- a/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.C +++ b/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,7 +30,9 @@ Description #include "helperFunctions.H" #include "meshSurfaceEngine.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGCheck @@ -47,33 +48,35 @@ void checkNonMappableCellConnections::findCellTypes() const faceListPMG& faces = mesh_.faces(); const cellListPMG& cells = mesh_.cells(); const labelList& owner = mesh_.owner(); - + cellType_.setSize(cells.size()); cellType_ = INTERNALCELL; - + //- find boundary cells - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); const label end = start + boundaries[patchI].patchSize(); - + for(label faceI=start;faceI<end;++faceI) cellType_[owner[faceI]] = BNDCELL; } - + //- find boundary cells with all vertices at the boundary meshSurfaceEngine mse(mesh_); const labelList& bp = mse.bp(); - + + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 1000) + # endif for(label cellI=cells.size()-1;cellI>=0;--cellI) { if( cellType_[cellI] & INTERNALCELL ) continue; - + const cell& c = cells[cellI]; - + //- mark boundary cells with all vertices at the boundary const labelList cellPoints = c.labels(faces); bool allBoundary(true); @@ -85,7 +88,7 @@ void checkNonMappableCellConnections::findCellTypes() break; } } - + if( allBoundary ) { cellType_[cellI] |= ALLBNDVERTEXCELL; @@ -94,7 +97,7 @@ void checkNonMappableCellConnections::findCellTypes() { continue; } - + //- check if the internal faces are connected into a single group //- over their edges DynList<label> internalFaces; @@ -109,28 +112,28 @@ void checkNonMappableCellConnections::findCellTypes() internalFaces.append(c[fI]); } } - + Map<label> faceGroup(internalFaces.size()); label nGroup(0); forAll(internalFaces, i) { if( faceGroup.found(internalFaces[i]) ) continue; - + DynList<label> front; front.append(internalFaces[i]); faceGroup.insert(internalFaces[i], nGroup); - + while( front.size() ) { const label fLabel = front.removeLastElement(); - + forAll(internalFaces, j) { const label nei = internalFaces[j]; if( faceGroup.found(nei) ) continue; - + if( help::shareAnEdge(faces[fLabel], faces[nei]) ) { front.append(nei); @@ -138,7 +141,7 @@ void checkNonMappableCellConnections::findCellTypes() } } } - + ++nGroup; } @@ -171,10 +174,10 @@ checkNonMappableCellConnections::~checkNonMappableCellConnections() void checkNonMappableCellConnections::findCells(labelHashSet& badCells) { badCells.clear(); - + //- classify cell types findCellTypes(); - + //- select ALLBNDVERTEXCELL and INTERNALFACEGROUP cells //- with at least one INTERNALCELL neighbour //- these cells do not need to stay in the mesh @@ -182,33 +185,33 @@ void checkNonMappableCellConnections::findCells(labelHashSet& badCells) const labelList& owner = mesh_.owner(); const labelList& neighbour = mesh_.neighbour(); const label nInternalFaces = mesh_.nInternalFaces(); - const PtrList<writeProcessorPatch>& procBoundaries = mesh_.procBoundaries(); - + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); + labelListList otherProcType; if( Pstream::parRun() ) { //- exchange cell types at processor boundaries otherProcType.setSize(procBoundaries.size()); - + //- send data to other processors forAll(procBoundaries, patchI) { label start = procBoundaries[patchI].patchStart(); labelList patchCellType(procBoundaries[patchI].patchSize()); - + forAll(patchCellType, faceI) patchCellType[faceI] = cellType_[owner[start++]]; - + OPstream toOtherProc ( Pstream::blocking, procBoundaries[patchI].neiProcNo(), patchCellType.byteSize() ); - + toOtherProc << patchCellType; } - + //- receive data from other processors forAll(procBoundaries, patchI) { @@ -217,40 +220,44 @@ void checkNonMappableCellConnections::findCells(labelHashSet& badCells) Pstream::blocking, procBoundaries[patchI].neiProcNo() ); - + labelList& otherTypes = otherProcType[patchI]; fromOtherProc >> otherTypes; } } - - # pragma omp parallel for schedule(dynamic) + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif for(label cellI=cellType_.size()-1;cellI>=0;--cellI) { if( cellType_[cellI] & INTERNALFACEGROUP ) { + # ifdef USE_OMP # pragma omp critical + # endif badCells.insert(cellI); } else if( cellType_[cellI] & (ALLBNDVERTEXCELL+INTERNALFACEGROUP) ) { //- mark cells which have only one internal neighbour const cell& c = cells[cellI]; - + bool hasInternalNeighbour(false); label nNeiCells(0); - + forAll(c, fI) { const label faceI = c[fI]; - + if( faceI < nInternalFaces ) { ++nNeiCells; - + label nei = neighbour[c[fI]]; if( nei == cellI ) nei = owner[c[fI]]; - + if( cellType_[nei] & INTERNALCELL ) { hasInternalNeighbour = true; @@ -260,10 +267,10 @@ void checkNonMappableCellConnections::findCells(labelHashSet& badCells) else if( mesh_.faceIsInProcPatch(faceI) != -1 ) { ++nNeiCells; - + const label patchI = mesh_.faceIsInProcPatch(faceI); const label j = faceI - procBoundaries[patchI].patchStart(); - + if( otherProcType[patchI][j] & INTERNALCELL ) { hasInternalNeighbour = true; @@ -271,10 +278,12 @@ void checkNonMappableCellConnections::findCells(labelHashSet& badCells) } } } - + if( hasInternalNeighbour || (nNeiCells == 1) ) { + # ifdef USE_OMP # pragma omp critical + # endif badCells.insert(cellI); } } @@ -284,31 +293,31 @@ void checkNonMappableCellConnections::findCells(labelHashSet& badCells) bool checkNonMappableCellConnections::removeCells() { labelHashSet badCells; - + label nRemoved; bool changed(false); - + do { findCells(badCells); - + nRemoved = badCells.size(); reduce(nRemoved, sumOp<label>()); - + Info << "Found " << nRemoved << " non-mappable cells" << endl; - + if( nRemoved != 0 ) { boolList removeCell(mesh_.cells().size(), false); forAllConstIter(labelHashSet, badCells, it) removeCell[it.key()] = true; - + polyMeshGenModifier(mesh_).removeCells(removeCell); - + changed = true; } } while( nRemoved ); - + return changed; } diff --git a/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.H b/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.H index 5f3f7b1ffffb004d0ca33745348466dc78df28a1..ae16cf926f02bf7b073517ccd149302d76e9ae76 100644 --- a/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.H +++ b/meshLibrary/utilities/smoothers/topology/checkNonMappableCellConnections/checkNonMappableCellConnections.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class checkNonMappableCellConnections @@ -56,7 +55,7 @@ class checkNonMappableCellConnections { // Private data //- Reference to polyMeshGen - polyMeshGen& mesh_; + polyMeshGen& mesh_; //- type of cell labelList cellType_; @@ -95,7 +94,7 @@ public: // Member Functions //- find problematic cells - void findCells(labelHashSet& badCells); + void findCells(labelHashSet& badCells); //- find and remove problematic cells bool removeCells(); diff --git a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.C b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.C index fc561088b6cd58d389d2381e31596c3f06664433..c3b1aa07f3fffc011b2c61f53932b40840f6f572 100644 --- a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.C +++ b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.H b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.H index b9cd9eb436d93caa0fbd8fced2490158cf5a12ec..8ba33c5f030e09a86a6ec34b478bf30ec317b875 100644 --- a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.H +++ b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleaner.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class topologicalCleaner @@ -52,25 +51,25 @@ namespace Foam class topologicalCleaner { // Private data - polyMeshGen& mesh_; - - bool changed_; - - boolList decomposeCell_; + polyMeshGen& mesh_; + + bool changed_; + + boolList decomposeCell_; // Private member functions - + //- check and fix incorrectly connected faces void checkNonConsecutiveBoundaryVertices(); - - //- check and fix non-mappable faces - void checkNonMappableFaces(); - - //- check and fix non-mappable cells - void checkNonMappableCells(); - - //- decompose marked cells - void decomposeCells(); + + //- check and fix non-mappable faces + void checkNonMappableFaces(); + + //- check and fix non-mappable cells + void checkNonMappableCells(); + + //- decompose marked cells + void decomposeCells(); //- Disallow default bitwise copy construct topologicalCleaner(const topologicalCleaner&); @@ -92,17 +91,17 @@ public: // Member Functions - //- clean topologically problematic cells - bool cleanTopology(); + //- clean topologically problematic cells + bool cleanTopology(); - //- check and fix vertices where two or more groups of cells meet - void checkInvalidConnectionsForVerticesCells + //- check and fix vertices where two or more groups of cells meet + void checkInvalidConnectionsForVerticesCells ( labelHashSet* irregularNodes = NULL ); - - //- check and fix vertices where two or more groups of faces meet - void checkInvalidConnectionsForVerticesFaces + + //- check and fix vertices where two or more groups of faces meet + void checkInvalidConnectionsForVerticesFaces ( labelHashSet* irregularNodes = NULL ); diff --git a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleanerInvalidVertices.C b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleanerInvalidVertices.C index 2bc4e72b9624e28109fb26e40b261ed616e06ca1..7e354438fe45a984378b4f443621b4b1057b766a 100644 --- a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleanerInvalidVertices.C +++ b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologicalCleanerInvalidVertices.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -89,12 +88,12 @@ void topologicalCleaner::checkInvalidConnectionsForVerticesCells { materialForCell[cI] = material; - DynList<label> frontCells(10); + DynList<label> frontCells; frontCells.append(cI); do { - DynList<label> newFrontCells(10); + DynList<label> newFrontCells; forAll(frontCells, fcI) { @@ -190,7 +189,9 @@ void topologicalCleaner::checkInvalidConnectionsForVerticesFaces boolList removeCell(mesh_.cells().size(), false); bool changed(false); + # ifdef USE_OMP # pragma omp parallel for schedule(static, 1) + # endif forAll(edgeFaces, edgeI) if( edgeFaces.sizeOfRow(edgeI) > 2 ) { @@ -209,8 +210,8 @@ void topologicalCleaner::checkInvalidConnectionsForVerticesFaces const VRWGraph& edgesAtProcs = mse.beAtProcs(); DynList<label> neiProcs; - std::map<label, labelListPMG> exchangeData; - std::map<label, labelListPMG>::iterator eIter; + std::map<label, labelLongList> exchangeData; + std::map<label, labelLongList>::iterator eIter; forAll(edgeFaces, eI) { @@ -235,10 +236,10 @@ void topologicalCleaner::checkInvalidConnectionsForVerticesFaces neiProcs.append(neiProc); exchangeData.insert ( - std::pair<label, labelListPMG> + std::pair<label, labelLongList> ( neiProc, - labelListPMG() + labelLongList() ) ); @@ -255,7 +256,7 @@ void topologicalCleaner::checkInvalidConnectionsForVerticesFaces forAll(neiProcs, procI) { eIter = exchangeData.find(neiProcs[procI]); - const labelListPMG& dataToSend = eIter->second; + const labelLongList& dataToSend = eIter->second; OPstream toOtherProc ( diff --git a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonConsecutiveBoundaryVertices.C b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonConsecutiveBoundaryVertices.C index 27b7c390e75bf805e27eccb5ae253f70246149bd..1d65007311ca80b533afdcfa68cd2fe273314ebc 100644 --- a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonConsecutiveBoundaryVertices.C +++ b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonConsecutiveBoundaryVertices.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -52,7 +51,7 @@ void topologicalCleaner::checkNonConsecutiveBoundaryVertices() boolList decomposeFace(faces.size(), false); bool changed(false); - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); @@ -79,7 +78,7 @@ void topologicalCleaner::checkNonConsecutiveBoundaryVertices() { const face& f = faces[c[fI]]; - DynList<label> shN(f.size()); + DynList<label> shN; forAll(bf, pI) forAll(f, pJ) diff --git a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonMappableCells.C b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonMappableCells.C index 536a87c8ff80d3c839939733e734d09cab12c62d..3b280547aee2e511018cd563d4dc1e9c0ce0535f 100644 --- a/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonMappableCells.C +++ b/meshLibrary/utilities/smoothers/topology/topologicalCleaner/topologyCleanerNonMappableCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,125 +41,125 @@ namespace Foam void topologicalCleaner::checkNonMappableCells() { - Info << "Checking for non-mappable cells" << endl; - //- decompose cells with more than one boundary face - const labelList& owner = mesh_.owner(); - - List<direction> nBoundaryFaces(mesh_.cells().size(), direction(0)); - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + Info << "Checking for non-mappable cells" << endl; + //- decompose cells with more than one boundary face + const labelList& owner = mesh_.owner(); + + List<direction> nBoundaryFaces(mesh_.cells().size(), direction(0)); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); const label end = start + boundaries[patchI].patchSize(); - + for(label faceI=start;faceI<end;++faceI) { ++nBoundaryFaces[owner[faceI]]; } } - - label nBadCells(0); - forAll(nBoundaryFaces, cI) - if( nBoundaryFaces[cI] > 1 ) - { - ++nBadCells; - decomposeCell_[cI] = true; - } - + + label nBadCells(0); + forAll(nBoundaryFaces, cI) + if( nBoundaryFaces[cI] > 1 ) + { + ++nBadCells; + decomposeCell_[cI] = true; + } + if( Pstream::parRun() ) reduce(nBadCells, sumOp<label>()); - - if( nBadCells != 0 ) - changed_ = true; - - Info << "Found " << nBadCells << " non-mappable cells" << endl; - Info << "Finished checking for non-mappable cells" << endl; + + if( nBadCells != 0 ) + changed_ = true; + + Info << "Found " << nBadCells << " non-mappable cells" << endl; + Info << "Finished checking for non-mappable cells" << endl; } void topologicalCleaner::checkNonMappableFaces() { - Info << "Checking for non-mappable faces" << endl; - - const faceListPMG& faces = mesh_.faces(); - const labelList& owner = mesh_.owner(); - const labelList& neighbour = mesh_.neighbour(); - - //- find boundary vertices - boolList boundaryVertex(mesh_.points().size(), false); - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - forAll(boundaries, patchI) + Info << "Checking for non-mappable faces" << endl; + + const faceListPMG& faces = mesh_.faces(); + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + + //- find boundary vertices + boolList boundaryVertex(mesh_.points().size(), false); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); const label end = start + boundaries[patchI].patchSize(); - - for(label faceI=start;faceI<end;++faceI) - { - const face& f = faces[faceI]; - forAll(f, pI) - boundaryVertex[f[pI]] = true; - } - } - - boolList decomposeFace(faces.size(), false); - - //- internal faces which have more than two vertices at the boundary - //- cannot always be mapped at the boundary and form a valid cell - //- The second case of interest are faces which have two vertices at the - //- boundary but are not connected over an edge - const label nIntFaces = mesh_.nInternalFaces(); - - //bool changed(false); - - label nBadFaces(0); - for(label faceI=0;faceI<nIntFaces;++faceI) - { - const face& f = faces[faceI]; - - DynList<label> bPos(f.size()); - forAll(f, pI) - if( boundaryVertex[f[pI]] ) - bPos.append(pI); - - if( - (bPos.size() > 2) || - ( - (bPos.size() == 2) && - ( - (bPos[1] != (bPos[0] + 1)) && - !((bPos[0] == 0) && (bPos[1] == (f.size() - 1))) - ) - ) - ) - { - ++nBadFaces; - decomposeFace[faceI] = true; - decomposeCell_[owner[faceI]] = true; - decomposeCell_[neighbour[faceI]] = true; - } - } - + + for(label faceI=start;faceI<end;++faceI) + { + const face& f = faces[faceI]; + forAll(f, pI) + boundaryVertex[f[pI]] = true; + } + } + + boolList decomposeFace(faces.size(), false); + + //- internal faces which have more than two vertices at the boundary + //- cannot always be mapped at the boundary and form a valid cell + //- The second case of interest are faces which have two vertices at the + //- boundary but are not connected over an edge + const label nIntFaces = mesh_.nInternalFaces(); + + //bool changed(false); + + label nBadFaces(0); + for(label faceI=0;faceI<nIntFaces;++faceI) + { + const face& f = faces[faceI]; + + DynList<label> bPos; + forAll(f, pI) + if( boundaryVertex[f[pI]] ) + bPos.append(pI); + + if( + (bPos.size() > 2) || + ( + (bPos.size() == 2) && + ( + (bPos[1] != (bPos[0] + 1)) && + !((bPos[0] == 0) && (bPos[1] == (f.size() - 1))) + ) + ) + ) + { + ++nBadFaces; + decomposeFace[faceI] = true; + decomposeCell_[owner[faceI]] = true; + decomposeCell_[neighbour[faceI]] = true; + } + } + if( Pstream::parRun() ) { //- check processor faces - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - + boolList decProcFace(procBoundaries[patchI].patchSize(), false); - + for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; - - DynList<label> bPos(f.size()); + + DynList<label> bPos; forAll(f, pI) if( boundaryVertex[f[pI]] ) bPos.append(pI); - + if( (bPos.size() > 2) || ( @@ -178,17 +177,17 @@ void topologicalCleaner::checkNonMappableFaces() decomposeCell_[owner[faceI]] = true; } } - + //- send information about decomposed faces to other processor OPstream toOtherProc - ( + ( Pstream::blocking, - procBoundaries[patchI].neiProcNo(), - decProcFace.byteSize() - ); + procBoundaries[patchI].neiProcNo(), + decProcFace.byteSize() + ); toOtherProc << decProcFace; } - + forAll(procBoundaries, patchI) { boolList decOtherProc; @@ -198,7 +197,7 @@ void topologicalCleaner::checkNonMappableFaces() procBoundaries[patchI].neiProcNo() ); fromOtherProc >> decOtherProc; - + const label start = procBoundaries[patchI].patchStart(); forAll(decOtherProc, faceI) if( decOtherProc[faceI] ) @@ -207,19 +206,19 @@ void topologicalCleaner::checkNonMappableFaces() decomposeCell_[owner[start+faceI]] = true; } } - + reduce(nBadFaces, sumOp<label>()); } - - Info << "Found " << nBadFaces << " non-mappable faces" << endl; - - if( nBadFaces != 0 ) - { - changed_ = true; - decomposeFaces(mesh_).decomposeMeshFaces(decomposeFace); - } - - Info << "Finished checking non-mappable faces" << endl; + + Info << "Found " << nBadFaces << " non-mappable faces" << endl; + + if( nBadFaces != 0 ) + { + changed_ = true; + decomposeFaces(mesh_).decomposeMeshFaces(decomposeFace); + } + + Info << "Finished checking non-mappable faces" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.C b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.C index cbe61977f1adcbb196b1f67b7d2cd7b9b862bb91..9edc8912d2e126f1c4dbd0fe8a83e38d60524da4 100644 --- a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.C +++ b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,114 +34,110 @@ Description namespace Foam { - + // * * * * * * * * * * * * * Private member functions * * * * * * * * * * * // - + void boundaryFacesGenerator::createBoundaryFaces() { - //- set sizes of boundary cells - polyMeshGenModifier meshModifier(mesh_); - cellListPMG& cells = meshModifier.cellsAccess(); - forAll(boundaryCell_, cellI) - if( boundaryCell_[cellI] ) - cells[cellI].setSize(nFacesInCell_[cellI]); - - //- create boundary faces - forAll(boundaryCell_, cellI) - if( boundaryCell_[cellI] ) - createBoundaryFacesForCell(cellI); + //- set sizes of boundary cells + polyMeshGenModifier meshModifier(mesh_); + cellListPMG& cells = meshModifier.cellsAccess(); + forAll(boundaryCell_, cellI) + if( boundaryCell_[cellI] ) + cells[cellI].setSize(nFacesInCell_[cellI]); + + //- create boundary faces + forAll(boundaryCell_, cellI) + if( boundaryCell_[cellI] ) + createBoundaryFacesForCell(cellI); } void boundaryFacesGenerator::storeBoundaryFaces() { - wordList patchNames; - if( hasFacesInDefaultPatch_ ) - { - patchNames.setSize(surface_.patches().size() + 1); - patchNames[surface_.patches().size()] = "defaultFaces"; - } - else - { - patchNames.setSize(surface_.patches().size()); - } - - forAll(surface_.patches(), patchI) - patchNames[patchI] = surface_.patches()[patchI].name(); - - polyMeshGenModifier(mesh_).replaceBoundary - ( - patchNames, - boundaryFaces_, - boundaryOwners_, - boundaryPatches_ - ); - polyMeshGenModifier(mesh_).removeUnusedVertices(); + wordList patchNames; + if( hasFacesInDefaultPatch_ ) + { + patchNames.setSize(surface_.patches().size() + 1); + patchNames[surface_.patches().size()] = "defaultFaces"; + } + else + { + patchNames.setSize(surface_.patches().size()); + } + + forAll(surface_.patches(), patchI) + patchNames[patchI] = surface_.patches()[patchI].name(); + + polyMeshGenModifier(mesh_).replaceBoundary + ( + patchNames, + boundaryFaces_, + boundaryOwners_, + boundaryPatches_ + ); + polyMeshGenModifier(mesh_).removeUnusedVertices(); } void boundaryFacesGenerator::createSurfaceCornersAndPatches() { - const labelListList& pointFaces = surface_.pointFaces(); - forAll(pointFaces, pI) - { - const labelList& pFaces = pointFaces[pI]; - - DynList<label> patches(5); - forAll(pFaces, pfI) - patches.appendIfNotIn(surface_[pFaces[pfI]].region()); - - //- corners are points in at least three regions - if( patches.size() > 2 ) - { - surfaceCorners_.append(pI); - cornersPatches_.append(patches); - } - } - - Info << "The surface has " << surfaceCorners_.size() << " corners" << endl; + const VRWGraph& pointFaces = surface_.pointFacets(); + forAll(pointFaces, pI) + { + DynList<label> patches; + forAllRow(pointFaces, pI, pfI) + patches.appendIfNotIn(surface_[pointFaces(pI, pfI)].region()); + + //- corners are points in at least three regions + if( patches.size() > 2 ) + { + surfaceCorners_.append(pI); + cornersPatches_.append(patches); + } + } + + Info << "The surface has " << surfaceCorners_.size() << " corners" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + boundaryFacesGenerator::boundaryFacesGenerator ( - polyMeshGen& mesh, - List<direction>& nFacesInCell, - label& nPoints, - const label nIntFaces, - const boolList& boundaryCell, - VRWGraph& pointPatches, - const triSurface& surface + polyMeshGen& mesh, + List<direction>& nFacesInCell, + label& nPoints, + const label nIntFaces, + const boolList& boundaryCell, + VRWGraph& pointPatches, + const triSurf& surface ) : - surface_(surface), - mesh_(mesh), - nFacesInCell_(nFacesInCell), - boundaryCell_(boundaryCell), - pointRegions_(pointPatches), - nPoints_(nPoints), - nIntFaces_(nIntFaces), - boundaryFaces_(), - boundaryOwners_(), - boundaryPatches_(), - hasFacesInDefaultPatch_(false), - defaultPatchID_(surface.patches().size()), - surfaceCorners_(surface.patches().size()), - cornersPatches_(surface.patches().size()) + surface_(surface), + mesh_(mesh), + nFacesInCell_(nFacesInCell), + boundaryCell_(boundaryCell), + pointRegions_(pointPatches), + nPoints_(nPoints), + nIntFaces_(nIntFaces), + boundaryFaces_(), + boundaryOwners_(), + boundaryPatches_(), + hasFacesInDefaultPatch_(false), + defaultPatchID_(surface.patches().size()), + surfaceCorners_(surface.patches().size()), + cornersPatches_(surface.patches().size()) { - createSurfaceCornersAndPatches(); - + createSurfaceCornersAndPatches(); + createBoundaryFaces(); - - storeBoundaryFaces(); + + storeBoundaryFaces(); boundaryOutwardOrientation boo(mesh); } // Destructor boundaryFacesGenerator::~boundaryFacesGenerator() -{ -} - +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.H b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.H index 1012ed857160af3d618a6a9cd454e084082155eb..3297ffec001993fe59840c9bc97566c8bf00e0c5 100644 --- a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.H +++ b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGenerator.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class boundaryFacesGenerator @@ -37,9 +36,9 @@ SourceFiles #define boundaryFacesGenerator_H #include "polyMeshGenModifier.H" -#include "triSurface.H" +#include "triSurf.H" #include "DynList.H" -#include "labelListPMG.H" +#include "labelLongList.H" namespace Foam { @@ -51,69 +50,69 @@ namespace Foam class boundaryFacesGenerator { // private data - //- triangulated surface - const triSurface& surface_; + //- triangulated surface + const triSurf& surface_; //- mesh data - polyMeshGen& mesh_; - - //- helpers + polyMeshGen& mesh_; + + //- helpers List<direction>& nFacesInCell_; const boolList& boundaryCell_; - VRWGraph& pointRegions_; - - label& nPoints_; + VRWGraph& pointRegions_; + + label& nPoints_; const label nIntFaces_; - //- boundary faces - VRWGraph boundaryFaces_; - labelListPMG boundaryOwners_; - labelListPMG boundaryPatches_; - bool hasFacesInDefaultPatch_; - label defaultPatchID_; - - //- surface corners - DynList<label> surfaceCorners_; - DynList< DynList<label> > cornersPatches_; + //- boundary faces + VRWGraph boundaryFaces_; + labelLongList boundaryOwners_; + labelLongList boundaryPatches_; + bool hasFacesInDefaultPatch_; + label defaultPatchID_; + + //- surface corners + DynList<label> surfaceCorners_; + DynList< DynList<label> > cornersPatches_; // private member functions - //- find patches for the given vertex + //- find patches for the given vertex labelList patchesForPoint(const label) const; - //- find patches for a given cell - void determineCellPatches(const label, DynList<label>&); - - //- find boundary chains for the given cell - void createBoundaryChainsForCell(const label, labelListList&); - - void createFacesForChain - ( - const labelList& chainVertices, - const DynList<label>& patches, - List<DynList<face> >& facesForChain - ); - void createFacesForChainWithCorner - ( - const label cornerLabel, - const labelList& bChain, - const DynList<label>& patches, - List<DynList<face> >& facesForChain - ); - void createFacesForChainWithoutCorners - ( - const labelList& bChain, - const DynList<label>& patches, - List<DynList<face> >& facesForChain - ); - void createBoundaryFacesForCell(const label); + //- find patches for a given cell + void determineCellPatches(const label, DynList<label>&); + + //- find boundary chains for the given cell + void createBoundaryChainsForCell(const label, labelListList&); + + void createFacesForChain + ( + const labelList& chainVertices, + const DynList<label>& patches, + List<DynList<face> >& facesForChain + ); + void createFacesForChainWithCorner + ( + const label cornerLabel, + const labelList& bChain, + const DynList<label>& patches, + List<DynList<face> >& facesForChain + ); + void createFacesForChainWithoutCorners + ( + const labelList& bChain, + const DynList<label>& patches, + List<DynList<face> >& facesForChain + ); + void createBoundaryFacesForCell(const label); void createBoundaryFaces(); - - //- store boundary faces into the mesh - void storeBoundaryFaces(); - - //- find surface corners - void createSurfaceCornersAndPatches(); + + //- store boundary faces into the mesh + void storeBoundaryFaces(); + + //- find surface corners + void createSurfaceCornersAndPatches(); //- disallows bitwise construct void operator=(const boundaryFacesGenerator&); @@ -128,13 +127,13 @@ public: //- construct components boundaryFacesGenerator ( - polyMeshGen& mesh, - List<direction>& nFacesInCell, - label& nPoints, - const label nIntFaces, - const boolList& boundaryCell, - VRWGraph& pointPatches, - const triSurface& surface + polyMeshGen& mesh, + List<direction>& nFacesInCell, + label& nPoints, + const label nIntFaces, + const boolList& boundaryCell, + VRWGraph& pointPatches, + const triSurf& surface ); //- Destructor diff --git a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorCreateBoundaryFaces.C b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorCreateBoundaryFaces.C index 3f1919958bfdd7cf6b063868da917da1a24d5fb2..7aa518b7541fc5c0f6e3e201a79a5ea8170f2df0 100644 --- a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorCreateBoundaryFaces.C +++ b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorCreateBoundaryFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,201 +39,201 @@ namespace Foam labelList boundaryFacesGenerator::patchesForPoint(const label vI) const { - labelList pcs(pointRegions_.sizeOfRow(vI)); - - forAll(pcs, pI) - pcs[pI] = pointRegions_(vI, pI); - - return pcs; + labelList pcs(pointRegions_.sizeOfRow(vI)); + + forAll(pcs, pI) + pcs[pI] = pointRegions_(vI, pI); + + return pcs; } void boundaryFacesGenerator::determineCellPatches ( - const label cellI, - DynList<label>& patches + const label cellI, + DynList<label>& patches ) { - const cellListPMG& polyCells_ = mesh_.cells(); - const faceListPMG& polyFaces_ = mesh_.faces(); - const cell& c = polyCells_[cellI]; - - # ifdef DEBUGCutter - Info << "Cell faces are " << c << endl; - forAll(c, fI) - Info << "Face " << c[fI] << " is " - << polyFaces_[c[fI]] << endl; - # endif - - const labelList cellPoints = c.labels(polyFaces_); - - # ifdef DEBUGCutter - Info << "Cell points are " << cellPoints << endl; - # endif - - //- find which boundary regions intersect the polyhedron - //- this can be determined by monitoring patch labels - //- of cell points - patches.clear(); - - forAll(cellPoints, cpI) - { - const labelList pp = patchesForPoint(cellPoints[cpI]); - forAll(pp, ppI) - patches.appendIfNotIn(pp[ppI]); - } - - # ifdef DEBUGCutter - Info << "Patches for cell " << cellI << " are " << patches << endl; - # endif + const cellListPMG& polyCells_ = mesh_.cells(); + const faceListPMG& polyFaces_ = mesh_.faces(); + const cell& c = polyCells_[cellI]; + + # ifdef DEBUGCutter + Info << "Cell faces are " << c << endl; + forAll(c, fI) + Info << "Face " << c[fI] << " is " + << polyFaces_[c[fI]] << endl; + # endif + + const labelList cellPoints = c.labels(polyFaces_); + + # ifdef DEBUGCutter + Info << "Cell points are " << cellPoints << endl; + # endif + + //- find which boundary regions intersect the polyhedron + //- this can be determined by monitoring patch labels + //- of cell points + patches.clear(); + + forAll(cellPoints, cpI) + { + const labelList pp = patchesForPoint(cellPoints[cpI]); + forAll(pp, ppI) + patches.appendIfNotIn(pp[ppI]); + } + + # ifdef DEBUGCutter + Info << "Patches for cell " << cellI << " are " << patches << endl; + # endif } void boundaryFacesGenerator::createBoundaryChainsForCell ( - const label cellI, - labelListList& boundaryChains + const label cellI, + labelListList& boundaryChains ) { - const faceListPMG& polyFaces_ = mesh_.faces(); - const cell& c = mesh_.cells()[cellI]; - //- find edges which appear once - //- these edges are on the boundary - const edgeList cellEdges = c.edges(polyFaces_); - - labelList nAppearances(cellEdges.size(), 0); - forAll(c, fI) - { - const face& f = polyFaces_[c[fI]]; - - const edgeList fe = f.edges(); - - forAll(fe, eI) - forAll(cellEdges, i) - if( fe[eI] == cellEdges[i] ) - { - ++nAppearances[i]; - break; - } - } - - //- create a list of boundary edges - DynList<edge> boundaryEdges(10); - - forAll(nAppearances, aI) - if( nAppearances[aI] == 1 ) - { - boundaryEdges.append(cellEdges[aI]); - } - else if( nAppearances[aI] > 2 ) - { - const cellListPMG& polyCells_ = mesh_.cells(); - forAll(polyCells_[cellI], fI) - Info << "Face " << polyCells_[cellI][fI] << " is " - << polyFaces_[polyCells_[cellI][fI]] << endl; - FatalErrorIn - ( - "void createBoundaryFaces()" - ) << "Cell " << cellI << " is not topologically closed!" - << abort(FatalError); - } - - //- sort edges into chains - boundaryChains = sortEdgesIntoChains(boundaryEdges).sortedChains(); - - # ifdef DEBUGCutter - Info << "boundaryChains " << boundaryChains << endl; - # endif + const faceListPMG& polyFaces_ = mesh_.faces(); + const cell& c = mesh_.cells()[cellI]; + //- find edges which appear once + //- these edges are on the boundary + const edgeList cellEdges = c.edges(polyFaces_); + + labelList nAppearances(cellEdges.size(), 0); + forAll(c, fI) + { + const face& f = polyFaces_[c[fI]]; + + const edgeList fe = f.edges(); + + forAll(fe, eI) + forAll(cellEdges, i) + if( fe[eI] == cellEdges[i] ) + { + ++nAppearances[i]; + break; + } + } + + //- create a list of boundary edges + DynList<edge> boundaryEdges; + + forAll(nAppearances, aI) + if( nAppearances[aI] == 1 ) + { + boundaryEdges.append(cellEdges[aI]); + } + else if( nAppearances[aI] > 2 ) + { + const cellListPMG& polyCells_ = mesh_.cells(); + forAll(polyCells_[cellI], fI) + Info << "Face " << polyCells_[cellI][fI] << " is " + << polyFaces_[polyCells_[cellI][fI]] << endl; + FatalErrorIn + ( + "void createBoundaryFaces()" + ) << "Cell " << cellI << " is not topologically closed!" + << abort(FatalError); + } + + //- sort edges into chains + boundaryChains = sortEdgesIntoChains(boundaryEdges).sortedChains(); + + # ifdef DEBUGCutter + Info << "boundaryChains " << boundaryChains << endl; + # endif } void boundaryFacesGenerator::createBoundaryFacesForCell(const label cellI) { - //- check if there are any faces in the current cell - if( nFacesInCell_[cellI] == 0 ) - FatalErrorIn - ( - "void boundaryFacesGenerator::createBoundaryFacesForCell" - "(const label)" - ) << "Cell " << cellI << " has no faces!!" - << nl << "This generally means that there is not enough cells " - << "in that region. It can be remedied by refining " - << "the mesh there." << exit(FatalError); - - //- determine cell patches - DynList<label> patches(5); - determineCellPatches(cellI, patches); - - # ifdef DEBUGCutter - Info << "Cell patches " << patches << endl; - # endif - - //- create boundary chains for cell - labelListList boundaryChains; - createBoundaryChainsForCell(cellI, boundaryChains); - - //- create storage for faces created from the boundary chain - //- this list contains faces created from the chain - //- with respect to the boundary patch they belong to - //- first list : faces for each chain - //- second list: faces with respect to the patch - //- third list : there can be more than one face per patch - List< List< DynList<face> > > facePoints - ( - boundaryChains.size() - ); - - forAll(facePoints, chI) - { - facePoints[chI].setSize(patches.size()+1); - } - - //- create faces for the given chains - forAll(boundaryChains, bcI) - createFacesForChain - ( - boundaryChains[bcI], - patches, - facePoints[bcI] - ); - - # ifdef DEBUGCutter - Info << "facePoints " << facePoints << endl; - # endif - - //- store faces into the list - forAll(facePoints, chI) - { - const List< DynList<face> >& chfcs = facePoints[chI]; - - forAll(chfcs, patchI) - { - const DynList<face>& patchFaces = chfcs[patchI]; - - if( patchI < patches.size() ) - { - forAll(patchFaces, pfI) - { - boundaryFaces_.appendList(patchFaces[pfI]); - boundaryOwners_.append(cellI); - boundaryPatches_.append(patches[patchI]); - } - } - else - { - # ifdef DEBUGCutter - Info << "Faces " << patchFaces - << " are in default patch" << endl; - # endif - //- faces in default patch - forAll(patchFaces, pfI) - { - hasFacesInDefaultPatch_ = true; - boundaryFaces_.appendList(patchFaces[pfI]); - boundaryOwners_.append(cellI); - boundaryPatches_.append(defaultPatchID_); - } - } - } - } + //- check if there are any faces in the current cell + if( nFacesInCell_[cellI] == 0 ) + FatalErrorIn + ( + "void boundaryFacesGenerator::createBoundaryFacesForCell" + "(const label)" + ) << "Cell " << cellI << " has no faces!!" + << nl << "This generally means that there is not enough cells " + << "in that region. It can be remedied by refining " + << "the mesh there." << exit(FatalError); + + //- determine cell patches + DynList<label> patches; + determineCellPatches(cellI, patches); + + # ifdef DEBUGCutter + Info << "Cell patches " << patches << endl; + # endif + + //- create boundary chains for cell + labelListList boundaryChains; + createBoundaryChainsForCell(cellI, boundaryChains); + + //- create storage for faces created from the boundary chain + //- this list contains faces created from the chain + //- with respect to the boundary patch they belong to + //- first list : faces for each chain + //- second list: faces with respect to the patch + //- third list : there can be more than one face per patch + List< List< DynList<face> > > facePoints + ( + boundaryChains.size() + ); + + forAll(facePoints, chI) + { + facePoints[chI].setSize(patches.size()+1); + } + + //- create faces for the given chains + forAll(boundaryChains, bcI) + createFacesForChain + ( + boundaryChains[bcI], + patches, + facePoints[bcI] + ); + + # ifdef DEBUGCutter + Info << "facePoints " << facePoints << endl; + # endif + + //- store faces into the list + forAll(facePoints, chI) + { + const List< DynList<face> >& chfcs = facePoints[chI]; + + forAll(chfcs, patchI) + { + const DynList<face>& patchFaces = chfcs[patchI]; + + if( patchI < patches.size() ) + { + forAll(patchFaces, pfI) + { + boundaryFaces_.appendList(patchFaces[pfI]); + boundaryOwners_.append(cellI); + boundaryPatches_.append(patches[patchI]); + } + } + else + { + # ifdef DEBUGCutter + Info << "Faces " << patchFaces + << " are in default patch" << endl; + # endif + //- faces in default patch + forAll(patchFaces, pfI) + { + hasFacesInDefaultPatch_ = true; + boundaryFaces_.appendList(patchFaces[pfI]); + boundaryOwners_.append(cellI); + boundaryPatches_.append(defaultPatchID_); + } + } + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorFacesForChain.C b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorFacesForChain.C index bcaaacb64b8621b168d11ab09e585da7ca8c29aa..1fe4dc092f93f05716345e70c651aa3af74ad657 100644 --- a/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorFacesForChain.C +++ b/meshLibrary/utilities/surfaceTools/boundaryFacesGenerator/boundaryFacesGeneratorFacesForChain.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,157 +34,157 @@ Description namespace Foam { - + // * * * * * * * * * * * * * Private member functions * * * * * * * * * * * // void boundaryFacesGenerator::createFacesForChain ( - const labelList& chainVertices, - const DynList<label>& patches, - List< DynList<face> >& facesForChain + const labelList& chainVertices, + const DynList<label>& patches, + List< DynList<face> >& facesForChain ) { - createFacesFromChain cffc(chainVertices, pointRegions_); - - //- create faces which do not need an additional corner first - cffc.createFacesWithoutACorner(); - - if( cffc.unresolvedPoints().size() == 0 ) - { - //- store created faces and return - const DynList<face>& createdFaces = cffc.createdFaces(); - const DynList<label>& faceRegion = cffc.faceRegion(); - - forAll(createdFaces, fI) - { - const label pos = patches.containsAtPosition(faceRegion[fI]); - const face& f = createdFaces[fI]; - # ifdef DEBUGCutter - Info << "Storing face " << f << " at position " << pos << endl; - # endif - facesForChain[pos].append(f); - } - - return; - } - else if( cffc.unresolvedPoints().size() < 3 ) - { - FatalErrorIn - ( - "void boundaryFacesGenerator::createFacesForChain" - "(" - "const labelList& chainVertices," - "const DynList<label>& patches," - "List< DynList<face> >& facesForChain" - ")" - ) << "I am not sure if this should ever happen!" << exit(FatalError); - } - - const labelList& unresolvedPoints = cffc.unresolvedPoints(); - DynList<label> chainPatches(5); - forAll(unresolvedPoints, upI) - { - const labelList pp = patchesForPoint(unresolvedPoints[upI]); - - forAll(pp, ppI) - chainPatches.appendIfNotIn(pp[ppI]); - } - - if( chainPatches.size() < 3 ) - { - //- expected three or more patches - //- this will be resolved by storing the face into a default patch - facesForChain[patches.size()].append(face(chainVertices)); - } - else - { - //- find the cornerLabel - DynList<label> cornersCandidates; - - forAll(cornersPatches_, cornerI) - { - const DynList<label>& cPatches = cornersPatches_[cornerI]; - - bool allFound(true); - forAll(cPatches, cpI) - { - bool found = chainPatches.contains(cPatches[cpI]); - - if( !found ) - { - allFound = false; - break; - } - } - - if( allFound ) - cornersCandidates.append(surfaceCorners_[cornerI]); - } - - if( cornersCandidates.size() != 0 ) - { - label cornerLabel(-1); - - if( cornersCandidates.size() == 1 ) - { - cornerLabel = cornersCandidates[0]; - } - else - { - //- find nearest corner - point c(vector::zero); - forAll(chainVertices, cvI) - c += mesh_.points()[chainVertices[cvI]]; - c /= chainVertices.size(); - - scalar dist(VGREAT); - forAll(cornersCandidates, cornerI) - if( - mag - ( - surface_.localPoints()[cornersCandidates[cornerI]] - - c - ) < dist - ) - { - dist = - mag - ( - surface_.localPoints()[cornersCandidates[cornerI]] - - c - ); - cornerLabel = cornersCandidates[cornerI]; - } - } - - //- create faces including the corner - //- create faces with a corner vertex - cffc.createFacesWithACorner(nPoints_); - - //- add new mesh vertex - polyMeshGenModifier modifier(mesh_); - modifier.pointsAccess().newElmt(nPoints_++) = - surface_.localPoints()[cornerLabel]; - - const DynList<face>& createdFaces = cffc.createdFaces(); - const DynList<label>& faceRegion = cffc.faceRegion(); - forAll(createdFaces, fI) - { - const label pos = patches.containsAtPosition(faceRegion[fI]); - const face& f = createdFaces[fI]; - # ifdef DEBUGCutter - Info << "Storing face " << f << " at position " << pos << endl; - # endif - facesForChain[pos].append(f); - } - } - else - { - //- this is a tricky combination - //- store the face into the default patch - facesForChain[patches.size()].append(face(chainVertices)); - } - } + createFacesFromChain cffc(chainVertices, pointRegions_); + + //- create faces which do not need an additional corner first + cffc.createFacesWithoutACorner(); + + if( cffc.unresolvedPoints().size() == 0 ) + { + //- store created faces and return + const DynList<face>& createdFaces = cffc.createdFaces(); + const DynList<label>& faceRegion = cffc.faceRegion(); + + forAll(createdFaces, fI) + { + const label pos = patches.containsAtPosition(faceRegion[fI]); + const face& f = createdFaces[fI]; + # ifdef DEBUGCutter + Info << "Storing face " << f << " at position " << pos << endl; + # endif + facesForChain[pos].append(f); + } + + return; + } + else if( cffc.unresolvedPoints().size() < 3 ) + { + FatalErrorIn + ( + "void boundaryFacesGenerator::createFacesForChain" + "(" + "const labelList& chainVertices," + "const DynList<label>& patches," + "List< DynList<face> >& facesForChain" + ")" + ) << "I am not sure if this should ever happen!" << exit(FatalError); + } + + const labelList& unresolvedPoints = cffc.unresolvedPoints(); + DynList<label> chainPatches; + forAll(unresolvedPoints, upI) + { + const labelList pp = patchesForPoint(unresolvedPoints[upI]); + + forAll(pp, ppI) + chainPatches.appendIfNotIn(pp[ppI]); + } + + if( chainPatches.size() < 3 ) + { + //- expected three or more patches + //- this will be resolved by storing the face into a default patch + facesForChain[patches.size()].append(face(chainVertices)); + } + else + { + //- find the cornerLabel + DynList<label> cornersCandidates; + + forAll(cornersPatches_, cornerI) + { + const DynList<label>& cPatches = cornersPatches_[cornerI]; + + bool allFound(true); + forAll(cPatches, cpI) + { + bool found = chainPatches.contains(cPatches[cpI]); + + if( !found ) + { + allFound = false; + break; + } + } + + if( allFound ) + cornersCandidates.append(surfaceCorners_[cornerI]); + } + + if( cornersCandidates.size() != 0 ) + { + label cornerLabel(-1); + + if( cornersCandidates.size() == 1 ) + { + cornerLabel = cornersCandidates[0]; + } + else + { + //- find nearest corner + point c(vector::zero); + forAll(chainVertices, cvI) + c += mesh_.points()[chainVertices[cvI]]; + c /= chainVertices.size(); + + scalar dist(VGREAT); + forAll(cornersCandidates, cornerI) + if( + mag + ( + surface_.points()[cornersCandidates[cornerI]] - + c + ) < dist + ) + { + dist = + mag + ( + surface_.points()[cornersCandidates[cornerI]] - + c + ); + cornerLabel = cornersCandidates[cornerI]; + } + } + + //- create faces including the corner + //- create faces with a corner vertex + cffc.createFacesWithACorner(nPoints_); + + //- add new mesh vertex + polyMeshGenModifier modifier(mesh_); + modifier.pointsAccess().newElmt(nPoints_++) = + surface_.points()[cornerLabel]; + + const DynList<face>& createdFaces = cffc.createdFaces(); + const DynList<label>& faceRegion = cffc.faceRegion(); + forAll(createdFaces, fI) + { + const label pos = patches.containsAtPosition(faceRegion[fI]); + const face& f = createdFaces[fI]; + # ifdef DEBUGCutter + Info << "Storing face " << f << " at position " << pos << endl; + # endif + facesForChain[pos].append(f); + } + } + else + { + //- this is a tricky combination + //- store the face into the default patch + facesForChain[patches.size()].append(face(chainVertices)); + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.C b/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.C index 62fdd5420e4f4a182d40f43a8153eca4b7393f21..4636d41214a4bd6ec9cb4f8c6cc25f3cbc693f35 100644 --- a/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.C +++ b/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,25 +40,25 @@ namespace Foam void boundaryOutwardOrientation::checkBoundaryOrientation() { - polyMeshGenModifier meshModifier_(mesh_); - faceListPMG& faces_ = meshModifier_.facesAccess(); - const cellListPMG& cells_ = mesh_.cells(); - const labelList& owner_ = mesh_.owner(); - const labelList& neighbour_ = mesh_.neighbour(); - - if( mesh_.boundaries().size() == 0 ) - { - WarningIn - ( - "void boundaryOutwardOrientation::checkBoundaryOrientation()" - ) << "Boundary data is not yet calculated!! Cannot proceed!" - << endl; - - return; - } - - const label nIntFaces_ = mesh_.nInternalFaces(); - + polyMeshGenModifier meshModifier_(mesh_); + faceListPMG& faces_ = meshModifier_.facesAccess(); + const cellListPMG& cells_ = mesh_.cells(); + const labelList& owner_ = mesh_.owner(); + const labelList& neighbour_ = mesh_.neighbour(); + + if( mesh_.boundaries().size() == 0 ) + { + WarningIn + ( + "void boundaryOutwardOrientation::checkBoundaryOrientation()" + ) << "Boundary data is not yet calculated!! Cannot proceed!" + << endl; + + return; + } + + const label nIntFaces_ = mesh_.nInternalFaces(); + for(register label faceI=nIntFaces_;faceI<faces_.size();faceI++) { const cell& c = cells_[owner_[faceI]]; @@ -92,11 +91,11 @@ void boundaryOutwardOrientation::checkBoundaryOrientation() if( e.start() != -1 ) { edge eOther(-1, -1); - const edgeList newBfEdges = newBf.edges(); - forAll(newBfEdges, eJ) - if( newBfEdges[eJ] == e ) - eOther = newBfEdges[eJ]; - + const edgeList newBfEdges = newBf.edges(); + forAll(newBfEdges, eJ) + if( newBfEdges[eJ] == e ) + eOther = newBfEdges[eJ]; + if( ( (owner_[c[fI]] == owner_[faceI] ) && @@ -124,12 +123,12 @@ void boundaryOutwardOrientation::checkBoundaryOrientation() boundaryOutwardOrientation::boundaryOutwardOrientation ( - polyMeshGen& mesh + polyMeshGen& mesh ) : - mesh_(mesh) + mesh_(mesh) { - checkBoundaryOrientation(); + checkBoundaryOrientation(); } boundaryOutwardOrientation::~boundaryOutwardOrientation() diff --git a/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.H b/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.H index 6eef88760163d3c28ea863b1fc9acdcd46566a37..2a651225acd94aa9f4f8de2d4d28d3ef5ef4de7d 100644 --- a/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.H +++ b/meshLibrary/utilities/surfaceTools/boundaryOutwardOrientation/boundaryOutwardOrientation.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class boundaryOutwardOrientation @@ -50,11 +49,11 @@ namespace Foam class boundaryOutwardOrientation { // Private data - //- refenrence to the mesh - polyMeshGen& mesh_; - - //- orientate boundary - void checkBoundaryOrientation(); + //- refenrence to the mesh + polyMeshGen& mesh_; + + //- orientate boundary + void checkBoundaryOrientation(); //- Disallow default bitwise copy construct boundaryOutwardOrientation(const boundaryOutwardOrientation&); diff --git a/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.C b/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.C index 4f5c133458fcdf901cf7e07d15747e47338ff7b1..f84bfa838de6219021cc9888b83cc4c105a94109 100644 --- a/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.C +++ b/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,14 +36,14 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // const meshSurfaceEngine& correctEdgesBetweenPatches::meshSurface() const { if( !msePtr_ ) msePtr_ = new meshSurfaceEngine(mesh_); - + return *msePtr_; } @@ -53,18 +52,18 @@ void correctEdgesBetweenPatches::clearMeshSurface() { deleteDemandDrivenData(msePtr_); } - + void correctEdgesBetweenPatches::replaceBoundary() { clearMeshSurface(); - - polyMeshGenModifier(mesh_).replaceBoundary - ( - patchNames_, - newBoundaryFaces_, - newBoundaryOwners_, - newBoundaryPatches_ - ); + + polyMeshGenModifier(mesh_).replaceBoundary + ( + patchNames_, + newBoundaryFaces_, + newBoundaryOwners_, + newBoundaryPatches_ + ); } void correctEdgesBetweenPatches::decomposeCorrectedCells() @@ -72,7 +71,7 @@ void correctEdgesBetweenPatches::decomposeCorrectedCells() if( decompose_ ) { clearMeshSurface(); - + decomposeCells dc(mesh_); dc.decomposeMesh(decomposeCell_); } @@ -80,26 +79,21 @@ void correctEdgesBetweenPatches::decomposeCorrectedCells() // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // -// Construct from mesh, octree, regions for boundary vertices -correctEdgesBetweenPatches::correctEdgesBetweenPatches -( - polyMeshGen& mesh -) +// Construct from mesh +correctEdgesBetweenPatches::correctEdgesBetweenPatches(polyMeshGen& mesh) : - mesh_(mesh), - msePtr_(NULL), - patchNames_(mesh.boundaries().size()), - newBoundaryFaces_(), - newBoundaryOwners_(), - newBoundaryPatches_(), - decomposeCell_(mesh_.cells().size(), false), - decompose_(false) + mesh_(mesh), + msePtr_(NULL), + patchNames_(mesh.boundaries().size()), + newBoundaryFaces_(), + newBoundaryOwners_(), + newBoundaryPatches_(), + decomposeCell_(mesh_.cells().size(), false), + decompose_(false) { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - forAll(boundaries, patchI) - patchNames_[patchI] = boundaries[patchI].patchName(); - - checkFacePatches(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + forAll(boundaries, patchI) + patchNames_[patchI] = boundaries[patchI].patchName(); decomposeProblematicFaces(); @@ -112,7 +106,7 @@ correctEdgesBetweenPatches::correctEdgesBetweenPatches correctEdgesBetweenPatches::~correctEdgesBetweenPatches() { - deleteDemandDrivenData(msePtr_); + deleteDemandDrivenData(msePtr_); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.H b/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.H index 4c735c317247b90b9bd4df316a0eba8eb0917165..4cb9d868702389d5b5e7d7df0ff013b7c98a9d29 100644 --- a/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.H +++ b/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatches.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class correctEdgesBetweenPatches Description Changes mesh surface until every boundary face shares only one edge with - the faces in other boundary patch + the faces in other boundary patch SourceFiles correctEdgesBetweenPatches.C @@ -38,7 +37,7 @@ SourceFiles #define correctEdgesBetweenPatches_H #include "polyMeshGenModifier.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "boolList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -57,47 +56,43 @@ class meshSurfaceEngine; class correctEdgesBetweenPatches { // Private data - //- mesh - polyMeshGen& mesh_; - - //- pointer to surface engine - mutable const meshSurfaceEngine* msePtr_; - - //- boundary data - wordList patchNames_; - VRWGraph newBoundaryFaces_; - labelListPMG newBoundaryOwners_; - labelListPMG newBoundaryPatches_; - - //- holds data which cells have to be decomposed - boolList decomposeCell_; - bool decompose_; + //- mesh + polyMeshGen& mesh_; + + //- pointer to surface engine + mutable const meshSurfaceEngine* msePtr_; + + //- boundary data + wordList patchNames_; + VRWGraph newBoundaryFaces_; + labelLongList newBoundaryOwners_; + labelLongList newBoundaryPatches_; + + //- holds data which cells have to be decomposed + boolList decomposeCell_; + bool decompose_; // Private member functions - + //- construct and return mesh surface const meshSurfaceEngine& meshSurface() const; - + //- delete mesh surface void clearMeshSurface(); - - //- replace boundary - void replaceBoundary(); - - //- decompose corrected cells - void decomposeCorrectedCells(); - - //- minimise the number of edges which should be constrained - //- to the feature edges - void checkFacePatches(); - + + //- replace boundary + void replaceBoundary(); + + //- decompose corrected cells + void decomposeCorrectedCells(); + //- decompose bnd faces for which the feature edges are not connected //- over vertices and internal faces which have more than one feature //- edge at the boundary void decomposeProblematicFaces(); - - //- perform decompose remaining faces having more than one feature edge - void patchCorrection(); + + //- perform decompose remaining faces having more than one feature edge + void patchCorrection(); //- Disallow default bitwise copy construct correctEdgesBetweenPatches(const correctEdgesBetweenPatches&); diff --git a/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatchesDistributeFaces.C b/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatchesDistributeFaces.C index c6c9a5d719e78e94b892f073075b9513c542f9ab..0c05cd8a9d238456413dedbbc4f9e1ebb21e7fde 100644 --- a/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatchesDistributeFaces.C +++ b/meshLibrary/utilities/surfaceTools/correctEdgesBetweenPatches/correctEdgesBetweenPatchesDistributeFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,7 +35,10 @@ Description #include "helperFunctionsPar.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGMapping @@ -47,169 +49,6 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void correctEdgesBetweenPatches::checkFacePatches() -{ - Info << "Checking patches" << endl; - const meshSurfaceEngine& mse = meshSurface(); - - const faceList::subList& bFaces = mse.boundaryFaces(); - const labelList& faceOwner = mse.faceOwners(); - const VRWGraph& faceEdges = mse.faceEdges(); - const VRWGraph& edgeFaces = mse.edgeFaces(); - const labelList& facePatch = mse.boundaryFacePatches(); - - newBoundaryFaces_.setSize(0); - newBoundaryOwners_.setSize(0); - newBoundaryPatches_.setSize(bFaces.size()); - forAll(newBoundaryPatches_, bfI) - newBoundaryPatches_[bfI] = facePatch[bfI]; - - label nCorrected; - bool changed(false); - std::map<label, label> otherProcNewPatch; - - do - { - nCorrected = 0; - - if( Pstream::parRun() ) - { - const Map<label>& otherProc = mse.otherEdgeFaceAtProc(); - const Map<label>& globalToLocal = - mse.globalToLocalBndEdgeAddressing(); - - //- create communication matrix - std::map<label, labelListPMG> exchangeData; - const DynList<label>& neiProcs = mse.beNeiProcs(); - forAll(neiProcs, procI) - exchangeData.insert - ( - std::make_pair(neiProcs[procI], labelListPMG()) - ); - - forAllConstIter(Map<label>, globalToLocal, it) - { - const label beI = it(); - - if( edgeFaces.sizeOfRow(beI) == 1 ) - { - labelListPMG& dts = exchangeData[otherProc[beI]]; - //- send data as follows: - //- 1. global edge label - //- 2. patch of the attached boundary face - dts.append(it.key()); - dts.append(newBoundaryPatches_[edgeFaces(beI, 0)]); - } - } - - labelListPMG receivedData; - help::exchangeMap(exchangeData, receivedData); - - label counter(0); - while( counter < receivedData.size() ) - { - const label beI = globalToLocal[receivedData[counter++]]; - const label fPatch = receivedData[counter++]; - - otherProcNewPatch[beI] = fPatch; - } - } - - //- go through the list of faces and check if they shall remain - //- in the current patch - # pragma omp parallel for schedule(guided) reduction(+ : nCorrected) - forAll(faceEdges, bfI) - { - DynList<label> allNeiPatches; - DynList<label> neiPatches; - neiPatches.setSize(faceEdges.sizeOfRow(bfI)); - - forAllRow(faceEdges, bfI, eI) - { - const label beI = faceEdges(bfI, eI); - - if( edgeFaces.sizeOfRow(beI) == 2 ) - { - label fNei = edgeFaces(beI, 0); - if( fNei == bfI ) - fNei = edgeFaces(faceEdges(bfI, eI), 1); - - allNeiPatches.appendIfNotIn(newBoundaryPatches_[fNei]); - neiPatches[eI] = newBoundaryPatches_[fNei]; - } - else if( edgeFaces.sizeOfRow(beI) == 1 ) - { - allNeiPatches.appendIfNotIn(otherProcNewPatch[beI]); - neiPatches[eI] = otherProcNewPatch[beI]; - } - } - - //- check if some faces have to be distributed to another patch - //- in order to reduce the number of feature edges - if( - (allNeiPatches.size() == 1) && - (allNeiPatches[0] == newBoundaryPatches_[bfI]) - ) - continue; - - Map<label> nNeiInPatch(allNeiPatches.size()); - forAll(allNeiPatches, i) - nNeiInPatch.insert(allNeiPatches[i], 0); - forAll(neiPatches, eI) - ++nNeiInPatch[neiPatches[eI]]; - - label newPatch(-1), nNeiEdges(0); - forAllConstIter(Map<label>, nNeiInPatch, it) - { - if( it() > nNeiEdges ) - { - newPatch = it.key(); - nNeiEdges = it(); - } - else if - ( - it() == nNeiEdges && it.key() == newBoundaryPatches_[bfI] - ) - newPatch = it.key(); - } - - if( (newPatch < 0) || (newPatch == newBoundaryPatches_[bfI]) ) - continue; - - boolList sharedEdge(bFaces[bfI].size(), false); - forAll(neiPatches, eI) - if( neiPatches[eI] == newPatch ) - sharedEdge[eI] = true; - - if( help::areElementsInChain(sharedEdge) ) - { - //- change the patch to the newPatch - ++nCorrected; - newBoundaryPatches_[bfI] = newPatch; - } - } - - reduce(nCorrected, sumOp<label>()); - - if( nCorrected != 0 ) - changed = true; - - } while( nCorrected != 0 ); - - if( changed ) - { - forAll(bFaces, bfI) - { - newBoundaryFaces_.appendList(bFaces[bfI]); - newBoundaryOwners_.append(faceOwner[bfI]); - } - - replaceBoundary(); - } - - Info << "Finished checking patches" << endl; -} - void correctEdgesBetweenPatches::decomposeProblematicFaces() { Info << "Decomposing problematic faces" << endl; @@ -252,11 +91,11 @@ void correctEdgesBetweenPatches::decomposeProblematicFaces() } //- propagate information to all processors that need this information - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAll(mse.beNeiProcs(), i) exchangeData.insert ( - std::make_pair(mse.beNeiProcs()[i], labelListPMG()) + std::make_pair(mse.beNeiProcs()[i], labelLongList()) ); //- append labels of feature edges that need to be sent to other @@ -278,7 +117,7 @@ void correctEdgesBetweenPatches::decomposeProblematicFaces() } } - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); label counter(0); @@ -298,7 +137,9 @@ void correctEdgesBetweenPatches::decomposeProblematicFaces() //- decompose internal faces with more than one feature edge const label nIntFaces = mesh.nInternalFaces(); + # ifdef USE_OMP # pragma omp parallel for schedule(guided) reduction(+ : nDecomposedFaces) + # endif for(label faceI=0;faceI<nIntFaces;++faceI) { const face& f = faces[faceI]; @@ -335,7 +176,9 @@ void correctEdgesBetweenPatches::decomposeProblematicFaces() //- decompose boundary faces in case the feature edges are not connected //- into a single open chain of edges + # ifdef USE_OMP # pragma omp parallel for schedule(guided) reduction(+ : nDecomposedFaces) + # endif forAll(faceEdges, bfI) { boolList featureEdge(faceEdges.sizeOfRow(bfI), false); @@ -355,7 +198,7 @@ void correctEdgesBetweenPatches::decomposeProblematicFaces() if( Pstream::parRun() ) { //- decompose processor faces having more than one feature edge - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh.procBoundaries(); forAll(procBoundaries, patchI) @@ -363,8 +206,10 @@ void correctEdgesBetweenPatches::decomposeProblematicFaces() const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); + # ifdef USE_OMP # pragma omp parallel for schedule(guided) \ reduction(+ : nDecomposedFaces) + # endif for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; @@ -442,14 +287,16 @@ void correctEdgesBetweenPatches::patchCorrection() nodeType[it.key()] |= 1; //- set flgs to edge vertices - const labelHashSet& edgeNodes = surfacePartitioner.edgeNodes(); - forAllConstIter(labelHashSet, edgeNodes, it) + const labelHashSet& edgePoints = surfacePartitioner.edgePoints(); + forAllConstIter(labelHashSet, edgePoints, it) nodeType[it.key()] |= 2; //- set flags for feature edges boolList featureEdge(edgeFaces.size(), false); + # ifdef USE_OMP # pragma omp parallel for schedule(guided) + # endif forAll(edgeFaces, eI) { if( edgeFaces.sizeOfRow(eI) != 2 ) diff --git a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.C b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.C index 052b499e8ceffb5c9d05f3c96fc293571e20912c..f2950cfd02f251df2dc08079674f42faaa100e72 100644 --- a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.C +++ b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.H b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.H index 297c92c966522d44480ad5b0d3f22e3a7f108770..eb2b79bca9cf895cef4a8b7a5cdc3d029db9244e 100644 --- a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.H +++ b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheets/createFundamentalSheets.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class createFundamentalSheets @@ -38,7 +37,7 @@ SourceFiles #define createFundamentalSheets_H #include "polyMeshGenModifier.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "boolList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.C b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.C index 942c1c177b701c2e280bcd221daf2ce7ef806e18..869c38677d307dcf982c389b25a27c79a4ed5f97 100644 --- a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.C +++ b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,9 @@ Description #include "addToRunTimeSelectionTable.H" +# ifdef USE_OMP #include <omp.h> +# endif // #define DEBUGSearch @@ -56,7 +57,7 @@ addToRunTimeSelectionTable void createFundamentalSheetsFJ::createInitialSheet() { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); const label start = boundaries[0].patchStart(); const label end @@ -71,7 +72,9 @@ void createFundamentalSheetsFJ::createInitialSheet() LongList<labelPair> extrudeFaces(end-start); + # ifdef USE_OMP # pragma omp parallel for + # endif for(label faceI=start;faceI<end;++faceI) extrudeFaces[faceI-start] = labelPair(faceI, owner[faceI]); @@ -80,7 +83,7 @@ void createFundamentalSheetsFJ::createInitialSheet() void createFundamentalSheetsFJ::createSheetsAtFeatureEdges() { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { @@ -207,8 +210,7 @@ createFundamentalSheetsFJ::createFundamentalSheetsFJ // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // createFundamentalSheetsFJ::~createFundamentalSheetsFJ() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.H b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.H index 3a964dcbc19bb9a89c52357ea4bc9dee35aff58a..6436d2edd32c45b527538ac662c78997f757fea3 100644 --- a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.H +++ b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsFJ/createFundamentalSheetsFJ.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class createFundamentalSheetsFJ @@ -42,7 +41,7 @@ SourceFiles #include "polyMeshGenModifier.H" #include "createFundamentalSheets.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "boolList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.C b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.C index 03538c3edc51c457ae252b82515d89e4610b5d25..eb244eb87be35e69d89d87bf70bdc92c5ac2ea97 100644 --- a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.C +++ b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,9 @@ Description #include "addToRunTimeSelectionTable.H" +# ifdef USE_OMP #include <omp.h> +# endif // #define DEBUGSearch @@ -56,7 +57,7 @@ addToRunTimeSelectionTable void createFundamentalSheetsJFS::createInitialSheet() { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); const label start = boundaries[0].patchStart(); const label end @@ -71,7 +72,9 @@ void createFundamentalSheetsJFS::createInitialSheet() LongList<labelPair> extrudeFaces(end-start); + # ifdef USE_OMP # pragma omp parallel for + # endif for(label faceI=start;faceI<end;++faceI) extrudeFaces[faceI-start] = labelPair(faceI, owner[faceI]); @@ -80,7 +83,7 @@ void createFundamentalSheetsJFS::createInitialSheet() void createFundamentalSheetsJFS::createSheetsAtFeatureEdges() { - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); const cellListPMG& cells = mesh_.cells(); const labelList& owner = mesh_.owner(); const labelList& neighbour = mesh_.neighbour(); @@ -98,23 +101,31 @@ void createFundamentalSheetsJFS::createSheetsAtFeatureEdges() LongList<labelPair> front; + # ifdef USE_OMP const label nThreads = 2 * omp_get_num_procs(); # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP # pragma omp for + # endif forAll(patchCell, cellI) patchCell[cellI] = -1; + # ifdef USE_OMP # pragma omp barrier # pragma omp for + # endif for(label faceI=start;faceI<end;++faceI) patchCell[owner[faceI]] = mesh_.faceIsInPatch(faceI); //- create the front faces LongList<labelPair> localFront; + # ifdef USE_OMP # pragma omp for + # endif for(label faceI=start;faceI<end;++faceI) { const cell& c = cells[owner[faceI]]; @@ -135,7 +146,9 @@ void createFundamentalSheetsJFS::createSheetsAtFeatureEdges() } label frontStart(-1); + # ifdef USE_OMP # pragma omp critical + # endif { frontStart = front.size(); front.setSize(front.size()+localFront.size()); @@ -168,8 +181,7 @@ createFundamentalSheetsJFS::createFundamentalSheetsJFS // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // createFundamentalSheetsJFS::~createFundamentalSheetsJFS() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.H b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.H index ddedb57eef84dc892b59c2e2f60999269d937399..11b5249b3c2dd16f124150501409d73d0195ecd3 100644 --- a/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.H +++ b/meshLibrary/utilities/surfaceTools/createFundamentalSheets/createFundamentalSheetsJFS/createFundamentalSheetsJFS.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class createFundamentalSheetsJFS @@ -38,7 +37,7 @@ SourceFiles #include "polyMeshGenModifier.H" #include "createFundamentalSheets.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "boolList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.C b/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.C index 13e59b3be3e5e74057e152ea878058250703e82b..3477ba42f8ba75e5b85605c7d25921e6019f417e 100644 --- a/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.C +++ b/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,7 +34,7 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -43,15 +42,15 @@ namespace Foam // Construct from mesh, octree, regions for boundary vertices decomposeCellsNearConcaveEdges::decomposeCellsNearConcaveEdges ( - polyMeshGen& mesh + polyMeshGen& mesh ) : - mesh_(mesh), - decomposeCell_(mesh_.cells().size(), false) -{ - findConcaveFacesAndCells(); - - decomposeConcaveCells(); + mesh_(mesh), + decomposeCell_(mesh_.cells().size(), false) +{ + findConcaveFacesAndCells(); + + decomposeConcaveCells(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.H b/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.H index 152527a1e3003d36e610a7113900afb2a1bc6969..0b3657e80f6d547f0787df9c6e6036af1caac076 100644 --- a/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.H +++ b/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdges.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class decomposeCellsNearConcaveEdges @@ -51,19 +50,19 @@ namespace Foam class decomposeCellsNearConcaveEdges { // Private data - //- mesh - polyMeshGen& mesh_; - - //- holds data which cells have to be decomposed - boolList decomposeCell_; + //- mesh + polyMeshGen& mesh_; + + //- holds data which cells have to be decomposed + boolList decomposeCell_; // Private member functions - //- find problematic cells which need to be decomposed - void findConcaveFacesAndCells(); - - //- perform patch correction - void decomposeConcaveCells(); + //- find problematic cells which need to be decomposed + void findConcaveFacesAndCells(); + + //- perform patch correction + void decomposeConcaveCells(); //- Disallow default bitwise copy construct decomposeCellsNearConcaveEdges(const decomposeCellsNearConcaveEdges&); diff --git a/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdgesDecompose.C b/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdgesDecompose.C index f15942b310a87455f2e9a8c6ac36456db747cd00..429ddef061adb6d1d4ac3e145f62f979c4c53bd1 100644 --- a/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdgesDecompose.C +++ b/meshLibrary/utilities/surfaceTools/decomposeCellsNearConcaveEdges/decomposeCellsNearConcaveEdgesDecompose.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,85 +42,85 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void decomposeCellsNearConcaveEdges::findConcaveFacesAndCells() { - meshSurfaceEngine mse(mesh_); - const faceList::subList& bFaces = mse.boundaryFaces(); - const labelList& facePatch = mse.boundaryFacePatches(); - const VRWGraph& edgeFaces = mse.edgeFaces(); - const edgeList& edges = mse.edges(); - const pointFieldPMG& points = mesh_.points(); - - boolList concaveVertex(points.size(), false); - forAll(edgeFaces, eI) - { - const label bfI = edgeFaces[eI][0]; - const label bfJ = edgeFaces[eI][1]; - - const face& f0 = bFaces[bfI]; - const face& f1 = bFaces[bfJ]; - - if( - (facePatch[bfI] != facePatch[bfJ]) && - !help::isSharedEdgeConvex(points, f0, f1) - ) - { - const edge& e = edges[eI]; - concaveVertex[e[0]] = true; - concaveVertex[e[1]] = true; - } - } - - //- decompose concave internal faces - decomposeFaces(mesh_).decomposeConcaveInternalFaces(concaveVertex); - - //- find which cells need to be decomposed - # ifdef DEBUGDec - const label id = mesh_.addCellSubset("decomposeCells"); - # endif + meshSurfaceEngine mse(mesh_); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& facePatch = mse.boundaryFacePatches(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const edgeList& edges = mse.edges(); + const pointFieldPMG& points = mesh_.points(); - const faceListPMG& faces = mesh_.faces(); - const labelList& owner = mesh_.owner(); - const labelList& neighbour = mesh_.neighbour(); - const label nIntFaces = mesh_.nInternalFaces(); - for(label faceI=0;faceI<nIntFaces;++faceI) - { - const face& f = faces[faceI]; - - forAll(f, pI) + boolList concaveVertex(points.size(), false); + forAll(edgeFaces, eI) + { + const label bfI = edgeFaces[eI][0]; + const label bfJ = edgeFaces[eI][1]; + + const face& f0 = bFaces[bfI]; + const face& f1 = bFaces[bfJ]; + + if( + (facePatch[bfI] != facePatch[bfJ]) && + !help::isSharedEdgeConvex(points, f0, f1) + ) + { + const edge& e = edges[eI]; + concaveVertex[e[0]] = true; + concaveVertex[e[1]] = true; + } + } + + //- decompose concave internal faces + decomposeFaces(mesh_).decomposeConcaveInternalFaces(concaveVertex); + + //- find which cells need to be decomposed + # ifdef DEBUGDec + const label id = mesh_.addCellSubset("decomposeCells"); + # endif + + const faceListPMG& faces = mesh_.faces(); + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + const label nIntFaces = mesh_.nInternalFaces(); + for(label faceI=0;faceI<nIntFaces;++faceI) + { + const face& f = faces[faceI]; + + forAll(f, pI) { if( f[pI] >= concaveVertex.size() ) continue; - if( concaveVertex[f[pI]] ) - { - decomposeCell_[owner[faceI]] = true; - decomposeCell_[neighbour[faceI]] = true; - - # ifdef DEBUGDec - mesh_.addCellToSubset(id, owner[faceI]); - mesh_.addCellToSubset(id, neighbour[faceI]); - # endif - - break; - } + if( concaveVertex[f[pI]] ) + { + decomposeCell_[owner[faceI]] = true; + decomposeCell_[neighbour[faceI]] = true; + + # ifdef DEBUGDec + mesh_.addCellToSubset(id, owner[faceI]); + mesh_.addCellToSubset(id, neighbour[faceI]); + # endif + + break; + } } - } - - # ifdef DEBUGDec + } + + # ifdef DEBUGDec Info << "Writting mesh" << endl; - mesh_.write(); - ::exit(1); - # endif -} + mesh_.write(); + ::exit(1); + # endif +} void decomposeCellsNearConcaveEdges::decomposeConcaveCells() { - decomposeCells dc(mesh_); - dc.decomposeMesh(decomposeCell_); + decomposeCells dc(mesh_); + dc.decomposeMesh(decomposeCell_); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractionFunctions/edgeExtractionFunctions.C b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractionFunctions/edgeExtractionFunctions.C deleted file mode 100644 index 7da5cfec7c2ac2af868eb46e777edc360f48fdb4..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractionFunctions/edgeExtractionFunctions.C +++ /dev/null @@ -1,77 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - -\*---------------------------------------------------------------------------*/ - -#include "error.H" -#include "helperFunctionsPar.H" -#include "DynList.H" -#include "labelPair.H" -#include "HashSet.H" - -#include <omp.h> - -#define DEBUGExchangeMap - -namespace Foam -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// - -namespace help -{ - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// - -void distributeBoundaryFaces -( - const meshSurfaceEngine& surfaceEngine, - const meshOctree& octree, - labelListPMG& facePatch -) -{ - -} - -void findCornerCandidates -( - const meshSurfaceEngine& surfaceEngine, - const meshOctree& octree, - LongList<labelPair>& pointMap -) -{ - -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// - -} // End namespace help - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// - -} // End namespace Foam - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractionFunctions/edgeExtractionFunctions.H b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractionFunctions/edgeExtractionFunctions.H deleted file mode 100644 index 1db47708eb65daa4f950bdd2a926df3cf90eacc0..0000000000000000000000000000000000000000 --- a/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractionFunctions/edgeExtractionFunctions.H +++ /dev/null @@ -1,80 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Namespace - Foam::edgeExtraction - -Description - Helper functions used for capturing feature edges - and transferring of surface patches on the volume mesh - -SourceFiles - -\*---------------------------------------------------------------------------*/ - -#ifndef edgeExtraction_H -#define edgeExtraction_H - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - - - -namespace Foam -{ - -/*---------------------------------------------------------------------------*\ - Namespace EdgeExtraction functions Declaration -\*---------------------------------------------------------------------------*/ - -namespace EdgeExtraction -{ - //- project face centres on the nearest location at the surface mesh - //- and assign the patch to the patch of the surface element - void distributeBoundaryFaces - ( - const meshSurfaceEngine&, - const meshOctree&, - labelListPMG& - ); - - //- find the nearest points on the surface of the volume mesh - //- to the corners on the triangulated surface - void findCornerCandidates - ( - const meshSurfaceEngine&, - const meshOctree& - LongList<labelPair>& - ); - - - -} // End namespace EdgeExtraction - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam - -#endif - -// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractor.C b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractor.C new file mode 100644 index 0000000000000000000000000000000000000000..0ac8e401f2c30969aa0dbdc22522075ee6996326 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractor.C @@ -0,0 +1,2578 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "error.H" +#include "polyMeshGenModifier.H" +#include "edgeExtractor.H" +#include "meshSurfaceEngine.H" +#include "meshSurfaceEngineModifier.H" +#include "meshSurfaceOptimizer.H" +#include "meshOctree.H" +#include "triSurf.H" +#include "triSurfModifier.H" +#include "helperFunctions.H" +#include "DynList.H" +#include "labelPair.H" +#include "labelledScalar.H" +#include "labelledPoint.H" +#include "refLabelledPoint.H" +#include "HashSet.H" +#include "triSurfacePartitioner.H" +#include "triSurfaceClassifyEdges.H" +#include "meshSurfaceMapper.H" +#include "meshSurfaceCheckInvertedVertices.H" +#include "meshSurfaceCheckEdgeTypes.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGEdgeExtractor + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// +// Private member functions + +void edgeExtractor::calculateValence() +{ + const meshSurfaceEngine& mse = this->surfaceEngine(); + pointValence_.setSize(mse.boundaryPoints().size()); + pointValence_ = 0; + + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& bp = mse.bp(); + + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + ++pointValence_[bp[bf[pI]]]; + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = + mse.globalToLocalBndPointAddressing(); + const VRWGraph& bpAtProcs = mse.bpAtProcs(); + const DynList<label>& bpNeiProcs = mse.bpNeiProcs(); + + std::map<label, LongList<labelPair> > exchangeData; + forAll(bpNeiProcs, i) + exchangeData.insert + ( + std::make_pair(bpNeiProcs[i], LongList<labelPair>()) + ); + + forAllConstIter(Map<label>, globalToLocal, iter) + { + const label bpI = iter(); + + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelPair(iter.key(), pointValence_[bpI]) + ); + } + } + + LongList<labelPair> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelPair& lp = receivedData[i]; + + pointValence_[globalToLocal[lp.first()]] += lp.second(); + } + } +} + +void edgeExtractor::calculateSingleCellEdge() +{ + const meshSurfaceEngine& mse = this->surfaceEngine(); + const edgeList& edges = mse.edges(); + const VRWGraph& bpEdges = mse.boundaryPointEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const labelList& faceCells = mse.faceOwners(); + + //- find the number of boundary faces for each cell in the mesh + edgeType_.setSize(edgeFaces.size()); + edgeType_ = NONE; + + forAll(edgeFaces, eI) + { + if( edgeFaces.sizeOfRow(eI) == 2 ) + { + const label c0 = faceCells[edgeFaces(eI, 0)]; + const label c1 = faceCells[edgeFaces(eI, 1)]; + + if( c0 == c1 ) + edgeType_[eI] |= SINGLECELLEDGE; + } + } + + //- calculate the number of cells attache to a boundary edge + const labelList& bp = mse.bp(); + const cellListPMG& cells = mse.mesh().cells(); + const faceListPMG& faces = mse.faces(); + + nCellsAtEdge_.setSize(edgeFaces.size()); + nCellsAtEdge_ = 0; + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 100) + # endif + forAll(cells, cellI) + { + const cell& c = cells[cellI]; + + DynList<edge> foundEdge; + + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + forAll(f, eI) + { + const edge e = f.faceEdge(eI); + + const label bps = bp[e.start()]; + + if( bps < 0 ) + continue; + + forAllRow(bpEdges, bps, i) + { + const label beI = bpEdges(bps, i); + const edge& be = edges[beI]; + + if( (e == be) && !foundEdge.contains(be) ) + { + foundEdge.append(be); + + # ifdef USE_OMP + # pragma omp atomic + # endif + ++nCellsAtEdge_[beI]; + } + } + } + } + } +} + +void edgeExtractor::findPatchesNearSurfaceFace() +{ + const meshSurfaceEngine& mse = this->surfaceEngine(); + const pointFieldPMG& points = mse.points(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const triSurf& surface = meshOctree_.surface(); + + patchesNearFace_.setSize(bFaces.size()); + labelLongList nPatchesAtFace(bFaces.size()); + + # ifdef USE_OMP + # pragma omp parallel + # endif + { + labelLongList localData; + DynList<label> nearFacets; + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + const vector c = bf.centre(points); + + // find a reasonable searching distance comparable to face size + scalar d(0.0); + forAll(bf, pI) + d = Foam::max(d, Foam::mag(c - points[bf[pI]])); + d = 2.0 * d + VSMALL; + + const boundBox bb(c - vector(d, d, d), c + vector(d, d, d)); + + //- get the patches near the current boundary face + meshOctree_.findTrianglesInBox(bb, nearFacets); + DynList<label> nearPatches; + forAll(nearFacets, i) + nearPatches.appendIfNotIn(surface[nearFacets[i]].region()); + + localData.append(bfI); + nPatchesAtFace[bfI] = nearPatches.size(); + forAll(nearPatches, i) + localData.append(nearPatches[i]); + } + + # ifdef USE_OMP + # pragma omp barrier + + # pragma omp master + patchesNearFace_.setSizeAndRowSize(nPatchesAtFace); + + # pragma omp barrier + # else + patchesNearFace_.setSizeAndRowSize(nPatchesAtFace); + # endif + + //- copy the data to the graph + label counter(0); + while( counter < localData.size() ) + { + const label edgeI = localData[counter++]; + + const label size = nPatchesAtFace[edgeI]; + + for(label i=0;i<size;++i) + patchesNearFace_(edgeI, i) = localData[counter++]; + } + } +} + +void edgeExtractor::findFeatureEdgesNearEdge() +{ + const meshSurfaceEngine& mse = this->surfaceEngine(); + const pointFieldPMG& points = mse.points(); + const edgeList& edges = mse.edges(); + + featureEdgesNearEdge_.setSize(edges.size()); + labelLongList nFeatureEdgesAtEdge(edges.size()); + + # ifdef USE_OMP + # pragma omp parallel + # endif + { + labelLongList localData; + DynList<label> nearEdges; + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(edges, edgeI) + { + const edge& e = edges[edgeI]; + const vector c = e.centre(points); + const scalar d = 1.5 * e.mag(points); + + const boundBox bb(c - vector(d, d, d), c + vector(d, d, d)); + + //- get the edges near the current edge + meshOctree_.findEdgesInBox(bb, nearEdges); + forAllReverse(nearEdges, i) + { + const label pos = nearEdges.containsAtPosition(nearEdges[i]); + + if( pos < i ) + nearEdges.removeElement(i); + } + + localData.append(edgeI); + nFeatureEdgesAtEdge[edgeI] = nearEdges.size(); + forAll(nearEdges, i) + localData.append(nearEdges[i]); + } + + # ifdef USE_OMP + # pragma omp barrier + + # pragma omp master + featureEdgesNearEdge_.setSizeAndRowSize(nFeatureEdgesAtEdge); + + # pragma omp barrier + # else + featureEdgesNearEdge_.setSizeAndRowSize(nFeatureEdgesAtEdge); + # endif + + //- copy the data to the graph + label counter(0); + while( counter < localData.size() ) + { + const label edgeI = localData[counter++]; + + const label size = nFeatureEdgesAtEdge[edgeI]; + + for(label i=0;i<size;++i) + featureEdgesNearEdge_(edgeI, i) = localData[counter++]; + } + } +} + +void edgeExtractor::markPatchPoints(boolList& patchPoint) +{ + const meshSurfaceEngine& mse = this->surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const edgeList& edges = mse.edges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const labelList& bp = mse.bp(); + + patchPoint.setSize(bPoints.size()); + patchPoint = true; + + std::map<label, label> otherProcPatch; + if( Pstream::parRun() ) + { + const Map<label>& otherProc = mse.otherEdgeFaceAtProc(); + const Map<label>& globalToLocal = + mse.globalToLocalBndEdgeAddressing(); + + //- create communication matrix + std::map<label, labelLongList> exchangeData; + const DynList<label>& neiProcs = mse.beNeiProcs(); + forAll(neiProcs, procI) + exchangeData.insert + ( + std::make_pair(neiProcs[procI], labelLongList()) + ); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + if( edgeFaces.sizeOfRow(beI) == 1 ) + { + labelLongList& dts = exchangeData[otherProc[beI]]; + //- send data as follows: + //- 1. global edge label + //- 2. patch of the attached boundary face + dts.append(it.key()); + dts.append(facePatch_[edgeFaces(beI, 0)]); + } + } + + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + label counter(0); + while( counter < receivedData.size() ) + { + const label beI = globalToLocal[receivedData[counter++]]; + const label fPatch = receivedData[counter++]; + + otherProcPatch[beI] = fPatch; + } + } + + //- set the patchPoint to false for all vertices at feature edges + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(edgeFaces, beI) + { + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + //- an ordinary edge + if( facePatch_[edgeFaces(beI, 0)] != facePatch_[edgeFaces(beI, 1)] ) + { + const edge& e = edges[beI]; + patchPoint[bp[e.start()]] = false; + patchPoint[bp[e.end()]] = false; + } + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + //- an edge at a parallel interface + const label otherPatch = otherProcPatch[beI]; + + if( facePatch_[edgeFaces(beI, 0)] != otherPatch ) + { + const edge& e = edges[beI]; + patchPoint[bp[e.start()]] = false; + patchPoint[bp[e.end()]] = false; + } + } + else + { + //- this is a non-manifold edge + const edge& e = edges[beI]; + patchPoint[bp[e.start()]] = false; + patchPoint[bp[e.end()]] = false; + } + } + + if( Pstream::parRun() ) + { + //- make sure that the information is spread to all processors + const VRWGraph& bpAtProcs = mse.bpAtProcs(); + const DynList<label>& neiProcs = mse.bpNeiProcs(); + const labelList& globalPointLabel = + mse.globalBoundaryPointLabel(); + const Map<label>& globalToLocal = + mse.globalToLocalBndPointAddressing(); + + + std::map<label, labelLongList> sendData; + forAll(neiProcs, i) + sendData.insert(std::make_pair(neiProcs[i], labelLongList())); + + forAll(bpAtProcs, bpI) + { + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc != Pstream::myProcNo() ) + sendData[neiProc].append(globalPointLabel[bpI]); + } + } + + labelLongList receivedData; + help::exchangeMap(sendData, receivedData); + + forAll(receivedData, i) + patchPoint[globalToLocal[receivedData[i]]] = false; + } +} + +const meshSurfaceEngine& edgeExtractor::surfaceEngine() const +{ + if( !surfaceEnginePtr_ ) + { + # ifdef USE_OMP + # pragma omp critical + # endif + { + if( !surfaceEnginePtr_ ) + { + surfaceEnginePtr_ = new meshSurfaceEngine(mesh_); + } + } + } + + return *surfaceEnginePtr_; +} + +const triSurfacePartitioner& edgeExtractor::partitioner() const +{ + if( !surfPartitionerPtr_ ) + { + # ifdef USE_OMP + # pragma omp critical + # endif + { + if( !surfPartitionerPtr_ ) + { + surfPartitionerPtr_ = + new triSurfacePartitioner(meshOctree_.surface()); + } + } + } + + return *surfPartitionerPtr_; +} + +const triSurfaceClassifyEdges& edgeExtractor::edgeClassifier() const +{ + if( !surfEdgeClassificationPtr_ ) + { + surfEdgeClassificationPtr_ = + new triSurfaceClassifyEdges(meshOctree_); + } + + return *surfEdgeClassificationPtr_; +} + +void edgeExtractor::findFaceCandidates +( + labelLongList& faceCandidates, + const labelList* facePatchPtr, + const Map<label>* otherFacePatchPtr +) const +{ + faceCandidates.clear(); + if( !facePatchPtr ) + facePatchPtr = &facePatch_; + + const labelList& fPatches = *facePatchPtr; + + if( !otherFacePatchPtr ) + { + Map<label> otherFacePatch; + findOtherFacePatchesParallel(otherFacePatch, &fPatches); + + otherFacePatchPtr = &otherFacePatch; + } + + const Map<label>& otherFacePatch = *otherFacePatchPtr; + + const meshSurfaceEngine& mse = surfaceEngine(); + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + # ifdef USE_OMP + # pragma omp parallel if( faceEdges.size() > 1000 ) + # endif + { + # ifdef USE_OMP + labelLongList procCandidates; + # pragma omp for schedule(dynamic, 40) + # endif + forAll(faceEdges, bfI) + { + DynList<label> allNeiPatches; + forAllRow(faceEdges, bfI, eI) + { + const label beI = faceEdges(bfI, eI); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + label fNei = edgeFaces(beI, 0); + if( fNei == bfI ) + fNei = edgeFaces(faceEdges(bfI, eI), 1); + + allNeiPatches.appendIfNotIn(fPatches[fNei]); + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + allNeiPatches.appendIfNotIn(otherFacePatch[beI]); + } + } + + if( allNeiPatches.size() > 1 ) + { + //- this face is probably near some feature edge + # ifdef USE_OMP + procCandidates.append(bfI); + # else + faceCandidates.append(bfI); + # endif + } + } + + # ifdef USE_OMP + # pragma omp critical + { + forAll(procCandidates, i) + faceCandidates.append(procCandidates[i]); + } + # endif + } +} + +void edgeExtractor::findOtherFacePatchesParallel +( + Map<label>& otherFacePatch, + const labelList* facePatchPtr +) const +{ + otherFacePatch.clear(); + + if( !facePatchPtr ) + facePatchPtr = &facePatch_; + + const labelList& fPatches = *facePatchPtr; + + if( Pstream::parRun() ) + { + const meshSurfaceEngine& mse = this->surfaceEngine(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const Map<label>& otherProc = mse.otherEdgeFaceAtProc(); + const Map<label>& globalToLocal = + mse.globalToLocalBndEdgeAddressing(); + + //- create communication matrix + std::map<label, labelLongList> exchangeData; + const DynList<label>& neiProcs = mse.beNeiProcs(); + forAll(neiProcs, procI) + exchangeData.insert + ( + std::make_pair(neiProcs[procI], labelLongList()) + ); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + if( edgeFaces.sizeOfRow(beI) == 1 ) + { + labelLongList& dts = exchangeData[otherProc[beI]]; + //- send data as follows: + //- 1. global edge label + //- 2. patch of the attached boundary face + dts.append(it.key()); + dts.append(fPatches[edgeFaces(beI, 0)]); + } + } + + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + label counter(0); + while( counter < receivedData.size() ) + { + const label beI = globalToLocal[receivedData[counter++]]; + const label fPatch = receivedData[counter++]; + + otherFacePatch.insert(beI, fPatch); + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +edgeExtractor::edgeExtractor +( + polyMeshGen& mesh, + const meshOctree& octree +) +: + mesh_(mesh), + surfaceEnginePtr_(NULL), + meshOctree_(octree), + surfPartitionerPtr_(NULL), + surfEdgeClassificationPtr_(NULL), + pointValence_(), + pointPatch_(), + facePatch_(), + nCellsAtEdge_(), + edgeType_(), + patchesNearFace_(), + featureEdgesNearEdge_() +{ + calculateValence(); + + calculateSingleCellEdge(); + + findPatchesNearSurfaceFace(); + + findFeatureEdgesNearEdge(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// +// Destructor + +edgeExtractor::~edgeExtractor() +{ + deleteDemandDrivenData(surfaceEnginePtr_); + deleteDemandDrivenData(surfPartitionerPtr_); + deleteDemandDrivenData(surfEdgeClassificationPtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +void edgeExtractor::moveVerticesTowardsDiscontinuities(const label nIterations) +{ + Info << "Reducing Hausdorff distance:" << flush; + + const meshSurfaceEngine& mse = this->surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const VRWGraph& pointFaces = mse.pointFaces(); + const pointFieldPMG& points = mse.points(); + const faceList::subList& bFaces = mse.boundaryFaces(); + + meshSurfaceEngineModifier modifier(mse); + + vectorField faceCentreDisplacement(bFaces.size()); + List<labelledPoint> pointDisplacements(bPoints.size()); + + for(label iterI=0;iterI<nIterations;++iterI) + { + # ifdef USE_OMP + # pragma omp parallel + # endif + { + //- find displacements of face centres + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(bFaces, bfI) + { + const vector centre = bFaces[bfI].centre(points); + + point newP; + scalar distSq; + label patchI, nearestTri; + meshOctree_.findNearestSurfacePoint + ( + newP, + distSq, + nearestTri, + patchI, + centre + ); + + faceCentreDisplacement[bfI] = newP - centre; + } + + //- initialise displacements + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(pointDisplacements, bpI) + pointDisplacements[bpI] = labelledPoint(0, vector::zero); + + # ifdef USE_OMP + # pragma omp barrier + # endif + + //- calculate displacements of boundary points as the average + //- of face centre displacements + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(pointFaces, bpI) + { + forAllRow(pointFaces, bpI, pfI) + { + pointDisplacements[bpI].coordinates() += + faceCentreDisplacement[pointFaces(bpI, pfI)]; + ++pointDisplacements[bpI].pointLabel(); + } + } + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = + mse.globalToLocalBndPointAddressing(); + const DynList<label>& neiProcs = mse.bpNeiProcs(); + const VRWGraph& bpAtProcs = mse.bpAtProcs(); + + std::map<label, LongList<refLabelledPoint> > exchangeData; + forAll(neiProcs, i) + exchangeData[i] = LongList<refLabelledPoint>(); + + forAllConstIter(Map<label>, globalToLocal, iter) + { + const label bpI = iter(); + + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + refLabelledPoint(iter.key(), pointDisplacements[bpI]) + ); + } + } + + LongList<refLabelledPoint> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const label globalLabel = receivedData[i].objectLabel(); + const labelledPoint& lp = receivedData[i].lPoint(); + + const label bpI = globalToLocal[globalLabel]; + + pointDisplacements[bpI].coordinates() += lp.coordinates(); + pointDisplacements[bpI].pointLabel() += lp.pointLabel(); + } + } + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(pointDisplacements, bpI) + { + const labelledPoint& lp = pointDisplacements[bpI]; + const point mp = + points[bPoints[bpI]] + lp.coordinates() / lp.pointLabel(); + + //Info << "Original point " << bPoints[bpI] << " has coordinates " + // << points[bPoints[bpI]] << endl; + //Info << "Displacement vector " << lp.coordinates() / lp.pointLabel() << endl; + //Info << "Moved point " << mp << endl; + + point newPoint; + label patchI, nt; + scalar distSq; + + meshOctree_.findNearestSurfacePoint(newPoint, distSq, nt, patchI, mp); + + //Info << "Mapped point " << newPoint << nl << endl; + + modifier.moveBoundaryVertexNoUpdate(bpI, newPoint); + } + + //- update geometry + modifier.updateGeometry(); + + Info << '.' << flush; + } + + Info << endl; +} + +void edgeExtractor::distributeBoundaryFaces() +{ + const meshSurfaceEngine& mse = this->surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const pointFieldPMG& points = mse.points(); + + //- set the size of the facePatch list + facePatch_.setSize(bFaces.size()); + + //- check if the mesh already has patches + if( mesh_.boundaries().size() > 1 ) + Warning << "Mesh patches are already assigned!" << endl; + + //- set size of patchNames, newBoundaryFaces_ and newBoundaryOwners_ + const triSurf& surface = meshOctree_.surface(); + const label nPatches = surface.patches().size(); + + //- find patches to which the surface points are mapped to + pointPatch_.setSize(bPoints.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(bPoints, bpI) + { + const point& bp = points[bPoints[bpI]]; + + label fPatch, nTri; + point p; + scalar distSq; + + meshOctree_.findNearestSurfacePoint(p, distSq, nTri, fPatch, bp); + + if( (fPatch > -1) && (fPatch < nPatches) ) + { + pointPatch_[bpI] = fPatch; + } + else + { + FatalErrorIn + ( + "void meshSurfaceEdgeExtractorNonTopo::" + "distributeBoundaryFaces()" + ) << "Cannot distribute a boundary points " << bPoints[bpI] + << " into any surface patch!. Exiting.." << exit(FatalError); + } + } + + //- find the patch for face by finding the patch nearest + //- to the face centre + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + const point c = bf.centre(points); + + //- find the nearest surface patch to face centre + label fPatch, nTri; + point p; + scalar distSq; + + meshOctree_.findNearestSurfacePoint(p, distSq, nTri, fPatch, c); + + if( (fPatch > -1) && (fPatch < nPatches) ) + { + facePatch_[bfI] = fPatch; + } + else + { + FatalErrorIn + ( + "void meshSurfaceEdgeExtractorNonTopo::" + "distributeBoundaryFaces()" + ) << "Cannot distribute a face " << bFaces[bfI] << " into any " + << "surface patch!. Exiting.." << exit(FatalError); + } + } +} + +bool edgeExtractor::distributeBoundaryFacesNormalAlignment() +{ + bool changed(false); + + const pointFieldPMG& points = mesh_.points(); + const meshSurfaceEngine& mse = this->surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + const triSurf& surf = meshOctree_.surface(); + const pointField& sPoints = surf.points(); + + label nCorrected, nIterations(0); + Map<label> otherProcNewPatch; + + do + { + nCorrected = 0; + + //- allocate a copy of boundary patches + labelList newBoundaryPatches(facePatch_); + + //- check whether there exist situations where a boundary face + //- is surrounded by more faces in different patches than the + //- faces in the current patch + if( Pstream::parRun() ) + { + findOtherFacePatchesParallel + ( + otherProcNewPatch, + &facePatch_ + ); + } + + //- find the faces which have neighbouring faces in other patches + labelLongList candidates; + findFaceCandidates(candidates, &facePatch_, &otherProcNewPatch); + + //- go through the list of faces and check if they shall remain + //- in the current patch + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) \ + reduction(+ : nCorrected) + # endif + forAll(candidates, i) + { + const label bfI = candidates[i]; + const face& bf = bFaces[bfI]; + + DynList<label> allNeiPatches; + DynList<label> neiPatches; + neiPatches.setSize(faceEdges.sizeOfRow(bfI)); + + forAllRow(faceEdges, bfI, eI) + { + const label beI = faceEdges(bfI, eI); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + label fNei = edgeFaces(beI, 0); + if( fNei == bfI ) + fNei = edgeFaces(faceEdges(bfI, eI), 1); + + allNeiPatches.appendIfNotIn(facePatch_[fNei]); + neiPatches[eI] = facePatch_[fNei]; + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + allNeiPatches.appendIfNotIn(otherProcNewPatch[beI]); + neiPatches[eI] = otherProcNewPatch[beI]; + } + } + + //- do not modify faces with all neighbours in the same patch + if + ( + (allNeiPatches.size() == 1) && + (allNeiPatches[0] == facePatch_[bfI]) + ) + continue; + + //- check whether there exist edges which are more suitable for + //- projection onto feature edges than the currently selected ones + label newPatch(-1); + DynList<scalar> normalAlignment(allNeiPatches.size()); + DynList<scalar> distanceSq(allNeiPatches.size()); + scalar maxDSq(0.0); + forAll(allNeiPatches, i) + { + point pMap; + scalar dSq(VGREAT); + label nearestTriangle; + + point p = bf.centre(points); + meshOctree_.findNearestSurfacePointInRegion + ( + pMap, + dSq, + nearestTriangle, + allNeiPatches[i], + p + ); + + maxDSq = Foam::max(dSq, maxDSq); + + //- calculate normal vectors + vector tn = surf[nearestTriangle].normal(sPoints); + tn /= (mag(tn) + VSMALL); + vector fn = bf.normal(points); + fn /= (mag(fn) + SMALL); + + //- calculate alignment + normalAlignment[i] = mag(tn & fn); + distanceSq[i] = dSq; + } + + scalar maxAlignment(0.0); + forAll(normalAlignment, i) + { + const scalar metric + ( + sqrt(maxDSq / (distanceSq[i] + VSMALL)) * normalAlignment[i] + ); + + if( metric > maxAlignment ) + { + maxAlignment = metric; + newPatch = allNeiPatches[i]; + } + } + + if( (newPatch >= 0) && (newPatch != facePatch_[bfI]) ) + { + newBoundaryPatches[bfI] = newPatch; + ++nCorrected; + } + } + + reduce(nCorrected, sumOp<label>()); + + if( nCorrected ) + { + changed = true; + + //- transfer the new patches back + facePatch_.transfer(newBoundaryPatches); + } + } while( (nCorrected != 0) && (++nIterations < 5) ); + + return changed; +} + +void edgeExtractor::findEdgeCandidates() +{ + const triSurf& surface = meshOctree_.surface(); + const vectorField& sp = surface.points(); + const VRWGraph& facetEdges = surface.facetEdges(); + const VRWGraph& edgeFacets = surface.edgeFacets(); + + const triSurfacePartitioner& partitioner = this->partitioner(); + + const meshSurfaceEngine& mse = this->surfaceEngine(); + const pointFieldPMG& points = mse.points(); + const labelList& bPoints = mse.boundaryPoints(); + const labelList& bp = mse.bp(); + const VRWGraph& faceEdges = mse.faceEdges(); + + Map<label> otherFacePatch; + findOtherFacePatchesParallel(otherFacePatch, &facePatch_); + labelLongList faceCandidates; + findFaceCandidates(faceCandidates, &facePatch_, &otherFacePatch); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) \ + if( faceCandidates.size() > 100 ) + # endif + forAll(faceCandidates, fcI) + { + const label bfI = faceCandidates[fcI]; + + forAllRow(faceEdges, bfI, i) + { + const label eI = faceEdges(bfI, i); + edgeType_[eI] |= CANDIDATE; + } + } + + //- find distances of all vertices supporting CANDIDATE edges + //- from feature edges separating various patches + const VRWGraph& pEdges = mse.boundaryPointEdges(); + const edgeList& edges = mse.edges(); + + List<List<labelledScalar> > featureEdgesNearPoint(bPoints.size()); + + DynList<label> containedTriangles; + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) private(containedTriangles) + # endif + forAll(pEdges, bpI) + { + // TODO rewrite for execution on distributed machines + bool check(false); + forAllRow(pEdges, bpI, peI) + { + const label eI = pEdges(bpI, peI); + + if( edgeType_[eI] & CANDIDATE ) + { + check = true; + break; + } + } + + if( check ) + { + //- check the squared distance from the nearest feature edge + scalar rSq(0.0); + forAllRow(pEdges, bpI, peI) + { + const label eI = pEdges(bpI, peI); + const edge& e = edges[eI]; + const scalar dSq = magSqr(points[e.start()] - points[e.end()]); + + rSq = Foam::max(rSq, dSq); + } + + rSq *= 2.0; + const scalar r = Foam::sqrt(rSq); + + //- create a boundaing box used for searching neighbour edges + const point& p = points[bPoints[bpI]]; + boundBox bb(p - point(r, r, r), p + point(r, r, r)); + + //- find the surface triangles in the vicinity of the point + //- check for potential feature edges + containedTriangles.clear(); + meshOctree_.findTrianglesInBox(bb, containedTriangles); + + DynList<label> featureEdgeCandidates; + + forAll(containedTriangles, ctI) + { + const label tI = containedTriangles[ctI]; + + forAllRow(facetEdges, tI, feI) + { + const label seI = facetEdges(tI, feI); + + if( edgeFacets.sizeOfRow(seI) == 2 ) + { + const label p0 = surface[edgeFacets(seI, 0)].region(); + const label p1 = surface[edgeFacets(seI, 1)].region(); + + if( p0 != p1 ) + { + featureEdgeCandidates.appendIfNotIn(seI); + } + } + else + { + featureEdgeCandidates.appendIfNotIn(seI); + } + } + } + + //- check the distance of the vertex from the candidates + List<labelledScalar>& featureEdgeDistances = + featureEdgesNearPoint[bpI]; + featureEdgeDistances.setSize(featureEdgeCandidates.size()); + forAll(featureEdgeCandidates, i) + { + const label seI = featureEdgeCandidates[i]; + + const point s = sp[edges[seI].start()]; + const point e = sp[edges[seI].end()]; + const point np = help::nearestPointOnTheEdgeExact(s, e, p); + + featureEdgeDistances[i] = labelledScalar(seI, magSqr(np - p)); + } + + //- find nearest edges + sort(featureEdgeDistances); + } + } + + //- start post-processing gathered data + const labelList& edgeGroup = partitioner.edgeGroups(); + + List<List<labelledScalar> > edgeGroupAndWeights(edges.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) \ + if( edges.size() > 1000 ) + # endif + forAll(edgeType_, edgeI) + { + if( edgeType_[edgeI] & CANDIDATE ) + { + const edge& e = edges[edgeI]; + + const List<labelledScalar>& sc = + featureEdgesNearPoint[bp[e.start()]]; + const List<labelledScalar>& ec = + featureEdgesNearPoint[bp[e.end()]]; + + //- find the feature-edge partition for which the sum of + //- node weights is minimal. + DynList<labelledScalar> weights; + forAll(sc, i) + { + const label sPart = edgeGroup[sc[i].scalarLabel()]; + + forAll(ec, j) + { + const label ePart = edgeGroup[ec[j].scalarLabel()]; + + if( (sPart >= 0) && (sPart == ePart) ) + { + weights.append + ( + labelledScalar + ( + sPart, + sc[i].value() + ec[j].value() + ) + ); + } + } + } + + //- store the data + edgeGroupAndWeights[edgeI].setSize(weights.size()); + forAll(edgeGroupAndWeights[edgeI], epI) + edgeGroupAndWeights[edgeI][epI] = weights[epI]; + + //- sort the data according to the weights + stableSort(edgeGroupAndWeights[edgeI]); + } + } + + Info << "Edge partitions and weights " << edgeGroupAndWeights << endl; +} + +void edgeExtractor::findNeiPatches +( + const label bfI, + const Map<label>& otherProcPatch, + DynList<label>& neiPatches +) const +{ + const meshSurfaceEngine& mse = surfaceEngine(); + + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + neiPatches.setSize(faceEdges.sizeOfRow(bfI)); + + forAllRow(faceEdges, bfI, feI) + { + const label beI = faceEdges(bfI, feI); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + label nei = edgeFaces(beI, 0); + if( nei == bfI ) + nei = edgeFaces(beI, 1); + + neiPatches[feI] = facePatch_[nei]; + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + neiPatches[feI] = otherProcPatch[beI]; + } + } +} + +scalar edgeExtractor::calculateAlignmentForEdge +( + const label beI, + const label patch0, + const label patch1 +) const +{ + scalar val(0.0); + + DynList<label> patches(2); + patches[0] = patch0; + patches[1] = patch1; + + const pointFieldPMG& points = surfaceEnginePtr_->mesh().points(); + + const edge& e = surfaceEnginePtr_->edges()[beI]; + const point& ps = points[e.start()]; + const point& pe = points[e.end()]; + + vector ev = e.vec(points); + const scalar magE = mag(ev) + VSMALL; + ev /= magE; + + point mps, mpe; + scalar dSqS, dSqE; + + meshOctree_.findNearestPointToPatches(mps, dSqS, ps, patches); + meshOctree_.findNearestPointToPatches(mpe, dSqE, pe, patches); + + vector fv = mpe - mps; + fv /= (mag(fv) + VSMALL); + + val = 0.5 * (1.0 + (ev & fv)); + + val = min(val, 1.0); + val = max(val, 0.0); + + return val; +} + +scalar edgeExtractor::calculateDeformationMetricForEdge +( + const label beI, + const label patch0, + const label patch1 +) const +{ + scalar val(0.0); + + DynList<label> patches(2); + patches[0] = patch0; + patches[1] = patch1; + + const pointFieldPMG& points = surfaceEnginePtr_->mesh().points(); + + const edge& e = surfaceEnginePtr_->edges()[beI]; + const point& ps = points[e.start()]; + const point& pe = points[e.end()]; + + vector ev = e.vec(points); + const scalar magE = mag(ev) + VSMALL; + ev /= magE; + + point mps, mpe; + scalar dSqS, dSqE; + + meshOctree_.findNearestPointToPatches(mps, dSqS, ps, patches); + meshOctree_.findNearestPointToPatches(mpe, dSqE, pe, patches); + + vector fv = mpe - mps; + fv /= (mag(fv) + VSMALL); + + scalar c = min(fv & ev, 1.0); + c = max(-1.0, c); + const scalar angle = acos(c); + + val = 0.5 * (sqrt(dSqS) + sqrt(dSqE)) + magE * angle; + + return val; +} + +scalar edgeExtractor::calculateDeformationMetricForFace +( + const label bfI, + const DynList<label>& neiPatches, + const label facePatch +) const +{ + scalar Enorm(0.0); + + const VRWGraph& faceEdges = surfaceEnginePtr_->faceEdges(); + + if( neiPatches.size() != faceEdges.sizeOfRow(bfI) ) + { + FatalErrorIn + ( + "scalar edgeExtractor::calculateDeformationMetricForFace" + "(const label, const DynList<label>&, const label) const" + ) << "Number of neiPatches and faceEdge does not match for face " + << bfI << abort(FatalError); + } + + const label patch0 = facePatch == -1 ? facePatch_[bfI] : facePatch; + + forAllRow(faceEdges, bfI, i) + { + const label beI = faceEdges(bfI, i); + + if( neiPatches[i] == patch0 ) + continue; + + Enorm += calculateDeformationMetricForEdge(beI, patch0, neiPatches[i]); + } + + return Enorm; +} + +bool edgeExtractor::checkConcaveEdgeCells() +{ + bool changed(false); + + const triSurf& surf = meshOctree_.surface(); + const VRWGraph& edgeFacets = surf.edgeFacets(); + + const pointFieldPMG& points = mesh_.points(); + const faceListPMG& faces = mesh_.faces(); + const cellListPMG& cells = mesh_.cells(); + const label bndStartFace = mesh_.boundaries()[0].patchStart(); + + const meshSurfaceEngine& mse = this->surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& bp = mse.bp(); + const labelList& faceCells = mse.faceOwners(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + //- analyse the surface mesh and find out which edges are concave or convex + const triSurfaceClassifyEdges& edgeClassifier = this->edgeClassifier(); + const List<direction>& edgeType = edgeClassifier.edgeTypes(); + + //- create a copy of facePatch array for local modifications + labelList newBoundaryPatches(facePatch_); + + //- start checking the surface of the mesh + label nChanged; + + boolList patchPoint(mse.boundaryPoints().size(), false); + + do + { + nChanged = 0; + + //- check which surface points are surrounded by boundary faces + //- in the same surface patch + markPatchPoints(patchPoint); + + //- check whether exist edges of a single cell which shall be projected + //- onto a concave edge + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) reduction(+ : nChanged) + # endif + forAll(edgeType_, beI) + { + if( !(edgeType_[beI] & SINGLECELLEDGE) ) + continue; + + //- check if all faces are assigned to the same patch + const label firstPatch = newBoundaryPatches[edgeFaces(beI, 0)]; + const label secondPatch = newBoundaryPatches[edgeFaces(beI, 1)]; + + if( firstPatch == secondPatch ) + continue; + + const cell& c = cells[faceCells[edgeFaces(beI, 0)]]; + + //- find edges within the bounding box determined by the cell + point pMin(VGREAT, VGREAT, VGREAT); + point pMax(-VGREAT, -VGREAT, -VGREAT); + forAll(c, fI) + { + const face& f = faces[c[fI]]; + + forAll(f, pI) + { + pMin = Foam::min(pMin, points[f[pI]]); + pMax = Foam::max(pMax, points[f[pI]]); + } + } + + const point cc = 0.5 * (pMin + pMax); + const point diff = pMax - pMin; + boundBox bb(cc-diff, cc+diff); + DynList<label> containedEdges; + meshOctree_.findEdgesInBox(bb, containedEdges); + + //- check if there exists concave edges boundaing patches + //- assigned to boundary faces of the current cell + forAll(containedEdges, ceI) + { + const label eI = containedEdges[ceI]; + + if( edgeFacets.sizeOfRow(eI) != 2 ) + continue; + if( !(edgeType[eI] & triSurfaceClassifyEdges::FEATUREEDGE) ) + continue; + + if( edgeType[eI] & triSurfaceClassifyEdges::CONCAVEEDGE ) + { + const label patch0 = surf[edgeFacets(eI, 0)].region(); + const label patch1 = surf[edgeFacets(eI, 1)].region(); + + if + ( + ((firstPatch == patch0) && (secondPatch == patch1)) || + ((firstPatch == patch1) && (secondPatch == patch0)) + ) + { + DynList<DynList<label>, 2> facesInPatch; + facesInPatch.setSize(2); + + DynList<label, 2> nFacesInPatch; + nFacesInPatch.setSize(2); + nFacesInPatch = 0; + + DynList<bool, 2> hasPatchPoints; + hasPatchPoints.setSize(2); + hasPatchPoints = false; + + forAll(c, fI) + { + if( c[fI] < bndStartFace ) + continue; + + const label bfI = c[fI] - bndStartFace; + const face& bf = bFaces[bfI]; + + if( newBoundaryPatches[bfI] == patch1 ) + { + facesInPatch[1].append(bfI); + ++nFacesInPatch[1]; + + forAll(bf, pI) + { + if( patchPoint[bp[bf[pI]]] ) + hasPatchPoints[1] = true; + } + } + else if( newBoundaryPatches[bfI] == patch0 ) + { + facesInPatch[0].append(bfI); + ++nFacesInPatch[0]; + + forAll(bf, pI) + { + if( patchPoint[bp[bf[pI]]] ) + hasPatchPoints[0] = true; + } + } + } + + if( nFacesInPatch[1] > nFacesInPatch[0] ) + { + //- there exist more faces in patch 1 + //- assign all boundary faces to the same patch + forAll(facesInPatch[0], i) + newBoundaryPatches[facesInPatch[0][i]] = patch1; + ++nChanged; + break; + } + else if( nFacesInPatch[0] > nFacesInPatch[1] ) + { + //- there exist more faces in patch 0 + //- assign all boundary faces to the same patch + forAll(facesInPatch[1], i) + newBoundaryPatches[facesInPatch[1][i]] = patch0; + ++nChanged; + break; + } + else + { + if( hasPatchPoints[0] && !hasPatchPoints[1] ) + { + //- transfer all faces to patch 1 + forAll(facesInPatch[0], i) + newBoundaryPatches[facesInPatch[0][i]] = + patch1; + ++nChanged; + break; + } + else if( !hasPatchPoints[0] && hasPatchPoints[1] ) + { + //- transfer all faces to patch 0 + forAll(facesInPatch[1], i) + newBoundaryPatches[facesInPatch[1][i]] = + patch0; + ++nChanged; + break; + } + else + { + //- just transfer all faces to the same patch + forAll(facesInPatch[1], i) + newBoundaryPatches[facesInPatch[1][i]] = + patch0; + ++nChanged; + break; + } + } + } + } + } + } + + if( Pstream::parRun() ) + reduce(nChanged, sumOp<label>()); + + if( nChanged ) + changed = true; + + } while( nChanged != 0 ); + + //- transfer the information back to facePatch + facePatch_.transfer(newBoundaryPatches); + + return changed; +} + +bool edgeExtractor::checkFacePatchesTopology() +{ + bool changed(false); + + const meshSurfaceEngine& mse = this->surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& bp = mse.bp(); + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + label nCorrected; + Map<label> otherProcNewPatch; + + label nIter(0); + do + { + # ifdef DEBUGEdgeExtractor + { + const triSurf* surfPtr = surfaceWithPatches(); + surfPtr->writeSurface + ( + "surfaceTopologyIter_"+help::scalarToText(nIter)+".stl" + ); + delete surfPtr; + } + # endif + + nCorrected = 0; + + //- allocate a copy of boundary patches + labelList newBoundaryPatches(facePatch_); + + //- check whether there exist situations where a boundary face + //- is surrounded by more faces in different patches than the + //- faces in the current patch + if( Pstream::parRun() ) + { + findOtherFacePatchesParallel + ( + otherProcNewPatch, + &facePatch_ + ); + } + + //- find the faces which have neighbouring faces in other patches + labelLongList candidates; + findFaceCandidates(candidates, &facePatch_, &otherProcNewPatch); + + //- go through the list of faces and check if they shall remain + //- in the current patch + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) \ + reduction(+ : nCorrected) + # endif + forAll(candidates, i) + { + const label bfI = candidates[i]; + const face& bf = bFaces[bfI]; + + //- do not change patches of faces where all points are mapped + //- onto the same patch + bool allInSamePatch(true); + forAll(bf, pI) + if( pointPatch_[bp[bf[pI]]] != facePatch_[bfI] ) + { + allInSamePatch = false; + break; + } + + if( allInSamePatch ) + continue; + + DynList<label> allNeiPatches; + DynList<label> neiPatches; + neiPatches.setSize(faceEdges.sizeOfRow(bfI)); + + forAllRow(faceEdges, bfI, eI) + { + const label beI = faceEdges(bfI, eI); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + label fNei = edgeFaces(beI, 0); + if( fNei == bfI ) + fNei = edgeFaces(faceEdges(bfI, eI), 1); + + allNeiPatches.appendIfNotIn(facePatch_[fNei]); + neiPatches[eI] = facePatch_[fNei]; + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + allNeiPatches.appendIfNotIn(otherProcNewPatch[beI]); + neiPatches[eI] = otherProcNewPatch[beI]; + } + } + + //- do not modify faces with all neighbours in the same patch + if + ( + (allNeiPatches.size() == 1) && + (allNeiPatches[0] == facePatch_[bfI]) + ) + continue; + + //- check whether there exist edges which are more suitable for + //- projection onto feature edges than the currently selected ones + label newPatch(-1); + + //- check if some faces have to be distributed to another patch + //- in order to reduce the number of feature edges + Map<label> nNeiInPatch(allNeiPatches.size()); + forAll(allNeiPatches, i) + nNeiInPatch.insert(allNeiPatches[i], 0); + forAll(neiPatches, eI) + ++nNeiInPatch[neiPatches[eI]]; + + newPatch = -1; + label nNeiEdges(0); + forAllConstIter(Map<label>, nNeiInPatch, it) + { + if( it() > nNeiEdges ) + { + newPatch = it.key(); + nNeiEdges = it(); + } + else if + ( + (it() == nNeiEdges) && (it.key() == facePatch_[bfI]) + ) + { + newPatch = it.key(); + } + } + + //- do not swap in case the + if( (newPatch < 0) || (newPatch == facePatch_[bfI]) ) + continue; + + //- check whether the edges shared ith the neighbour patch form + //- a singly linked chain + DynList<bool> sharedEdge; + sharedEdge.setSize(bFaces[bfI].size()); + sharedEdge = false; + + forAll(neiPatches, eI) + if( neiPatches[eI] == newPatch ) + sharedEdge[eI] = true; + + if( help::areElementsInChain(sharedEdge) ) + { + //- change the patch to the newPatch + ++nCorrected; + newBoundaryPatches[bfI] = newPatch; + } + } + + //- eavluate the new situation and ensure that no oscillation occur + reduce(nCorrected, sumOp<label>()); + if( nCorrected ) + { + faceEvaluator faceEvaluator(*this); + + faceEvaluator.setNewBoundaryPatches(newBoundaryPatches); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(candidates, i) + { + const label bfI = candidates[i]; + + const label bestPatch = + faceEvaluator.bestPatchAfterModification(bfI); + + newBoundaryPatches[bfI] = bestPatch; + } + } + + if( nCorrected ) + { + changed = true; + + //- transfer the new patches back + facePatch_.transfer(newBoundaryPatches); + } + + } while( nCorrected != 0 && (nIter++ < 30) ); + + return changed; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +namespace featureEdgeHelpers +{ + +class featureEdgesNeiOp +{ + // Private data + //- reference to meshSurfaceEngine + const meshSurfaceEngine& mse_; + + //- refence to a list holding information which edges are feature edges + const boolList& isFeatureEdge_; + + //- number of feature edges at a surface point + labelList nFeatureEdgesAtPoint_; + + // Private member functions + //- calculate the number of feature edges connected to a surface vertex + void calculateNumberOfEdgesAtPoint() + { + const labelList& bp = mse_.bp(); + const edgeList& edges = mse_.edges(); + + nFeatureEdgesAtPoint_.setSize(mse_.boundaryPoints().size()); + nFeatureEdgesAtPoint_ = 0; + + forAll(isFeatureEdge_, edgeI) + { + if( !isFeatureEdge_[edgeI] ) + continue; + + const edge& e = edges[edgeI]; + ++nFeatureEdgesAtPoint_[bp[e.start()]]; + ++nFeatureEdgesAtPoint_[bp[e.end()]]; + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = + mse_.globalToLocalBndPointAddressing(); + const DynList<label>& neiProcs = mse_.bpNeiProcs(); + const VRWGraph& bpAtProcs = mse_.bpAtProcs(); + + std::map<label, DynList<labelPair> > exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + //- fill the data from sending + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelPair(it.key(), nFeatureEdgesAtPoint_[bpI]) + ); + } + } + + //- exchange the data between the procesors + LongList<labelPair> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelPair& lp = receivedData[i]; + + nFeatureEdgesAtPoint_[globalToLocal[lp.first()]] += + lp.second(); + } + } + } + +public: + + featureEdgesNeiOp + ( + const meshSurfaceEngine& mse, + const boolList& isFeatureEdge + ) + : + mse_(mse), + isFeatureEdge_(isFeatureEdge), + nFeatureEdgesAtPoint_() + { + calculateNumberOfEdgesAtPoint(); + } + + label size() const + { + return isFeatureEdge_.size(); + } + + void operator()(const label beI, DynList<label>& neighbourEdges) const + { + neighbourEdges.clear(); + + const VRWGraph& bpEdges = mse_.boundaryPointEdges(); + const labelList& bp = mse_.bp(); + const edgeList& edges = mse_.edges(); + + const edge& e = edges[beI]; + + const label bps = bp[e.start()]; + const label bpe = bp[e.end()]; + + if( nFeatureEdgesAtPoint_[bps] == 2 ) + { + forAllRow(bpEdges, bps, peI) + { + const label beJ = bpEdges(bps, peI); + + if( (beJ == beI) || !isFeatureEdge_[beJ] ) + continue; + + neighbourEdges.append(beJ); + } + } + + if( nFeatureEdgesAtPoint_[bpe] == 2 ) + { + forAllRow(bpEdges, bpe, peI) + { + const label beJ = bpEdges(bpe, peI); + + if( (beJ == beI) || !isFeatureEdge_[beJ] ) + continue; + + neighbourEdges.append(beJ); + } + } + } + + template<class labelListType> + void collectGroups + ( + std::map<label, DynList<label> >& neiGroups, + const labelListType& elementInGroup, + const DynList<label>& localGroupLabel + ) const + { + const Map<label>& globalToLocal = mse_.globalToLocalBndPointAddressing(); + const VRWGraph& bpAtProcs = mse_.bpAtProcs(); + const VRWGraph& bpEdges = mse_.boundaryPointEdges(); + + const DynList<label>& neiProcs = mse_.beNeiProcs(); + + std::map<label, DynList<labelPair> > exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + if( nFeatureEdgesAtPoint_[bpI] != 2 ) + continue; + + forAllRow(bpEdges, bpI, i) + { + const label beI = bpEdges(bpI, i); + + if( !isFeatureEdge_[beI] ) + continue; + + const label groupI = elementInGroup[beI]; + + forAllRow(bpAtProcs, bpI, ppI) + { + const label neiProc = bpAtProcs(bpI, ppI); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelPair(it.key(), localGroupLabel[groupI]) + ); + } + } + } + + LongList<labelPair> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelPair& lp = receivedData[i]; + const label groupI = elementInGroup[globalToLocal[lp.first()]]; + + DynList<label>& ng = neiGroups[localGroupLabel[groupI]]; + + //- store the connection over the inter-processor boundary + ng.appendIfNotIn(lp.second()); + } + } +}; + +class featureEdgesSelOp +{ + // Private data + //- reference to a list holding information which edge is afeture edge + const boolList& isFeatureEdge_; + +public: + + featureEdgesSelOp(const boolList& isFeatureEdge) + : + isFeatureEdge_(isFeatureEdge) + {} + + bool operator()(const label beI) const + { + return isFeatureEdge_[beI]; + } +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +} // End namespace featureEdgeHelpers + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +bool edgeExtractor::checkFacePatchesGeometry() +{ + bool changed(false); + + const meshSurfaceEngine& mse = this->surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& bp = mse.bp(); + + //- allocate a copy of boundary patches + labelList newBoundaryPatches(facePatch_.size()); + + label nCorrected; + Map<label> otherProcNewPatch; + + boolList activePoints(bPoints.size(), true); + labelLongList activePointLabel(bPoints.size()); + forAll(bPoints, bpI) + activePointLabel[bpI] = bpI; + + label iter(0); + + do + { + # ifdef DEBUGEdgeExtractor + { + const triSurf* surfPtr = surfaceWithPatches(); + surfPtr->writeSurface + ( + "surfaceIter_"+help::scalarToText(iter)+".stl" + ); + delete surfPtr; + } + # endif + + //- create feature edges and corners information + meshSurfacePartitioner mPart(mse, facePatch_); + + //- project vertices onto the surface mesh + meshSurfaceMapper(mPart, meshOctree_).mapVerticesOntoSurfacePatches + ( + activePointLabel + ); + + //- stop after a certain number of iterations + if( iter++ > 20 ) + break; + + //- check if there exist any inverted faces + meshSurfaceCheckInvertedVertices surfCheck(mse, activePoints); + const labelHashSet& invertedPoints = surfCheck.invertedVertices(); + + if( returnReduce(invertedPoints.size(), sumOp<label>()) == 0 ) + return false; + + WarningIn + ( + "void edgeExtractor::extractEdges()" + ) << "Found " << invertedPoints.size() + << " points with inverted surface normals. Getting rid of them..." + << endl; + + //- untangle the surface + activePointLabel.clear(); + forAllConstIter(labelHashSet, invertedPoints, it) + activePointLabel.append(bp[it.key()]); + + //- update active points + activePoints = false; + forAll(activePointLabel, i) + activePoints[activePointLabel[i]] = true; + + //- untangle the surface + meshSurfaceOptimizer mso(*surfaceEnginePtr_, meshOctree_); + mso.untangleSurface(activePointLabel, 1); + + nCorrected = 0; + newBoundaryPatches = facePatch_; + + //- check whether there exist situations where a boundary face + //- is surrounded by more faces in different patches than the + //- faces in the current patch + if( Pstream::parRun() ) + { + findOtherFacePatchesParallel + ( + otherProcNewPatch, + &facePatch_ + ); + } + + //- find the faces which have neighbouring faces in other patches + labelLongList candidates; + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + if( invertedPoints.found(bf[pI]) ) + { + candidates.append(bfI); + break; + } + } + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 5) reduction(+ : nCorrected) + # endif + forAll(candidates, i) + { + const label bfI = candidates[i]; + + DynList<label> neiPatches; + findNeiPatches(bfI, otherProcNewPatch, neiPatches); + + DynList<label> allNeiPatches; + forAll(neiPatches, i) + allNeiPatches.appendIfNotIn(neiPatches[i]); + + //- check the deformation energy and find the minimum energy which + //- can be achieved by switching face patch + scalar minE(VGREAT); + label minEPatch(-1); + DynList<scalar> Enorm(allNeiPatches.size()); + forAll(allNeiPatches, i) + { + Enorm[i] = + calculateDeformationMetricForFace + ( + bfI, + neiPatches, + allNeiPatches[i] + ); + + if( Enorm[i] < minE ) + { + minE = Enorm[i]; + minEPatch = allNeiPatches[i]; + } + } + + if( minEPatch != facePatch_[bfI] ) + { + newBoundaryPatches[bfI] = minEPatch; + ++nCorrected; + } + } + + //- check if any faces are re-assigned to some other patch + reduce(nCorrected, sumOp<label>()); + if( nCorrected == 0 ) + break; + + //- update faceEvaluator with information after patches have been + //- altered. It blocks chaning of patches if it causes oscillations + faceEvaluator facePatchEvaluator(*this); + facePatchEvaluator.setNewBoundaryPatches(newBoundaryPatches); + + //- compare face patches before and after + //- disallow modification which may trigger oscillating behaviour + labelHashSet changedFaces; + forAll(newBoundaryPatches, bfI) + { + if( newBoundaryPatches[bfI] != facePatch_[bfI] ) + { + const label patchI = + facePatchEvaluator.bestPatchAfterModification(bfI); + newBoundaryPatches[bfI] = patchI; + + if( patchI != facePatch_[bfI] ) + changedFaces.insert(bfI); + } + } + + nCorrected = changedFaces.size(); + + reduce(nCorrected, sumOp<label>()); + + if( nCorrected ) + { + changed = true; + facePatch_ = newBoundaryPatches; + } + + } while( nCorrected != 0 ); + + return changed; +} + +void edgeExtractor::projectDeterminedFeatureVertices() +{ + List<DynList<label, 5> > pointPatches; + pointPatches.setSize(pointValence_.size()); + + const meshSurfaceEngine& mse = surfaceEngine(); + const pointFieldPMG& points = mse.mesh().points(); + const labelList& bPoints = mse.boundaryPoints(); + const labelList& bp = mse.bp(); + const faceList::subList& bFaces = mse.boundaryFaces(); + meshOctree_.surface().pointEdges(); + + //- calculate patches for each point + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + pointPatches[bp[bf[pI]]].appendIfNotIn(facePatch_[bfI]); + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = + mse.globalToLocalBndPointAddressing(); + const VRWGraph& bpAtProcs = mse.bpAtProcs(); + const DynList<label>& bpNeiProcs = mse.bpNeiProcs(); + + std::map<label, LongList<labelPair> > exchangeData; + forAll(bpNeiProcs, i) + exchangeData.insert + ( + std::make_pair(bpNeiProcs[i], LongList<labelPair>()) + ); + + //- collect the data distributed to others + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + const DynList<label, 5>& pPatches = pointPatches[bpI]; + + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + LongList<labelPair>& data = exchangeData[neiProc]; + + forAll(pPatches, ppI) + data.append(labelPair(it.key(), pPatches[ppI])); + } + } + + //- exchange information + LongList<labelPair> receivedData; + help::exchangeMap(exchangeData, receivedData); + + //- unify the data + forAll(receivedData, i) + { + const labelPair& lp = receivedData[i]; + + pointPatches[globalToLocal[lp.first()]].appendIfNotIn(lp.second()); + } + } + + meshSurfaceEngineModifier surfMod(mse); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 10) + # endif + forAll(pointPatches, bpI) + { + if( pointPatches[bpI].size() < 2 ) + continue; + + const DynList<label> pPatches = pointPatches[bpI]; + + const point& p = points[bPoints[bpI]]; + + //- find the nearest object on the surface mesh + point newP; + scalar dSqExact; + if( pPatches.size() == 2 ) + { + label nse; + meshOctree_.findNearestEdgePoint(newP, dSqExact, nse, p, pPatches); + } + else + { + label nsp; + meshOctree_.findNearestCorner(newP, dSqExact, nsp, p, pPatches); + } + + //- find the nearest object in an iterative procedure + point pp(p); + for(label iterI=0;iterI<20;++iterI) + { + point inp(vector::zero); + + forAll(pPatches, i) + { + point np; + scalar dSq; + label nt; + + meshOctree_.findNearestSurfacePointInRegion + ( + np, + dSq, + nt, + pPatches[i], + pp + ); + + inp += np; + } + + inp /= pPatches.size(); + const scalar currDSq = magSqr(inp - pp); + pp = inp; + + if( currDSq < 1e-2 * dSqExact ) + break; + } + + //- check if the exact position of the corner is further away + //- than the iteratively found object + if( dSqExact > 1.1 * magSqr(pp - p) ) + newP = pp; + + surfMod.moveBoundaryVertexNoUpdate(bpI, newP); + } + + surfMod.syncVerticesAtParallelBoundaries(); + surfMod.updateGeometry(); +} + +bool edgeExtractor::untangleSurface() +{ + bool changed(false); + + meshSurfaceEngine& mse = + const_cast<meshSurfaceEngine&>(this->surfaceEngine()); + meshSurfaceOptimizer optimizer(mse, meshOctree_); + changed = optimizer.untangleSurface(); + + return changed; +} + +void edgeExtractor::extractEdges() +{ + distributeBoundaryFaces(); + + distributeBoundaryFacesNormalAlignment(); + + # ifdef DEBUGEdgeExtractor + const triSurf* sPtr = surfaceWithPatches(); + sPtr->writeSurface("initialDistributionOfPatches.stl"); + deleteDemandDrivenData(sPtr); + # endif + + Info << "Starting topological adjustment of patches" << endl; + if( checkFacePatchesTopology() ) + { + Info << "Finished topological adjustment of patches" << endl; + + # ifdef DEBUGEdgeExtractor + Info << "Changes due to face patches" << endl; + fileName sName("checkFacePatches"+help::scalarToText(nIter)+".stl"); + sPtr = surfaceWithPatches(); + sPtr->writeSurface(sName); + deleteDemandDrivenData(sPtr); + # endif + } + else + { + Info << "No topological adjustment was needed" << endl; + } + + Info << "Starting geometrical adjustment of patches" << endl; + if( checkFacePatchesGeometry() ) + { + Info << "Finished geometrical adjustment of patches" << endl; + } + else + { + Info << "No geometrical adjustment was needed" << endl; + } + +// updateMeshPatches(); +// mesh_.write(); +// returnReduce(1, sumOp<label>()); +// ::exit(0); + + # ifdef DEBUGEdgeExtractor + const triSurf* sPtr = surfaceWithPatches(); + sPtr->writeSurface("finalDistributionOfPatches.stl"); + deleteDemandDrivenData(sPtr); + # endif +} + +const triSurf* edgeExtractor::surfaceWithPatches() const +{ + //- allocate the memory for the surface mesh + triSurf* surfPtr = new triSurf(); + + //- surface of the volume mesh + const meshSurfaceEngine& mse = surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& bp = mse.bp(); + const pointFieldPMG& points = mesh_.points(); + + //- modifier of the new surface mesh + triSurfModifier surfModifier(*surfPtr); + surfModifier.patchesAccess() = meshOctree_.surface().patches(); + pointField& sPts = surfModifier.pointsAccess(); + sPts.setSize(mse.boundaryPoints().size()); + + //- copy points + forAll(bp, pointI) + { + if( bp[pointI] < 0 ) + continue; + + sPts[bp[pointI]] = points[pointI]; + } + + //- create the triangulation of the volume mesh surface + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + labelledTri tri; + tri.region() = facePatch_[bfI]; + tri[0] = bp[bf[0]]; + + for(label i=bf.size()-2;i>0;--i) + { + tri[1] = bp[bf[i]]; + tri[2] = bp[bf[i+1]]; + + surfPtr->appendTriangle(tri); + } + } + + return surfPtr; +} + +const triSurf* edgeExtractor::surfaceWithPatches(const label bpI) const +{ + //- allocate the memory for the surface mesh + triSurf* surfPtr = new triSurf(); + + //- surface of the volume mesh + const meshSurfaceEngine& mse = surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const VRWGraph& pFaces = mse.pointFaces(); + const pointFieldPMG& points = mesh_.points(); + + //- modifier of the new surface mesh + triSurfModifier surfModifier(*surfPtr); + surfModifier.patchesAccess() = meshOctree_.surface().patches(); + pointField& sPts = surfModifier.pointsAccess(); + + //- create the triangulation of the volume mesh surface + labelLongList newPointLabel(points.size(), -1); + label nPoints(0); + forAllRow(pFaces, bpI, pfI) + { + const label bfI = pFaces(bpI, pfI); + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + if( newPointLabel[bf[pI]] == -1 ) + newPointLabel[bf[pI]] = nPoints++; + + labelledTri tri; + tri.region() = facePatch_[bfI]; + tri[0] = newPointLabel[bf[0]]; + + for(label i=bf.size()-2;i>0;--i) + { + tri[1] = newPointLabel[bf[i]]; + tri[2] = newPointLabel[bf[i+1]]; + + surfPtr->appendTriangle(tri); + } + } + + //- copy points + sPts.setSize(nPoints); + forAll(newPointLabel, pointI) + if( newPointLabel[pointI] != -1 ) + { + sPts[newPointLabel[pointI]] = points[pointI]; + } + + return surfPtr; +} + +void edgeExtractor::updateMeshPatches() +{ + const triSurf& surface = meshOctree_.surface(); + const label nPatches = surface.patches().size(); + + const meshSurfaceEngine& mse = this->surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& faceOwner = mse.faceOwners(); + + wordList patchNames(nPatches); + VRWGraph newBoundaryFaces; + labelLongList newBoundaryOwners(bFaces.size()); + labelLongList newBoundaryPatches(bFaces.size()); + + //- set patchNames + forAll(surface.patches(), patchI) + patchNames[patchI] = surface.patches()[patchI].name(); + + //- append boundary faces + forAll(bFaces, bfI) + { + newBoundaryFaces.appendList(bFaces[bfI]); + newBoundaryOwners[bfI] = faceOwner[bfI]; + newBoundaryPatches[bfI] = facePatch_[bfI]; + } + + //- replace the boundary with the new patches + polyMeshGenModifier(mesh_).replaceBoundary + ( + patchNames, + newBoundaryFaces, + newBoundaryOwners, + newBoundaryPatches + ); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractor.H b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractor.H new file mode 100644 index 0000000000000000000000000000000000000000..4998bc85da2c38860e1c445e47eefd93a9e2514a --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractor.H @@ -0,0 +1,410 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Namespace + edgeExtractor + +Description + A class with a functions used to detect feature edges in the surface + of the volume mesh and to detect the patches to which the boundary + faces belong to + +SourceFiles + +\*---------------------------------------------------------------------------*/ + +#ifndef edgeExtractor_H +#define edgeExtractor_H + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#include "labelList.H" +#include "labelLongList.H" +#include "VRWGraph.H" +#include "boolList.H" +#include "labelledPoint.H" +#include "DynList.H" +#include "Map.H" + +namespace Foam +{ + +// Forward declarations +class polyMeshGen; +class meshSurfaceEngine; +class meshSurfacePartitioner; +class meshOctree; +class triSurf; +class triSurfaceClassifyEdges; +class triSurfacePartitioner; + +/*---------------------------------------------------------------------------*\ + Class edgeExtractor Declaration +\*---------------------------------------------------------------------------*/ + +class edgeExtractor +{ + // Private data + //- reference to the mesh + polyMeshGen& mesh_; + + //- surface engine + mutable meshSurfaceEngine* surfaceEnginePtr_; + + //- reference to the octree + const meshOctree& meshOctree_; + + //- surface mesh partitioner + mutable const triSurfacePartitioner* surfPartitionerPtr_; + + //- classification of edges in the surface mesh + mutable const triSurfaceClassifyEdges* surfEdgeClassificationPtr_; + + //- valence of surface points + labelLongList pointValence_; + + //- patch to which a boundary point is mapped to + labelLongList pointPatch_; + + //- boundary face patch + labelList facePatch_; + + //- number of cells attached to a boundary edge + labelLongList nCellsAtEdge_; + + //- edge classification + LongList<direction> edgeType_; + + //- patches in the vicinity of a face on the surface of the volume mesh + VRWGraph patchesNearFace_; + + //- feature edges in the surface mesh + //- which are candindates for an edge at the surface of the volume mesh + VRWGraph featureEdgesNearEdge_; + + // Private member functions + //- calculate point valence + void calculateValence(); + + //- calculate the number of boundary faces for each cell + void calculateSingleCellEdge(); + + //- search for surface patches in the vicinity of a face + //- at the surface of the volume mesh + void findPatchesNearSurfaceFace(); + + //- search for feature edges in the surface mesh which are + //- in the vicinity of an edge at the surface of the volume mesh + void findFeatureEdgesNearEdge(); + + //- calculate a list of booleans with the following properties: + //- true if all faces at a surface vertex are in the same patch + //- false otherwise + void markPatchPoints(boolList&); + + //- get the surface engine + const meshSurfaceEngine& surfaceEngine() const; + + //- get the surface partitioner + const triSurfacePartitioner& partitioner() const; + + //- get the edge classifier + const triSurfaceClassifyEdges& edgeClassifier() const; + + //- find faces which have faces assigned to other patches + //- as their neighbours + void findFaceCandidates + ( + labelLongList& faceCandidates, + const labelList* facePatchPtr = NULL, + const Map<label>* otherFacePatchPtr = NULL + ) const; + + //- find patches over edges + void findOtherFacePatchesParallel + ( + Map<label>& otherFacePatch, + const labelList* facePatchPtr = NULL + ) const; + + //- find neighbour patches over edges for a boundary face + void findNeiPatches + ( + const label, + const Map<label>&, + DynList<label>& + ) const; + + //- calculate alignment between the boundary edge and a feature edge + //- between the specified patches + scalar calculateAlignmentForEdge + ( + const label beI, + const label patch0, + const label patch1 + ) const; + + //- calculates the deformation energy metric for the boundary edge + //- when it would be constrained to a feature edge between + //- the specified patches + scalar calculateDeformationMetricForEdge + ( + const label beI, + const label patch0, + const label patch1 + ) const; + + //- calculates deformation energy metric for a face + scalar calculateDeformationMetricForFace + ( + const label bfI, + const DynList<label>& neiPatches, + const label facePatch = -1 + ) const; + + //- project face centres on the nearest location at the surface mesh + //- and assign the patch to the patch of the surface element + void distributeBoundaryFaces(); + + //- move faces into the patch with the best alignment + bool distributeBoundaryFacesNormalAlignment(); + + //- go through the boundary faces which have at least one neighour + //- assigned to a different patch and check which of its edges + //- are best candidates to be used as feature edges + void findEdgeCandidates(); + + //- Disallow default bitwise copy construct + edgeExtractor(const edgeExtractor&); + + //- Disallow default bitwise assignment + void operator=(const edgeExtractor&); + + // Private nested classes + + class faceEvaluator + { + // Private data + //- const reference to the parent class + const edgeExtractor& extractor_; + + //- calculated patches of faces over inter-processor boundaries + Map<label> otherFacePatch_; + + //- new status of face patches after re-assigning of patches + const labelList* newBoundaryPatchesPtr_; + + //- calculated patches of faces over inter-processor boundaries + //- after re-assigning of patches + Map<label>* newOtherFacePatchPtr_; + + // Private member functions + //- calculate patches of faces over inter-processor boundaries + void calculateNeiPatchesParallel(); + void calculateNeiPatchesParallelNewPatches(); + + //- find neighbour faces over edges + void neiFacesOverEdges(const label, DynList<label>&) const; + + //- find processors of faces over edges + void neiFacesProcs(const label, DynList<label>&) const; + + //- calculate neighbour patches over edges of a boundary face + void neiPatchesOverEdges + ( + const label bfI, + const labelList& fPatches, + const Map<label>& otherFacePatch, + DynList<label> &neiPatches + ) const; + + //- evaluate new patch for a face based on the number of + //- common edges shared between faces in other patches + static label bestPatchTopological + ( + const DynList<label>& neiPatches, + const label currentPatch + ); + + public: + + // Constructors + //- Construct from edgeExtractor + faceEvaluator(const edgeExtractor&); + + // Destructor + ~faceEvaluator(); + + // Public member functions + //- set the values for new boundary patches + void setNewBoundaryPatches(const labelList& newBoudaryPatches); + + //- calculate neighbour patches over edges of a face + void neiPatchesOverEdges + ( + const label bfI, + DynList<label>& neiPatches + ) const; + + //- return the patch that the face shall be moved to such that + //- the number of feature edges between the two patches + //- is minimised + label bestPatchTopological(const label bfI) const; + + //- return the best patch for a face by comparing the patch + //- before and after modifications to face patches + //- have been made + //- this function checks whether the changes of face patches + //- cause oscillations in the procedure + label bestPatchAfterModification(const label bfI) const; + }; + + class cornerEvaluator + { + // Private data + //- const reference to the parent class + const edgeExtractor& extractor_; + + //- const reference to meshSurfacePartitioner + const meshSurfacePartitioner& partitioner_; + + //- faces attached to points at inter-processor boundaries + std::map<label, DynList<DynList<labelledPoint, 6> > > faceMap_; + std::map<label, DynList<label> > facePatches_; + std::map<label, DynList<label> > faceAtProc_; + + // Private member functions + //- create addressing at inter-processor boundaries + void createParallelAddressing(); + + //- sort faces attached to a boundary point + void sortedFacesAtPoint(const label, DynList<label>&) const; + + public: + + // Constructors + //- construct from edgeExtractor and meshSurfacePartitioner + cornerEvaluator + ( + const edgeExtractor&, + const meshSurfacePartitioner& + ); + + // Destructor + ~cornerEvaluator(); + + // Public member functions + + //- check patches of the faces attached to corners + //- and re-assign the patches such that the mesh undergoes + //- minimum rotation during the projection stage + void improveCorners(labelList& newBoundaryPatches); + }; + + // Private enumerators + + enum edgeClassifier_ + { + NONE = 0, + SINGLECELLEDGE = 1, + FITSATCONVEXEDGE = 2, + FITSATCONCAVEEDGE = 4, + ATTACHEDTOCORNER = 8, + CANDIDATE = 16 + }; + +public: + + // Constructors + + //- Construct from mesh surface and octree + edgeExtractor + ( + polyMeshGen& mesh, + const meshOctree& octree + ); + + + // Destructor + + ~edgeExtractor(); + + // Member Functions + + + //- move vertices in the vicinity of discontinuities towards the + //- the surface mesh by reducing the deviation of the mesh from the + //- input geometry + void moveVerticesTowardsDiscontinuities(const label nIterations = 2); + + //- check if there exist cells at concave feature edges which have more + //- than one face at the boundary and the faces are + //- distributed into patches at the concave edge + bool checkConcaveEdgeCells(); + + //- check and improve the distribution of mesh faces into patches + //- in order to minimize the number of decomposed faces + bool checkFacePatchesTopology(); + + //- checks whether there exist corners which do not exist in the surface + //- mesh, and checks whether the locations of corners in the volume mesh + //- are near the existing counterparts in the surface mesh + bool checkCorners(); + + //- optimise distribution of mesh faces into patches + //- in order to get better geometric quality of the mesh + bool checkFacePatchesGeometry(); + + //- find the nearest points on the surface of the volume mesh + //- to the corners on the surface mesh + bool findCornerCandidates(); + + //- project the estimated corners and edges onto the surface mesh + void projectDeterminedFeatureVertices(); + + //- check and untangle the surface of the volume mesh + bool untangleSurface(); + + //- assemble the above functionality into a workflow + void extractEdges(); + + //- generate a surface mesh and store the created patches + //- this is mainly intended for debugging purposes + const triSurf* surfaceWithPatches() const; + + //- generate a surface mesh constin of facets adjacent to the requested + //- surface point + const triSurf* surfaceWithPatches(const label bpI) const; + + //- update mesh with selected patches + void updateMeshPatches(); +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractorCorners.C b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractorCorners.C new file mode 100644 index 0000000000000000000000000000000000000000..67f8568c8e7d9704be36f5e0f42d0da967061184 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/edgeExtraction/edgeExtractor/edgeExtractorCorners.C @@ -0,0 +1,1809 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "error.H" +#include "polyMeshGenModifier.H" +#include "edgeExtractor.H" +#include "meshSurfaceEngine.H" +#include "meshSurfaceEngineModifier.H" +#include "meshSurfaceOptimizer.H" +#include "meshOctree.H" +#include "triSurf.H" +#include "triSurfModifier.H" +#include "helperFunctions.H" +#include "DynList.H" +#include "labelPair.H" +#include "labelledScalar.H" +#include "labelledPoint.H" +#include "refLabelledPoint.H" +#include "HashSet.H" +#include "triSurfacePartitioner.H" +#include "triSurfaceClassifyEdges.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGEdgeExtractor + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +void edgeExtractor::faceEvaluator::calculateNeiPatchesParallel() +{ + otherFacePatch_.clear(); + + const labelList& fPatches = extractor_.facePatch_; + + if( Pstream::parRun() ) + { + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const Map<label>& otherProc = mse.otherEdgeFaceAtProc(); + const Map<label>& globalToLocal = + mse.globalToLocalBndEdgeAddressing(); + + //- create communication matrix + std::map<label, labelLongList> exchangeData; + const DynList<label>& neiProcs = mse.beNeiProcs(); + forAll(neiProcs, procI) + exchangeData.insert + ( + std::make_pair(neiProcs[procI], labelLongList()) + ); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + if( edgeFaces.sizeOfRow(beI) == 1 ) + { + labelLongList& dts = exchangeData[otherProc[beI]]; + //- send data as follows: + //- 1. global edge label + //- 2. patch of the attached boundary face + dts.append(it.key()); + dts.append(fPatches[edgeFaces(beI, 0)]); + } + } + + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + label counter(0); + while( counter < receivedData.size() ) + { + const label beI = globalToLocal[receivedData[counter++]]; + const label fPatch = receivedData[counter++]; + + otherFacePatch_.insert(beI, fPatch); + } + } +} + +void edgeExtractor::faceEvaluator::calculateNeiPatchesParallelNewPatches() +{ + if( newOtherFacePatchPtr_ ) + return; + + if( !newBoundaryPatchesPtr_ ) + FatalErrorIn + ( + "void edgeExtractor::faceEvaluator::" + "calculateNeiPatchesParallelNewPatches()" + ) << "newBoundaryPatchesPtr_ are NULL" << exit(FatalError); + + newOtherFacePatchPtr_ = new Map<label>(); + Map<label>& otherFacePatch = *newOtherFacePatchPtr_; + + const labelList& fPatches = *newBoundaryPatchesPtr_; + + if( Pstream::parRun() ) + { + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + const Map<label>& otherProc = mse.otherEdgeFaceAtProc(); + const Map<label>& globalToLocal = + mse.globalToLocalBndEdgeAddressing(); + + //- create communication matrix + std::map<label, labelLongList> exchangeData; + const DynList<label>& neiProcs = mse.beNeiProcs(); + forAll(neiProcs, procI) + exchangeData.insert + ( + std::make_pair(neiProcs[procI], labelLongList()) + ); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + if( edgeFaces.sizeOfRow(beI) == 1 ) + { + labelLongList& dts = exchangeData[otherProc[beI]]; + //- send data as follows: + //- 1. global edge label + //- 2. patch of the attached boundary face + dts.append(it.key()); + dts.append(fPatches[edgeFaces(beI, 0)]); + } + } + + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + label counter(0); + while( counter < receivedData.size() ) + { + const label beI = globalToLocal[receivedData[counter++]]; + const label fPatch = receivedData[counter++]; + + otherFacePatch.insert(beI, fPatch); + } + } +} + +void edgeExtractor::faceEvaluator::neiFacesOverEdges +( + const label bfI, + DynList<label>& neiFaces +) const +{ + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + neiFaces.setSize(faceEdges.sizeOfRow(bfI)); + + forAllRow(faceEdges, bfI, feI) + { + const label beI = faceEdges(bfI, feI); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + neiFaces[feI] = edgeFaces(beI, 0); + if( neiFaces[feI] == bfI ) + neiFaces[feI] = edgeFaces(beI, 1); + } + else + { + neiFaces[feI] = -1; + } + } +} + +void edgeExtractor::faceEvaluator::neiFacesProcs +( + const label bfI, + DynList<label>& neiProcs +) const +{ + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + + const VRWGraph& faceEdges = mse.faceEdges(); + + neiProcs.setSize(faceEdges.sizeOfRow(bfI)); + neiProcs = Pstream::myProcNo(); + + if( Pstream::parRun() ) + { + const Map<label>& otherFaceProc = mse.otherEdgeFaceAtProc(); + + forAllRow(faceEdges, bfI, feI) + { + const label beI = faceEdges(bfI, feI); + + const Map<label>::const_iterator it = otherFaceProc.find(beI); + + if( it != otherFaceProc.end() ) + neiProcs[feI] = it(); + } + } +} + +void edgeExtractor::faceEvaluator::neiPatchesOverEdges +( + const label bfI, + const labelList& fPatches, + const Map<label>& otherFacePatch, + DynList<label> &neiPatches +) const +{ + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + neiPatches.setSize(faceEdges.sizeOfRow(bfI)); + + forAllRow(faceEdges, bfI, feI) + { + const label beI = faceEdges(bfI, feI); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + label nei = edgeFaces(beI, 0); + if( nei == bfI ) + nei = edgeFaces(beI, 1); + + neiPatches[feI] = fPatches[nei]; + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + neiPatches[feI] = otherFacePatch[beI]; + } + } +} + +label edgeExtractor::faceEvaluator::bestPatchTopological +( + const DynList<label>& neiPatches, + const label currentPatch +) +{ + //- find indices of all neighbour patches + DynList<label> allNeiPatches; + forAll(neiPatches, i) + allNeiPatches.appendIfNotIn(neiPatches[i]); + + if( (allNeiPatches.size() == 1) && (allNeiPatches[0] == currentPatch) ) + return currentPatch; + + //- counter the number of neighbours in a patch + Map<label> nNeiInPatch(allNeiPatches.size()); + forAll(allNeiPatches, i) + nNeiInPatch.insert(allNeiPatches[i], 0); + forAll(neiPatches, eI) + ++nNeiInPatch[neiPatches[eI]]; + + label newPatch = -1; + label nNeiEdges(0); + forAllConstIter(Map<label>, nNeiInPatch, it) + { + if( it() > nNeiEdges ) + { + newPatch = it.key(); + nNeiEdges = it(); + } + else if + ( + (it() == nNeiEdges) && (it.key() == currentPatch) + ) + { + newPatch = it.key(); + } + } + + //- do not swap if the situation allows for more than one edge + //- shared with faces in other patches than the dominant one + if( nNeiEdges < (neiPatches.size() - 1) ) + return currentPatch; + + //- do not swap if the best face is in the current patch + if( (newPatch < 0) || (newPatch == currentPatch) ) + return currentPatch; + + //- check whether the edges shared ith the neighbour patch form + //- a singly linked chain + DynList<bool> sharedEdge; + sharedEdge.setSize(neiPatches.size()); + sharedEdge = false; + + forAll(neiPatches, eI) + if( neiPatches[eI] == newPatch ) + sharedEdge[eI] = true; + + if( help::areElementsInChain(sharedEdge) ) + return newPatch; + + return currentPatch; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +edgeExtractor::faceEvaluator::faceEvaluator(const edgeExtractor& ee) +: + extractor_(ee), + otherFacePatch_(), + newBoundaryPatchesPtr_(NULL), + newOtherFacePatchPtr_(NULL) +{ + if( Pstream::parRun() ) + calculateNeiPatchesParallel(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +edgeExtractor::faceEvaluator::~faceEvaluator() +{ + deleteDemandDrivenData(newOtherFacePatchPtr_); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +void edgeExtractor::faceEvaluator::setNewBoundaryPatches +( + const labelList& newBoudaryPatches +) +{ + newBoundaryPatchesPtr_ = &newBoudaryPatches; + + if( Pstream::parRun() ) + calculateNeiPatchesParallelNewPatches(); +} + +void edgeExtractor::faceEvaluator::neiPatchesOverEdges +( + const label bfI, + DynList<label>& neiPatches +) const +{ + neiPatchesOverEdges + ( + bfI, + extractor_.facePatch_, + otherFacePatch_, + neiPatches + ); +} + +label edgeExtractor::faceEvaluator::bestPatchTopological(const label bfI) const +{ + //- get neighbour patches over edges + DynList<label> neiPatches; + neiPatchesOverEdges + ( + bfI, + extractor_.facePatch_, + otherFacePatch_, + neiPatches + ); + + return bestPatchTopological(neiPatches, extractor_.facePatch_[bfI]); +} + +label edgeExtractor::faceEvaluator::bestPatchAfterModification +( + const label bfI +) const +{ + const label patchI = newBoundaryPatchesPtr_->operator[](bfI); + + if( patchI != extractor_.facePatch_[bfI] ) + { + DynList<label> newNeiPatches, oldNeiPatches; + neiPatchesOverEdges + ( + bfI, + *newBoundaryPatchesPtr_, + *newOtherFacePatchPtr_, + newNeiPatches + ); + + neiPatchesOverEdges + ( + bfI, + extractor_.facePatch_, + otherFacePatch_, + oldNeiPatches + ); + + DynList<label> neiFaces, neiProcs; + neiFacesOverEdges(bfI, neiFaces); + neiFacesProcs(bfI, neiProcs); + + forAll(neiFaces, eI) + { + const label origPatchI = extractor_.facePatch_[neiFaces[eI]]; + const label newPatchI = (*newBoundaryPatchesPtr_)[neiFaces[eI]]; + + if( neiFaces[eI] > bfI ) + { + if( newPatchI != origPatchI ) + newNeiPatches[eI] = origPatchI; + } + else if( neiFaces[eI] < 0 ) + { + if( neiProcs[eI] > Pstream::myProcNo() ) + newNeiPatches[eI] = origPatchI; + } + } + + return bestPatchTopological(newNeiPatches, patchI); + } + + return patchI; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +void edgeExtractor::cornerEvaluator::createParallelAddressing() +{ + const labelHashSet& corners = partitioner_.corners(); + + const labelList& facePatch = extractor_.facePatch_; + + typedef Map<label> mapType; + + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const pointFieldPMG& points = mse.points(); + const labelList& bp = mse.bp(); + const VRWGraph& pointFaces = mse.pointFaces(); + const labelList& globalLabel = mse.globalBoundaryPointLabel(); + const mapType& globalToLocal = mse.globalToLocalBndPointAddressing(); + const VRWGraph& bpAtProcs = mse.bpAtProcs(); + const DynList<label>& neiProcs = mse.bpNeiProcs(); + + typedef std::map<label, LongList<labelledPoint> > exchangeMapType; + exchangeMapType exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + faceMap_.clear(); + faceAtProc_.clear(); + facePatches_.clear(); + + forAllConstIter(mapType, globalToLocal, it) + { + const label bpI = it(); + + if( corners.found(bpI) ) + { + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + LongList<labelledPoint>& dts = exchangeData[neiProc]; + + //- data is send in the ollowing form + //- 1. globsl label of the current point + //- 2. number of faces attached to the point + //- 3. for each face send its patch, number of points and point + dts.append(labelledPoint(it.key(), vector::zero)); + dts.append + ( + labelledPoint(pointFaces.sizeOfRow(bpI), vector::zero) + ); + forAllRow(pointFaces, bpI, i) + { + const face& bf = bFaces[pointFaces(bpI, i)]; + dts.append + ( + labelledPoint + ( + facePatch[pointFaces(bpI, i)], + vector::zero + ) + ); + dts.append(labelledPoint(bf.size(), vector::zero)); + + DynList<labelledPoint> lpf; + forAll(bf, pI) + { + const labelledPoint lp + ( + globalLabel[bp[bf[bpI]]], + points[bf[pI]] + ); + + dts.append(lp); + lpf.append(lp); + } + + faceMap_[bpI].append(lpf); + faceAtProc_[bpI].append(Pstream::myProcNo()); + facePatches_[bpI].append(facePatch[pointFaces(bpI, i)]); + } + } + } + } + + std::map<label, List<labelledPoint> > receivedDataMap; + help::exchangeMap(exchangeData, receivedDataMap); + + for + ( + std::map<label, List<labelledPoint> >::const_iterator it=receivedDataMap.begin(); + it!=receivedDataMap.end(); + ++it + ) + { + const label procI = it->first; + const List<labelledPoint>& receivedData = it->second; + + for(label i=0;i<receivedData.size();) + { + const label bpI = globalToLocal[receivedData[i++].pointLabel()]; + + const label nFaces = receivedData[i++].pointLabel(); + + for(label fI=0;fI<nFaces;++fI) + { + const label patchI = receivedData[i++].pointLabel(); + const label size = receivedData[i++].pointLabel(); + + DynList<labelledPoint> lpf(size); + forAll(lpf, pI) + lpf[pI] = receivedData[i++]; + + faceMap_[bpI].append(lpf); + faceAtProc_[bpI].append(procI); + facePatches_[bpI].append(patchI); + } + } + } + + //- srot the faces in the counter-clockwise order + for + ( + std::map<label, DynList<label> >::iterator it=faceAtProc_.begin(); + it!=faceAtProc_.end(); + ++it + ) + { + const label bpI = it->first; + + DynList<label>& faceProc = it->second; + DynList<label>& fPatches = facePatches_[bpI]; + DynList<DynList<labelledPoint, 6> >& pFaces = faceMap_[bpI]; + + forAll(pFaces, i) + { + const DynList<labelledPoint, 6>& lpf = pFaces[i]; + + label pos(-1); + forAll(lpf, pI) + if( lpf[i].pointLabel() == globalLabel[bpI] ) + { + pos = pI; + break; + } + + for(label j=i+2;j<pFaces.size();++j) + { + const DynList<labelledPoint, 6>& olpf = pFaces[j]; + + if( olpf.contains(lpf[lpf.rcIndex(pos)]) ) + { + label helper = faceProc[j]; + faceProc[j] = faceProc[i+1]; + faceProc[i+1] = helper; + + helper = fPatches[j]; + fPatches[j] = fPatches[i+1]; + fPatches[i+1] = helper; + + DynList<labelledPoint, 6> lpfHelper; + lpfHelper = pFaces[j]; + pFaces[j] = pFaces[i+1]; + pFaces[i+1] = lpfHelper; + } + } + } + } +} + +void edgeExtractor::cornerEvaluator::sortedFacesAtPoint +( + const label bpI, + DynList<label>& pFaces +) const +{ + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const VRWGraph& pointFaces = mse.pointFaces(); + const VRWGraph& pointInFace = mse.pointInFaces(); + + pFaces = pointFaces[bpI]; + + forAll(pFaces, i) + { + const face& bf = bFaces[pFaces[i]]; + const label pos = pointFaces.containsAtPosition(bpI, pFaces[i]); + + const edge e = bf.faceEdge(bf.rcIndex(pointInFace(bpI, pos))); + + for(label j=i+2;j<pFaces.size();++j) + { + if( bFaces[pFaces[j]].which(e.start()) >= 0 ) + { + label bfJ = pFaces[i+1]; + pFaces[i+1] = pFaces[j]; + pFaces[j] = bfJ; + } + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +edgeExtractor::cornerEvaluator::cornerEvaluator +( + const edgeExtractor& ee, + const meshSurfacePartitioner& mPart +) +: + extractor_(ee), + partitioner_(mPart), + faceMap_(), + facePatches_(), + faceAtProc_() +{ + if( Pstream::parRun() ) + createParallelAddressing(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +edgeExtractor::cornerEvaluator::~cornerEvaluator() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +void edgeExtractor::cornerEvaluator::improveCorners +( + labelList& newBoundaryPatches +) +{ + const meshOctree& mo = extractor_.meshOctree_; + + const labelHashSet& corners = partitioner_.corners(); + + const meshSurfaceEngine& mse = extractor_.surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const pointFieldPMG& points = mse.points(); + const faceList::subList& bFaces = mse.boundaryFaces(); + + forAllConstIter(labelHashSet, corners, it) + { + const point& p = points[bPoints[it.key()]]; + + if( faceMap_.find(it.key()) == faceMap_.end() ) + { + const labelList& facePatch = extractor_.facePatch_; + Info << "Checking corner " << it.key() << endl; + + //- get faces attached to this point + //- sorted in the counter-clocwise order + DynList<label> pFaces; + sortedFacesAtPoint(it.key(), pFaces); + + Info << "Faces at corner " << pFaces << endl; + + //- find feature edges attached to the point + DynList<labelPair> edgePatches; + DynList<label> edgeIndex; + forAll(pFaces, i) + { + const label patch0 = facePatch[pFaces[i]]; + const label patch1 = facePatch[pFaces[pFaces.fcIndex(i)]]; + + if( patch0 != patch1 ) + { + edgeIndex.append(i); + edgePatches.append(labelPair(patch0, patch1)); + } + } + + Info << "Edge patches " << edgePatches << endl; + Info << "Edge indices " << edgeIndex << endl; + + //- find the best aligned feature edge to the feature edge + DynList<label> bestEdgeIndices(edgePatches.size()); + forAll(edgePatches, i) + { + const label patch0 = edgePatches[i].first(); + const label patch1 = edgePatches[i].second(); + DynList<label> patches(2); + patches[0] = patch0; + patches[1] = patch1; + + //- find the proection of the first point onto the feature edge + point mps; + scalar dSqS; + mo.findNearestPointToPatches(mps, dSqS, p, patches); + + scalar bestAlignment(0.0); + label bestEdgeIndex(-1); + + forAll(pFaces, pfI) + { + const face& bf = bFaces[pFaces[pfI]]; + + const label pos = bf.which(bPoints[it.key()]); + + const point& pe = points[bf[bf.rcIndex(pos)]]; + + //- calculate the vector of current edge + vector ev = pe - p; + ev /= (mag(ev) + VSMALL); + + //- project the endpoint onto the feature edge + point mpe; + scalar dSqE; + mo.findNearestPointToPatches(mpe, dSqE, pe, patches); + + vector fv = mpe - mps; + fv /= (mag(fv) + VSMALL); + + //- calculate alignment metrix between the current edge + //- and the feature edge + const scalar align = 0.5 * (1.0 + (ev & fv)); + + if( align > bestAlignment ) + { + bestAlignment = align; + bestEdgeIndex = pfI; + } + } + + bestEdgeIndices[i] = bestEdgeIndex; + } + + Info << "\nPatches of edges at corner " << it.key() + << " are " << edgePatches << endl; + Info << "Orig edge indices " << edgeIndex << endl; + Info << "New edge indices " << bestEdgeIndices << endl; + + DynList<label> newFacePatches(pFaces.size()); + forAll(bestEdgeIndices, i) + { + const label patch = edgePatches[i].first(); + label index = bestEdgeIndices[i]; + + while( index != bestEdgeIndices[bestEdgeIndices.fcIndex(i)] ) + { + newFacePatches[index] = patch; + index = (index + 1) % pFaces.size(); + } + } + + bool allPatchesRemain(true); + forAll(edgePatches, i) + if( !newFacePatches.contains(edgePatches[i].first()) ) + { + allPatchesRemain = false; + break; + } + + Info << "New patches at point" << newFacePatches << endl; + if( allPatchesRemain ) + { + forAll(pFaces, i) + newBoundaryPatches[pFaces[i]] = newFacePatches[i]; + } + } + else + { + + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +bool edgeExtractor::findCornerCandidates() +{ + bool changed(false); + + const triSurf& surf = meshOctree_.surface(); + const pointField& sp = surf.points(); + + //- create the surface partitioner and find the corners on the surface mesh + triSurfacePartitioner surfPartitioner(surf); + + const labelList& corners = surfPartitioner.corners(); + + Map<label> surfacePointToCorner; + forAll(corners, cornerI) + surfacePointToCorner.insert(corners[cornerI], cornerI); + + List<labelledScalar> nearestPoint + ( + corners.size(), + labelledScalar(0, VGREAT) + ); + + //- calculate the search range + const meshSurfaceEngine& mse = this->surfaceEngine(); + const pointFieldPMG& points = mesh_.points(); + const labelList& bPoints = mse.boundaryPoints(); + const labelList& bp = mse.bp(); + const faceList::subList& bFaces = mse.boundaryFaces(); + + scalarList searchRange(bPoints.size(), 0.0); + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + const point c = bf.centre(points); + + forAll(bf, pI) + { + const scalar d = 2.0 * Foam::mag(c - points[bf[pI]]); + const label bpI = bp[bf[pI]]; + + searchRange[bpI] = Foam::max(d, searchRange[bpI]); + } + } + + if( Pstream::parRun() ) + { + const VRWGraph& bpAtProcs = mse.beAtProcs(); + const DynList<label>& bpNeiProcs = mse.bpNeiProcs(); + const Map<label>& globalToLocal = + mse.globalToLocalBndPointAddressing(); + + std::map<label, LongList<labelledScalar> > exchangeData; + forAll(bpNeiProcs, i) + exchangeData.insert + ( + std::make_pair(bpNeiProcs[i], LongList<labelledScalar>()) + ); + + forAllConstIter(Map<label>, globalToLocal, iter) + { + const label bpI = iter(); + + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelledScalar(iter.key(), searchRange[bpI]) + ); + } + } + + LongList<labelledScalar> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const label bpI = globalToLocal[receivedData[i].scalarLabel()]; + + searchRange[bpI] = + Foam::max(searchRange[bpI], receivedData[i].value()); + } + } + + DynList<label> containedTriangles; + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) private(containedTriangles) + # endif + forAll(bPoints, bpI) + { + const point& p = points[bPoints[bpI]]; + const scalar s = searchRange[bpI]; + + boundBox bb(p-vector(s, s, s), p+vector(s, s, s)); + meshOctree_.findTrianglesInBox(bb, containedTriangles); + + //- find the nearest corner on the surface mesh + forAll(containedTriangles, i) + { + const labelledTri& tri = surf[containedTriangles[i]]; + + forAll(tri, pI) + { + const label spI = tri[pI]; + if( !surfacePointToCorner.found(spI) ) + continue; + + const label cornerI = surfacePointToCorner[spI]; + + const scalar d = Foam::magSqr(sp[spI] - points[bPoints[bpI]]); + + if( nearestPoint[cornerI].value() > d ) + { + //- update the nearest point to the found corner + # ifdef USE_OMP + # pragma omp critical + # endif + { + nearestPoint[cornerI] = labelledScalar(bpI, d); + } + } + } + } + } + + # ifdef DEBUGEdgeExtractor + Info << "Nearest points to corners " << nearestPoint << endl; + # endif + + return changed; +} + +bool edgeExtractor::checkCorners() +{ + bool changed(false); + + # ifdef DEBUGEdgeExtractor + const triSurf* surfPtr = surfaceWithPatches(); + surfPtr->writeSurface("checkCornersBefore.fms"); + deleteDemandDrivenData(surfPtr); + # endif + + const pointFieldPMG& points = mesh_.points(); + const meshSurfaceEngine& mse = this->surfaceEngine(); + const labelList& bPoints = mse.boundaryPoints(); + const faceList::subList& bFaces = mse.boundaryFaces(); + const labelList& bp = mse.bp(); + const edgeList& edges = mse.edges(); + const VRWGraph& pointFaces = mse.pointFaces(); + const VRWGraph& faceEdges = mse.faceEdges(); + const VRWGraph& edgeFaces = mse.edgeFaces(); + + const triSurfacePartitioner& sPartitioner = this->partitioner(); + const List<labelHashSet>& patchPatches = sPartitioner.patchPatches(); + + //- allocate a copy of boundary patches + labelList newBoundaryPatches(facePatch_.size()); + + label nCorrected; + Map<label> otherProcNewPatch; + + label nIteration(0); + + do + { + nCorrected = 0; + newBoundaryPatches = facePatch_; + + //- check whether there exist situations where a boundary face + //- is surrounded by more faces in different patches than the + //- faces in the current patch + if( Pstream::parRun() ) + { + findOtherFacePatchesParallel + ( + otherProcNewPatch, + &newBoundaryPatches + ); + } + + //- update the information which edges are assigned as feature edges + meshSurfacePartitioner mPart(mse, newBoundaryPatches); + + //- find corners in the current constelation + const labelHashSet& corners = mPart.corners(); + const VRWGraph& pPatches = mPart.pointPatches(); + + typedef std::map<label, label> mapType; + typedef std::map<label, std::pair<point, scalar> > distMapType; + + mapType cornerIndex; + distMapType nearestToCorner; + + # ifdef DEBUGEdgeExtractor + Info << "Finding corners " << endl; + # endif + + //- find nearest corners in the surface mesh + forAllConstIter(labelHashSet, corners, it) + { + const label bpI = it.key(); + const DynList<label> neiPatches = pPatches[bpI]; + + const point& p = points[bPoints[bpI]]; + point pMap; + scalar dSq; + label nsp; + + if( !meshOctree_.findNearestCorner(pMap, dSq, nsp, p, neiPatches) ) + { + nsp = -1; + meshOctree_.findNearestPointToPatches(pMap, dSq, p, neiPatches); + } + + nearestToCorner[bpI] = std::make_pair(pMap, dSq); + cornerIndex[bpI] = nsp; + } + + std::map<label, DynList<label> > bpMappedAtSurfaceCorner; + forAllConstIter(mapType, cornerIndex, mIt) + { + if( mIt->second < 0 ) + { + //- the corner does not exist in the surface mesh + //- this may be a situation where parts of the surface are in + //- close proximity and are not topologically connected + Warning << "Should not get in here. Not implemented" << endl; + } + else + { + bpMappedAtSurfaceCorner[mIt->second].append(mIt->first); + } + } + + # ifdef DEBUGEdgeExtractor + for + ( + mapType::const_iterator mIt=bpMappedAtSurfaceCorner.begin(); + mIt!=bpMappedAtSurfaceCorner.end(); + ++mIt + ) + if( mIt->second.size() > 1 ) + Info << "Surface corner " << mIt->first + << " mapped mesh points " << mIt->second << endl; + # endif + + //- for all edge nodes find their nearest counterparts in the surface + # ifdef DEBUGEdgeExtractor + Info << "Finding nearest edges" << endl; + # endif + + const labelHashSet& featureEdge = mPart.featureEdges(); + + distMapType nearestToEdgePoint; + mapType edgePointIndex; + std::map<std::pair<label, label>, labelLongList> edgesSharedByPatches; + + forAllConstIter(labelHashSet, featureEdge, it) + { + const label beI = it.key(); + + //- get the patches bounded by this feature edge + DynList<label> patches(2); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + patches[0] = newBoundaryPatches[edgeFaces(beI, 0)]; + patches[1] = newBoundaryPatches[edgeFaces(beI, 1)]; + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + patches[0] = newBoundaryPatches[edgeFaces(beI, 0)]; + patches[1] = otherProcNewPatch[beI]; + } + + //- store the edge into the right group + std::pair<label, label> patchPair + ( + Foam::min(patches[0], patches[1]), + Foam::max(patches[0], patches[1]) + ); + edgesSharedByPatches[patchPair].append(beI); + + //- check if some points have already been checked + const edge& e = edges[beI]; + const label bps = bp[e.start()]; + const label bpe = bp[e.end()]; + + DynList<label> checkPoints; + if + ( + corners.found(bps) && + (nearestToEdgePoint.find(bps) == nearestToEdgePoint.end()) + ) + checkPoints.append(bps); + + if + ( + corners.found(bpe) && + (nearestToEdgePoint.find(bpe) == nearestToEdgePoint.end()) + ) + checkPoints.append(bpe); + + forAll(checkPoints, i) + { + const point& p = points[bPoints[checkPoints[i]]]; + point pMap; + scalar dSq; + label nse; + + if( !meshOctree_.findNearestEdgePoint(pMap, dSq, nse, p, patches) ) + { + nse = -1; + meshOctree_.findNearestPointToPatches(pMap, dSq, p, patches); + } + + nearestToEdgePoint[checkPoints[i]] = std::make_pair(pMap, dSq); + edgePointIndex[checkPoints[i]] = nse; + } + } + + labelHashSet invalidFeatureEdges; + for + ( + std::map<std::pair<label, label>, labelLongList>::const_iterator mIt=edgesSharedByPatches.begin(); + mIt!=edgesSharedByPatches.end(); + ++mIt + ) + { + const bool validConnection = + patchPatches[mIt->first.first].found(mIt->first.second); + + # ifdef DEBUGEdgeExtractor + Info << "Patches " << mIt->first.first + << " and " << mIt->first.second + << " share " << mIt->second + << " edges " << validConnection << endl; + # endif + + if( !validConnection ) + { + //- find surface facets in the vicinity of the edge + //- and check whether there exist various disconnected surface + //- parts in the vicinity of this group of edge + + const DynList<label>& invalidEdges = mIt->second; + + forAll(invalidEdges, i) + invalidFeatureEdges.insert(invalidEdges[i]); + } + } + + # ifdef DEBUGEdgeExtractor + Info << "Invalid feature edges " << invalidFeatureEdges << endl; + ::exit(0); + # endif + + //- check the vicinity of the corner point and check whether + //- it shall be replaced by some other point in the vicinity + std::map<label, DynList<labelPair> > facesAtCornerNewPatches; + forAllConstIter(distMapType, nearestToCorner, it) + { + const label bpI = it->first; + + //- find all points connected to the corner point via a face + labelHashSet nearPoints; + std::map<label, DynList<label> > facesContainingPoint; + forAllRow(pointFaces, bpI, pfI) + { + const label bfI = pointFaces(bpI, pfI); + const face& bf = bFaces[bfI]; + + forAll(bf, pI) + { + nearPoints.insert(bf[pI]); + facesContainingPoint[bf[pI]].append(bfI); + } + } + + # ifdef DEBUGEdgeExtractor + forAllConstIter(labelHashSet, nearPoints, iterN) + { + Info << "Near point " << iterN.key() << endl; + Info << "Faces containing near point are " + << facesContainingPoint[iterN.key()] << endl; + } + # endif + + //- find the nearest point to the location where the corner + //- shall be mapped onto the surface mesh + label bestPoint(-1); + scalar minDistSq(VGREAT); + forAllConstIter(labelHashSet, nearPoints, iter) + { + const point& p = points[iter.key()]; + + const scalar dSq = magSqr(p - nearestToCorner[bpI].first); + + if( dSq < minDistSq ) + { + minDistSq = dSq; + bestPoint = iter.key(); + } + } + + if( bestPoint == bPoints[bpI] ) + { + # ifdef DEBUGEdgeExtractor + Info << "Current corner is nearest" << endl; + # endif + + continue; + } + + # ifdef DEBUGEdgeExtractor + surfPtr = surfaceWithPatches(bpI); + surfPtr->writeSurface + ( + "corner_"+help::scalarToText(bpI)+ + "_iter_"+help::scalarToText(nIteration)+".fms" + ); + deleteDemandDrivenData(surfPtr); + Info << "Best candidate " << bestPoint << endl; + # endif + + //- sort faces and edges at the corner in counter-clockwise order + DynList<label> pFaces, pEdges; + + DynList<label> front; + front.append(0); + + while( front.size() ) + { + const label fI = front.removeLastElement(); + const label bfI = pointFaces(bpI, fI); + + pFaces.append(bfI); + + const face& bf = bFaces[bfI]; + const label pos = bf.which(bPoints[bpI]); + + const label beI = faceEdges(bfI, bf.rcIndex(pos)); + + pEdges.append(beI); + + label nei = edgeFaces(beI, 0); + if( nei == bfI ) + nei = edgeFaces(beI, 1); + + if( pFaces.contains(nei) || (nei < 0) ) + continue; + + front.append(pointFaces.containsAtPosition(bpI, nei)); + } + + # ifdef DEBUGEdgeExtractor + Info << "Boundary point " << bpI + << " pFaces " << pFaces + << " pEdges " << pEdges << endl; + forAll(pFaces, i) + { + Info << "Face " << pFaces[i] << " has nodes " << bFaces[pFaces[i]] << endl; + Info << "Face " << pFaces[i] << " is in patch " << facePatch_[pFaces[i]] << endl; + Info << "Edge " << pEdges[i] << " has nodes " << edges[pEdges[i]] << endl; + } + # endif + + //- find the best fitting edge to move towards the corner + label bestEdge(-1); + scalar bestAlignment(0.0); + + vector dv = it->second.first - points[bPoints[bpI]]; + dv /= (mag(dv) + VSMALL); + + if( facesContainingPoint[bestPoint].size() == 1 ) + { + const label bfI = facesContainingPoint[bestPoint][0]; + + //- only the edges of this face can be candidates + forAll(pEdges, i) + { + const label beI = pEdges[i]; + const edge& e = edges[pEdges[i]]; + + if( !(edgeFaces(beI, 0) == bfI || edgeFaces(beI, 1) == bfI) ) + continue; + + vector ev + ( + points[e.otherVertex(bPoints[bpI])] - points[bPoints[bpI]] + ); + ev /= (mag(ev) + VSMALL); + + const scalar metric = 0.5 * (1.0 + (dv & ev)); + + if( metric > bestAlignment ) + { + bestAlignment = metric; + bestEdge = pEdges[i]; + } + } + } + else + { + //- the edge containing the best point is the candidate + forAll(pEdges, i) + { + const edge& e = edges[pEdges[i]]; + + if( e.otherVertex(bestPoint) != -1 ) + { + //- select the edge which contains best fitting point + bestEdge = pEdges[i]; + break; + } + } + } + + # ifdef DEBUGEdgeExtractor + Info << "Best edge " << bestEdge + << " has alignment " << bestAlignment << endl; + # endif + + //- find groups of sorted faces at this corner which are bounded by + //- existing feature edges and the new candidate + DynList<label> faceInGroup(pFaces.size(), -1); + label groupI(0); + forAll(pFaces, i) + { + if( faceInGroup[i] != -1 ) + continue; + + DynList<label> front; + front.append(i); + faceInGroup[i] = groupI; + + while( front.size() != 0 ) + { + const label currIndex = front.removeLastElement(); + + const label nbeI = pEdges[currIndex]; + const label pbeI = pEdges[pFaces.rcIndex(currIndex)]; + if( (nbeI != bestEdge) && !featureEdge.found(nbeI) ) + { + const label nfI = pFaces.fcIndex(currIndex); + + if( faceInGroup[nfI] == -1 ) + { + faceInGroup[nfI] = groupI; + front.append(nfI); + } + } + else if( (pbeI != bestEdge) && !featureEdge.found(pbeI) ) + { + const label pfI = pFaces.rcIndex(currIndex); + + if( faceInGroup[pfI] == -1 ) + { + faceInGroup[pfI] = groupI; + front.append(pfI); + } + } + } + + ++groupI; + } + + # ifdef DEBUGEdgeExtractor + Info << "faceInGroup " << faceInGroup << endl; + # endif + + //- check which group of faces shall change patch in order to make + //- the best fitting edge a feature edge + DynList<labelPair> groupPairs, groupPatches; + labelPair groupsForChanging(-1, -1); + forAll(pEdges, i) + { + const label beI = pEdges[i]; + + if( beI == bestEdge ) + { + label pos = pFaces.containsAtPosition(edgeFaces(beI, 0)); + groupsForChanging.first() = faceInGroup[pos]; + pos = pFaces.containsAtPosition(edgeFaces(beI, 1)); + groupsForChanging.second() = faceInGroup[pos]; + } + else if( featureEdge.found(beI) ) + { + labelPair lp, lpp; + label pos = pFaces.containsAtPosition(edgeFaces(beI, 0)); + lpp.first() = facePatch_[pFaces[pos]]; + lp.first() = faceInGroup[pos]; + pos = pFaces.containsAtPosition(edgeFaces(beI, 1)); + lpp.second() = facePatch_[pFaces[pos]]; + lp.second() = faceInGroup[pos]; + + groupPairs.append(lp); + groupPatches.append(lpp); + } + } + + # ifdef DEBUGEdgeExtractor + Info << "group pairs " << groupPairs << endl; + Info << "Group patches " << groupPatches << endl; + Info << "Groups for changing " << groupsForChanging << endl; + # endif + + //- check which groups shall change their patch + //- desired patches at the best edge are determined by finding + //- the best alignment between the bestEdge and the feature edges + scalar maxAlignment(0.0); + label bestGroupsOfPatches(-1); + forAll(groupPatches, i) + { + const labelPair& pp = groupPatches[i]; + + const point& bes = points[edges[bestEdge].start()]; + const point& bee = points[edges[bestEdge].end()]; + + DynList<label> patches(2); + patches[0] = pp.first(); + patches[1] = pp.second(); + + point mps, mpe; + scalar dSqS, dSqE; + label nse; + + meshOctree_.findNearestEdgePoint(mps, dSqS, nse, bes, patches); + meshOctree_.findNearestEdgePoint(mpe, dSqE, nse, bee, patches); + + const scalar align = 0.5 * (1.0 + ((bee - bes) & (mpe - mps))); + + if( align > maxAlignment ) + { + maxAlignment = align; + bestGroupsOfPatches = i; + } + } + + # ifdef DEBUGEdgeExtractor + Info << "Best groups of patches " << bestGroupsOfPatches << endl; + # endif + + //- assign new patches + FixedList<label, 2> newPatchForGroup(-1); + DynList<labelPair>& newPatchForFace = facesAtCornerNewPatches[bpI]; + forAll(groupPatches, i) + { + if( i == bestGroupsOfPatches ) + continue; + + const labelPair& gp = groupPairs[i]; + const labelPair& gpp = groupPatches[i]; + + if + ( + gp.first() == groupsForChanging.first() || + gp.first() == groupsForChanging.second() + ) + { + const label otherPatch = gpp.second(); + + scalar Eold(0.0), Enew(0.0); + forAll(faceInGroup, j) + { + if( faceInGroup[j] != gp.first() ) + continue; + + const label bfI = pFaces[j]; + + forAllRow(faceEdges, bfI, feI) + { + const label beI = faceEdges(bfI, feI); + + # ifdef DEBUGEdgeExtractor + Info << "2. beI " << beI << endl; + # endif + + const point& ps = points[edges[beI].start()]; + const point& pe = points[edges[beI].end()]; + const scalar magE = edges[beI].mag(points) + VSMALL; + + vector ev = pe - ps; + ev /= magE; + + label nei = edgeFaces(beI, 0); + if( nei == bfI ) + nei = edgeFaces(beI, 1); + + const label posNei = pFaces.containsAtPosition(nei); + if + ( + (posNei < 0) || + (faceInGroup[posNei] != faceInGroup[j]) + ) + { + if( facePatch_[bfI] != facePatch_[nei] ) + { + DynList<label> patches(2); + patches[0] = facePatch_[bfI]; + patches[1] = facePatch_[nei]; + //- calculate deformation energy + //- of the old state + point mps, mpe; + scalar dSqS, dSqE; + + meshOctree_.findNearestPointToPatches + ( + mps, + dSqS, + ps, + patches + ); + meshOctree_.findNearestPointToPatches + ( + mpe, + dSqE, + pe, + patches + ); + + vector fv = mpe - mps; + fv /= (mag(fv) + VSMALL); + + scalar c = min(fv & ev, 1.0); + c = max(-1.0, c); + const scalar angle = acos(c); + + Eold += + 1.0/magE * (dSqS + dSqE) + magE * angle; + } + if( otherPatch != facePatch_[nei] ) + { + //- calculate deformation energy + //- of the new state + DynList<label> patches(2); + patches[0] = otherPatch; + patches[1] = facePatch_[nei]; + + point mps, mpe; + scalar dSqS, dSqE; + + meshOctree_.findNearestPointToPatches + ( + mps, + dSqS, + ps, + patches + ); + meshOctree_.findNearestPointToPatches + ( + mpe, + dSqE, + pe, + patches + ); + + vector fv = mpe - mps; + fv /= (mag(fv) + VSMALL); + + scalar c = min(fv & ev, 1.0); + c = max(-1.0, c); + const scalar angle = acos(c); + + Enew += + 1.0/magE * (dSqS + dSqE) + magE * angle; + } + } + } + } + + # ifdef DEBUGEdgeExtractor + Info << "1. Eold " << Eold << " Enew " << Enew << endl; + # endif + + if( Enew <= Eold ) + { + newPatchForGroup[0] = otherPatch; + + forAll(faceInGroup, j) + { + if( faceInGroup[j] != gp.first() ) + continue; + + newPatchForFace.append + ( + labelPair(pFaces[j], otherPatch) + ); + } + } + } + else if + ( + gp.second() == groupsForChanging.first() || + gp.second() == groupsForChanging.second() + ) + { + const label otherPatch = gpp.first(); + + scalar Eold(0.0), Enew(0.0); + forAll(faceInGroup, j) + { + if( faceInGroup[j] != gp.second() ) + continue; + + const label bfI = pFaces[j]; + + forAllRow(faceEdges, bfI, feI) + { + const label beI = faceEdges(bfI, feI); + + # ifdef DEBUGEdgeExtractor + Info << "2. beI " << beI << endl; + # endif + + const point& ps = points[edges[beI].start()]; + const point& pe = points[edges[beI].end()]; + const scalar magE = edges[beI].mag(points) + VSMALL; + + vector ev = pe - ps; + ev /= magE; + + label nei = edgeFaces(beI, 0); + if( nei == bfI ) + nei = edgeFaces(beI, 1); + + const label posNei = pFaces.containsAtPosition(nei); + if + ( + (posNei < 0) || + (faceInGroup[posNei] != faceInGroup[j]) + ) + { + if( facePatch_[bfI] != facePatch_[nei] ) + { + DynList<label> patches(2); + patches[0] = facePatch_[bfI]; + patches[1] = facePatch_[nei]; + + //- calculate deformation energy + //- of the old state + point mps, mpe; + scalar dSqS, dSqE; + + meshOctree_.findNearestPointToPatches + ( + mps, + dSqS, + ps, + patches + ); + meshOctree_.findNearestPointToPatches + ( + mpe, + dSqE, + pe, + patches + ); + + vector fv = mpe - mps; + fv /= (mag(fv) + VSMALL); + + scalar c = min(fv & ev, 1.0); + c = max(-1.0, c); + const scalar angle = acos(c); + + Eold += + 1.0/magE * (dSqS + dSqE) + magE * angle; + } + if( otherPatch != facePatch_[nei] ) + { + //- calculate deformation energy + //- of the new state + DynList<label> patches(2); + patches[0] = otherPatch; + patches[1] = facePatch_[nei]; + + point mps, mpe; + scalar dSqS, dSqE; + + meshOctree_.findNearestPointToPatches + ( + mps, + dSqS, + ps, + patches + ); + meshOctree_.findNearestPointToPatches + ( + mpe, + dSqE, + pe, + patches + ); + + vector fv = mpe - mps; + fv /= (mag(fv) + VSMALL); + + scalar c = min(fv & ev, 1.0); + c = max(-1.0, c); + const scalar angle = acos(c); + + Enew += + 1.0/magE * (dSqS + dSqE) + magE * angle; + } + } + } + } + + # ifdef DEBUGEdgeExtractor + Info << "2. Eold " << Eold << " Enew " << Enew << endl; + # endif + + if( Enew <= Eold ) + { + newPatchForGroup[1] = otherPatch; + + forAll(faceInGroup, j) + { + if( faceInGroup[j] != gp.second() ) + continue; + + newPatchForFace.append + ( + labelPair(pFaces[j], otherPatch) + ); + } + } + } + } + + # ifdef DEBUGEdgeExtractor + Info << "New patches for boundary faces " + << newPatchForFace << endl; + # endif + } + + labelHashSet changedPatch; + typedef std::map<label, DynList<labelPair> > labelToPairMap; + forAllConstIter(labelToPairMap, facesAtCornerNewPatches, it) + { + const DynList<labelPair>& lp = it->second; + forAll(lp, i) + { + if( changedPatch.found(lp[i].first()) ) + FatalError << "Face " << lp[i].first() + << " is already modified" << abort(FatalError); + + changedPatch.insert(lp[i].first()); + + newBoundaryPatches[lp[i].first()] = lp[i].second(); + ++nCorrected; + } + } + + reduce(nCorrected, sumOp<label>()); + + if( nCorrected ) + { + changed = true; + facePatch_ = newBoundaryPatches; + } + + if( nIteration++ > 5 ) + { + Info << "Too many iterations" << endl; + break; + } + + # ifdef DEBUGEdgeExtractor + surfPtr = surfaceWithPatches(); + surfPtr->writeSurface + ( + "checkCornersAfterIteration_"+help::scalarToText(nIteration)+".fms" + ); + deleteDemandDrivenData(surfPtr); + # endif + + } while( nCorrected != 0 ); + + return changed; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.C index a1f2a15a0310b0202292eb7a095c4ffb1cc87299..95d62623f5cf2a9c968fcb6f8a8bc9c48f50f6aa 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,7 +35,9 @@ Description #include "labelledPoint.H" #include <map> +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -61,23 +62,33 @@ void meshSurfaceCheckEdgeTypes::classifyEdges() boolList problematicPoint(pointFaces.size()); edgeTypes_.setSize(edges.size()); + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( bFaces.size() < 1000 ) nThreads = 1; + # endif + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(edgeTypes_, edgeI) edgeTypes_[edgeI] = NONE; + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(problematicPoint, pointI) problematicPoint[pointI] = false; + # ifdef USE_OMP # pragma omp barrier # pragma omp for schedule(static, 1) + # endif forAll(bFaces, bfI) { const face& bf = bFaces[bfI]; @@ -116,10 +127,12 @@ void meshSurfaceCheckEdgeTypes::classifyEdges() } } + # ifdef USE_OMP # pragma omp barrier //- start checking feature edges # pragma omp for schedule(static, 1) + # endif forAll(edgeFaces, edgeI) { if( edgeFaces.sizeOfRow(edgeI) == 2 ) @@ -128,10 +141,7 @@ void meshSurfaceCheckEdgeTypes::classifyEdges() const label f1 = edgeFaces(edgeI, 1); if( facePatch[f0] == facePatch[f1] ) - { edgeTypes_[edgeI] |= PATCHEDGE; - continue; - } const edge e = edges[edgeI]; @@ -193,11 +203,11 @@ void meshSurfaceCheckEdgeTypes::classifyEdges() //- make sure that problematic points //- are consistent ove processor boundaries - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAll(bpNeiProcs, i) exchangeData.insert ( - std::make_pair(bpNeiProcs[i], labelListPMG()) + std::make_pair(bpNeiProcs[i], labelLongList()) ); forAllConstIter(Map<label>, globalToLocal, bpIter) @@ -218,7 +228,7 @@ void meshSurfaceCheckEdgeTypes::classifyEdges() } } - labelListPMG receiveData; + labelLongList receiveData; help::exchangeMap(exchangeData, receiveData); forAll(receiveData, i) @@ -365,12 +375,11 @@ meshSurfaceCheckEdgeTypes::meshSurfaceCheckEdgeTypes // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // meshSurfaceCheckEdgeTypes::~meshSurfaceCheckEdgeTypes() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void meshSurfaceCheckEdgeTypes::convexEdges(labelListPMG& convexEdges) const +void meshSurfaceCheckEdgeTypes::convexEdges(labelLongList& convexEdges) const { convexEdges.clear(); @@ -381,7 +390,7 @@ void meshSurfaceCheckEdgeTypes::convexEdges(labelListPMG& convexEdges) const } } -void meshSurfaceCheckEdgeTypes::concaveEdges(labelListPMG& concaveEdges) const +void meshSurfaceCheckEdgeTypes::concaveEdges(labelLongList& concaveEdges) const { concaveEdges.clear(); diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.H b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.H index b8cbb22da0c52b09b2b398dd664fc91fbe702d23..e35707ad6cbe5cb36b3eb51f83feefc9c3c58284 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckEdgeTypes/meshSurfaceCheckEdgeTypes.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceCheckEdgeTypes @@ -104,10 +103,10 @@ public: } //- return indices of convex edges - void convexEdges(labelListPMG& convexEdges) const; + void convexEdges(labelLongList& convexEdges) const; //- return indices of concave edges - void concaveEdges(labelListPMG& concaveEdges) const; + void concaveEdges(labelLongList& concaveEdges) const; }; diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.C index 8dd753d0ea166b11c5bd77655f85fd9151d206c5..bc056d13dd3d1c2f5a44d6b00870cf8add1c7895 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.C @@ -1,39 +1,42 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ #include "meshSurfaceCheckInvertedVertices.H" -#include "meshSurfaceEngine.H" +#include "meshSurfacePartitioner.H" #include "boolList.H" #include "demandDrivenData.H" +#include "refLabelledPoint.H" #include "helperFunctionsPar.H" #include <map> + +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -41,34 +44,164 @@ namespace Foam { // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void meshSurfaceCheckInvertedVertices::checkVertices() { - const meshSurfaceEngine& mse = *surfaceEnginePtr_; + const labelList& facePatch = surfacePartitioner_.boundaryFacePatches(); + const meshSurfaceEngine& mse = surfacePartitioner_.surfaceEngine(); const pointFieldPMG& points = mse.points(); - const labelList& bp = mse.bp(); const VRWGraph& pointFaces = mse.pointFaces(); const VRWGraph& pointInFaces = mse.pointInFaces(); const faceList::subList& bFaces = mse.boundaryFaces(); const vectorField& pNormals = mse.pointNormals(); const vectorField& fCentres = mse.faceCentres(); - + const vectorField& fNormals = mse.faceNormals(); + + const labelHashSet& corners = surfacePartitioner_.corners(); + const labelHashSet& edgePoints = surfacePartitioner_.edgePoints(); + + typedef std::map<label, vector> ltvMap; + typedef std::map<label, ltvMap> lltvMap; + lltvMap pointPatchNormal; + + forAllConstIter(labelHashSet, corners, it) + { + const label bpI = it.key(); + + if( activePointsPtr_ && !activePointsPtr_->operator[](bpI)) + continue; + + ltvMap& patchNormal = pointPatchNormal[bpI]; + + forAllRow(pointFaces, bpI, pfI) + { + const label bfI = pointFaces(bpI, pfI); + const label patchI = facePatch[bfI]; + + if( patchNormal.find(patchI) == patchNormal.end() ) + { + patchNormal[patchI] = fNormals[bfI]; + } + else + { + patchNormal[patchI] += fNormals[bfI]; + } + } + } + + forAllConstIter(labelHashSet, edgePoints, it) + { + const label bpI = it.key(); + + if( activePointsPtr_ && !activePointsPtr_->operator[](bpI)) + continue; + + ltvMap& patchNormal = pointPatchNormal[bpI]; + + forAllRow(pointFaces, bpI, pfI) + { + const label bfI = pointFaces(bpI, pfI); + const label patchI = facePatch[bfI]; + + if( patchNormal.find(patchI) == patchNormal.end() ) + { + patchNormal[patchI] = fNormals[bfI]; + } + else + { + patchNormal[patchI] += fNormals[bfI]; + } + } + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); + const DynList<label>& neiProcs = mse.bpNeiProcs(); + const VRWGraph& bpAtProcs = mse.bpAtProcs(); + + std::map<label, LongList<refLabelledPoint> > exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + if( pointPatchNormal.find(bpI) != pointPatchNormal.end() ) + { + const ltvMap& patchNormal = pointPatchNormal[bpI]; + + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + forAllConstIter(ltvMap, patchNormal, pIt) + exchangeData[neiProc].append + ( + refLabelledPoint + ( + it.key(), + labelledPoint(pIt->first, pIt->second) + ) + ); + } + } + } + + LongList<refLabelledPoint> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const refLabelledPoint& rlp = receivedData[i]; + const label bpI = globalToLocal[rlp.objectLabel()]; + + ltvMap& patchNormal = pointPatchNormal[bpI]; + + const labelledPoint& lp = rlp.lPoint(); + patchNormal[lp.pointLabel()] += lp.coordinates(); + } + } + + forAllIter(lltvMap, pointPatchNormal, it) + { + ltvMap& patchNormal = pointPatchNormal[it->first]; + + forAllIter(ltvMap, patchNormal, pIt) + { + const scalar magv = mag(pIt->second) + VSMALL; + + pIt->second /= magv; + } + } + invertedVertices_.clear(); - + + # ifdef USE_OMP # pragma omp parallel for if( pointFaces.size() > 100 ) \ schedule(dynamic, 20) + # endif forAll(pointFaces, bpI) { if( activePointsPtr_ && !activePointsPtr_->operator[](bpI) ) continue; - + forAllRow(pointFaces, bpI, pfI) { const label pI = pointInFaces(bpI, pfI); const label bfI = pointFaces(bpI, pfI); - + + vector pNormal = pNormals[bpI]; + + if( pointPatchNormal.find(bpI) != pointPatchNormal.end() ) + pNormal = pointPatchNormal[bpI][facePatch[bfI]]; + const face& bf = bFaces[bfI]; - + //- chech the first triangle (with the next node) triangle<point, point> triNext ( @@ -76,44 +209,56 @@ void meshSurfaceCheckInvertedVertices::checkVertices() points[bf.nextLabel(pI)], fCentres[bfI] ); - - vector n = triNext.normal(); - scalar m = mag(n); - if( m < VSMALL ) + + vector nNext = triNext.normal(); + scalar mNext = mag(nNext); + + //- face has zero area + if( mNext < VSMALL ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } else { - n /= m; + nNext /= mNext; } - + + //- collocated points if( magSqr(triNext.a() - triNext.b()) < VSMALL ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } if( magSqr(triNext.c() - triNext.a()) < VSMALL ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } - - if( (n & pNormals[bp[bf[pI]]]) < 0.0 ) + + //- normal vector is not visible + if( (nNext & pNormal) < 0.0 ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } - + //- check the second triangle (with previous node) triangle<point, point> triPrev ( @@ -121,54 +266,70 @@ void meshSurfaceCheckInvertedVertices::checkVertices() fCentres[bfI], points[bf.prevLabel(pI)] ); - - n = triPrev.normal(); - m = mag(n); - if( m < VSMALL ) + + vector nPrev = triPrev.normal(); + scalar mPrev = mag(nPrev); + + //- face has zero area + if( mPrev < VSMALL ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } else { - n /= m; + nPrev /= mPrev; } - + + //- collocated points if( magSqr(triPrev.a() - triPrev.b()) < VSMALL ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } if( magSqr(triPrev.c() - triPrev.a()) < VSMALL ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } - - if( (n & pNormals[bp[bf[pI]]]) < 0.0 ) + + //- normal vector is not visible + if( (nPrev & pNormal) < 0.0 ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); - - continue; + + break; } - + //- check whether the normals of both triangles //- point in the same direction - if( (triNext.normal() & triPrev.normal()) < 0.0 ) + if( (nNext & nPrev) < 0.0 ) { + # ifdef USE_OMP # pragma omp critical + # endif invertedVertices_.insert(bf[pI]); + + break; } } } - + if( Pstream::parRun() ) { //- exchange global labels of inverted points @@ -177,33 +338,33 @@ void meshSurfaceCheckInvertedVertices::checkVertices() const Map<label>& globalToLocal = mse.globalToLocalBndPointAddressing(); const VRWGraph& bpAtProcs = mse.bpAtProcs(); const DynList<label>& neiProcs = mse.bpNeiProcs(); - - std::map<label, labelListPMG> shareData; + + std::map<label, labelLongList> shareData; forAll(neiProcs, i) - shareData.insert(std::make_pair(neiProcs[i], labelListPMG())); - + shareData.insert(std::make_pair(neiProcs[i], labelLongList())); + forAllConstIter(Map<label>, globalToLocal, iter) { const label bpI = iter(); - + if( !invertedVertices_.found(bPoints[bpI]) ) continue; - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - + shareData[neiProc].append(globalPointLabel[bpI]); } } - + //- exchange data with other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(shareData, receivedData); - + forAll(receivedData, i) { const label bpI = globalToLocal[receivedData[i]]; @@ -216,38 +377,33 @@ void meshSurfaceCheckInvertedVertices::checkVertices() meshSurfaceCheckInvertedVertices::meshSurfaceCheckInvertedVertices ( - const meshSurfaceEngine& mse, - const boolList* activePointsPtr + const meshSurfacePartitioner& mpart ) : - deleteSurface_(false), - surfaceEnginePtr_(&mse), - activePointsPtr_(activePointsPtr), + surfacePartitioner_(mpart), + activePointsPtr_(NULL), invertedVertices_() { - checkVertices(); + checkVertices(); } meshSurfaceCheckInvertedVertices::meshSurfaceCheckInvertedVertices ( - polyMeshGen& mesh + const meshSurfacePartitioner& mpart, + const boolList& activePoints ) : - deleteSurface_(true), - surfaceEnginePtr_(new meshSurfaceEngine(mesh)), - activePointsPtr_(NULL), + surfacePartitioner_(mpart), + activePointsPtr_(&activePoints), invertedVertices_() { - checkVertices(); + checkVertices(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // meshSurfaceCheckInvertedVertices::~meshSurfaceCheckInvertedVertices() -{ - if( deleteSurface_ ) - deleteDemandDrivenData(surfaceEnginePtr_); -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.H b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.H index 2a1968bc816147ac4ec26cc44cddb07f4fc1cb0e..9448dc48906a270c7932721565521dcc03e2371f 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCheckInvertedVertices/meshSurfaceCheckInvertedVertices.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceCheckInvertedVertices @@ -47,7 +46,7 @@ namespace Foam { // Forward declarations -class meshSurfaceEngine; +class meshSurfacePartitioner; /*---------------------------------------------------------------------------*\ Class meshSurfaceCheckInvertedVertices Declaration @@ -56,11 +55,8 @@ class meshSurfaceEngine; class meshSurfaceCheckInvertedVertices { // Private data - //- shall the mesh surface be deleted or not - bool deleteSurface_; - - //- mesh surface - const meshSurfaceEngine* surfaceEnginePtr_; + //- mesh surface partitioner + const meshSurfacePartitioner& surfacePartitioner_; //- active surface points const boolList* activePointsPtr_; @@ -85,15 +81,18 @@ public: // Constructors - //- Construct from meshSurfaceEngine + //- Construct from meshSurfacePartitioner meshSurfaceCheckInvertedVertices ( - const meshSurfaceEngine&, - const boolList* activePointsPtr = NULL + const meshSurfacePartitioner& ); - //- Construct from the mesh - meshSurfaceCheckInvertedVertices(polyMeshGen&); + //- Construct from meshSurfacePartitioner and a list of active points + meshSurfaceCheckInvertedVertices + ( + const meshSurfacePartitioner&, + const boolList& activePoints + ); // Destructor diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.C index c0e52febdd417df5ab70649092b700561c60b7a4..cae474a2c19f497eb25de36722c8dcf8ae7a42cc 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,25 +35,25 @@ namespace Foam { // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + meshSurfaceCutter::meshSurfaceCutter ( - polyMeshGen& mesh, - const triSurface& surface + polyMeshGen& mesh, + const triSurf& surface ) : - surface_(surface), - mesh_(mesh), - nIntFaces_(0), - nPoints_(mesh.points().size()), - nFacesInCell_(mesh.cells().size(), direction(0)), - problematicTopology_(mesh.cells().size(), false), - boundaryCell_(mesh.cells().size(), false), - edgePointPtr_(NULL), - newPointsPtr_(NULL), - newPointLabelPtr_(NULL), - facesFromFacePtr_(NULL), - pointTriIndex_() + surface_(surface), + mesh_(mesh), + nIntFaces_(0), + nPoints_(mesh.points().size()), + nFacesInCell_(mesh.cells().size(), direction(0)), + problematicTopology_(mesh.cells().size(), false), + boundaryCell_(mesh.cells().size(), false), + edgePointPtr_(NULL), + newPointsPtr_(NULL), + newPointLabelPtr_(NULL), + facesFromFacePtr_(NULL), + pointTriIndex_() { # ifdef DEBUGCutter @@ -71,7 +70,7 @@ meshSurfaceCutter::meshSurfaceCutter Info << "Checking for cell consisting of two or more closed parts" << endl; # endif //checkCellTopology(); - + # ifdef DEBUGCutter Info << "Checking directions of face normals" << endl; # endif @@ -83,7 +82,7 @@ meshSurfaceCutter::~meshSurfaceCutter() { deleteDemandDrivenData(facesFromFacePtr_); } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.H b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.H index 36459880288da1520b9b8587aa46e78ffb1f1b0b..340b93a6abf12d777b0e75304f2b7ee117cbff62 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutter.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceCutter @@ -37,7 +36,7 @@ SourceFiles #define meshSurfaceCutter_H #include "polyMeshGenModifier.H" -#include "triSurface.H" +#include "triSurf.H" #include "boolList.H" #include "DynList.H" @@ -51,33 +50,33 @@ namespace Foam class meshSurfaceCutter { // private data - //- triangulated surface - const triSurface& surface_; + //- triangulated surface + const triSurf& surface_; //- mesh data - polyMeshGen& mesh_; - - //- helpers - label nIntFaces_; + polyMeshGen& mesh_; + + //- helpers + label nIntFaces_; label nPoints_; List<direction> nFacesInCell_; boolList problematicTopology_; boolList boundaryCell_; - - edgeList* edgePointPtr_; - DynList<point>* newPointsPtr_; - labelList* newPointLabelPtr_; + + edgeList* edgePointPtr_; + DynList<point>* newPointsPtr_; + labelList* newPointLabelPtr_; faceListList* facesFromFacePtr_; List< DynList<label> > pointTriIndex_; // private member functions - //- return patches for the given point + //- return patches for the given point labelList patchesForPoint(const label) const; - - //- find internal points and intersections with the surface - void findInternalPointsAndIntersections(); - //- find vertices on boundary edges + //- find internal points and intersections with the surface + void findInternalPointsAndIntersections(); + + //- find vertices on boundary edges void findBoundaryEdgePoints ( const label, @@ -86,17 +85,17 @@ class meshSurfaceCutter const boolList& ); - //- cuts the face + //- cuts the face bool faceCutter ( const label ); - - void createInternalMeshPointsAndFaces(); - - void createBoundaryFaces(); - //void checkCellTopology(); - //void checkFaceDirections(); + + void createInternalMeshPointsAndFaces(); + + void createBoundaryFaces(); + //void checkCellTopology(); + //void checkFaceDirections(); //- disallows bitwise construct void operator=(const meshSurfaceCutter&); @@ -111,8 +110,8 @@ public: //- construct components meshSurfaceCutter ( - polyMeshGen& mesh, - const triSurface& surface + polyMeshGen& mesh, + const triSurf& surface ); //- Destructor diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterBoundaryFaces.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterBoundaryFaces.C index 092f2b11f37ee06afc087148e81f8caaf9bfe7f6..5548796210f0e6df17b6cdf3afe5ac5648ea2374 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterBoundaryFaces.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterBoundaryFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,12 +42,11 @@ labelList meshSurfaceCutter::patchesForPoint(const label vI) const if( pointTriIndex_[vI].size() ) { labelList pcs(pointTriIndex_[vI].size()); - const List<labelledTri>& fcs = surface_.localFaces(); const DynList<label>& tria = pointTriIndex_[vI]; short i(0); - forAll(tria, tI) - pcs[i++] = fcs[tria[tI]].region(); + forAll(tria, tI) + pcs[i++] = surface_[tria[tI]].region(); return pcs; } @@ -60,24 +58,24 @@ labelList meshSurfaceCutter::patchesForPoint(const label vI) const void meshSurfaceCutter::createBoundaryFaces() { - VRWGraph pointPatches(nPoints_); - forAll(pointPatches, pI) - { - const labelList pp = patchesForPoint(pI); - forAll(pp, ppI) - pointPatches.append(pI, pp[ppI]); - } - - boundaryFacesGenerator - ( - mesh_, - nFacesInCell_, - nPoints_, - nIntFaces_, - boundaryCell_, - pointPatches, - surface_ - ); + VRWGraph pointPatches(nPoints_); + forAll(pointPatches, pI) + { + const labelList pp = patchesForPoint(pI); + forAll(pp, ppI) + pointPatches.append(pI, pp[ppI]); + } + + boundaryFacesGenerator + ( + mesh_, + nFacesInCell_, + nPoints_, + nIntFaces_, + boundaryCell_, + pointPatches, + surface_ + ); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *// diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterCreateEdges.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterCreateEdges.C index 5db4cd5453b070ed1a1d78f2ea44447743225a13..b6b577b05473c675f2ed0c178b7cebf06dc22abb 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterCreateEdges.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterCreateEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,9 +40,9 @@ void meshSurfaceCutter::createEdges labelListList& faceEdges ) const { - const pointFieldPMG& points = mesh_.points(); - const faceListPMG& faces = mesh_.faces(); - + const pointFieldPMG& points = mesh_.points(); + const faceListPMG& faces = mesh_.faces(); + //- set sizes of lists faceEdges.setSize(faces.size()); //- create point faces addressing diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterDecomposeCells.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterDecomposeCells.C index 637eaa4d1b3240ef1d3084a15310885418a079d0..7039dfc1b5a758c44b7f896b585541923c96f62e 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterDecomposeCells.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterDecomposeCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgePoints.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgePoints.C index 4cb8daa5c4e10beb46763955b8880e23327ae1d7..575bf1172c47a4deab3a431400e2f20dd0118bee 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgePoints.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgePoints.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -47,16 +46,16 @@ void meshSurfaceCutter::findBoundaryEdgePoints const boolList& inwardPoint ) { - DynList<point>& newPoints = *newPointsPtr_; - - const faceListPMG& faces = mesh_.faces(); - const pointFieldPMG& meshPoints = mesh_.points(); - + DynList<point>& newPoints = *newPointsPtr_; + + const faceListPMG& faces = mesh_.faces(); + const pointFieldPMG& meshPoints = mesh_.points(); + # ifdef DEBUGCutter Info << "Creating edge points for face " << faceI << endl; - Info << "Face consists of vertices " << faces[faceI] << endl; - const pointField fvrt = faces[faceI].points(meshPoints); - Info << "Vertices " << fvrt << endl; + Info << "Face consists of vertices " << faces[faceI] << endl; + const pointField fvrt = faces[faceI].points(meshPoints); + Info << "Vertices " << fvrt << endl; # endif label inward(-1); @@ -77,15 +76,15 @@ void meshSurfaceCutter::findBoundaryEdgePoints vector normal = f.normal(meshPoints); normal /= mag(normal); - #ifdef DEBUGCutter - Info << "Face normal " << normal << endl; - # endif - + #ifdef DEBUGCutter + Info << "Face normal " << normal << endl; + # endif + const pointField& points = surface_.points(); - const List<labelledTri>& faces = surface_.localFaces(); - const labelListList& fe = surface_.faceEdges(); - const labelListList& ef = surface_.edgeFaces(); - + const LongList<labelledTri>& faces = surface_.facets(); + const VRWGraph& fe = surface_.facetEdges(); + const VRWGraph& ef = surface_.edgeFacets(); + bool finished; short faceJ(0); @@ -94,7 +93,7 @@ void meshSurfaceCutter::findBoundaryEdgePoints faceList& newFaces = facesFromFace_[faceI]; newFaces.setSize(1); newFaces[0] = face(15); - + forAll(newF, npJ) { //- look for points on the boundary edges @@ -105,8 +104,8 @@ void meshSurfaceCutter::findBoundaryEdgePoints //- store the current vertex newFaces[faceJ].newElmt(facePointI++) = newF[npI]; - - if( + + if( outwardPoint[npI] && inwardPoint[next] ) { @@ -122,11 +121,11 @@ void meshSurfaceCutter::findBoundaryEdgePoints } finished = false; - + labelList intersectedNeighbours(2); pointField intersectionPoints(2); List< DynList<label> > iPointPatches(2); - + while( !finished ) { intersectedNeighbours = -1; @@ -148,8 +147,8 @@ void meshSurfaceCutter::findBoundaryEdgePoints # ifdef DEBUGCutter Info << "SEarch tri " << searchTri << " " << faces[searchTri] << endl; - Info << "Vertices in the triangle " - << faces[searchTri].points(points) << endl; + Info << "Vertices in the triangle " + << faces[searchTri].points(points) << endl; Info << "intersected edges " << intersectedEdges << endl; Info << "Intersections " << edgePoints << endl; Info << "intersected vertices " @@ -167,12 +166,12 @@ void meshSurfaceCutter::findBoundaryEdgePoints } else if( intersectedEdges[eI] ) { - const label curEdge = fe[searchTri][eI]; - - label neighbourTri = ef[curEdge][0]; + const label curEdge = fe(searchTri, eI); + + label neighbourTri = ef(curEdge, 0); if( neighbourTri == searchTri ) - neighbourTri = ef[curEdge][1]; - + neighbourTri = ef(curEdge, 1); + # ifdef DEBUGCutter Info << "Neighbour tri " << neighbourTri << " " << faces[neighbourTri] << endl; @@ -236,13 +235,13 @@ void meshSurfaceCutter::findBoundaryEdgePoints FatalErrorIn ( "void meshSurfaceCutter::" - "findBoundaryEdgePoints()" + "findBoundaryEdgePoints()" ) << " Cannot close face " << faceI << " because your data is higly degenerate" << ". Please smooth your triangulated" << " surface and try again!" << abort(FatalError); - + const scalar d0 = mag ( @@ -261,12 +260,12 @@ void meshSurfaceCutter::findBoundaryEdgePoints { searchTri = intersectedNeighbours[1]; } - else if( (d0 - d1) > SMALL ) + else if( (d0 - d1) > SMALL ) { searchTri = intersectedNeighbours[0]; } - - + + if( mag(d0 - d1) < SMALL ) { Info << "intersectionPoints " @@ -275,12 +274,12 @@ void meshSurfaceCutter::findBoundaryEdgePoints << newPoints[newF[npI]] << endl; FatalErrorIn ( - "void meshSurfaceCutter::" - "findBoundaryEdgePoints()" + "void meshSurfaceCutter::" + "findBoundaryEdgePoints()" ) << "Cannot find the vertex on the edge!!" << " Cannot close face " << faceI << abort(FatalError); - } + } } else { @@ -331,7 +330,7 @@ void meshSurfaceCutter::findBoundaryEdgePoints intersectionPoints[0] - newPoints[newF[npI]] ); - + const scalar d1 = mag ( @@ -345,7 +344,7 @@ void meshSurfaceCutter::findBoundaryEdgePoints intersectionPoints[1] - intersectionPoints[0] ); - + if( d0 > 0.1*el && d1 > 0.1*el ) { //- intersection vertices are on the @@ -358,13 +357,13 @@ void meshSurfaceCutter::findBoundaryEdgePoints searchTri = intersectedNeighbours[0]; foundDirection = true; } - else if( (d0 - d1) > SMALL ) + else if( (d0 - d1) > SMALL ) { searchTri = intersectedNeighbours[1]; foundDirection = true; - } + } } - + if( !foundDirection ) { Info << "Search tri " << searchTri << endl; @@ -372,8 +371,8 @@ void meshSurfaceCutter::findBoundaryEdgePoints << intersectedNeighbours << endl; FatalErrorIn ( - "void meshSurfaceCutter::" - "findBoundaryEdgePoints()" + "void meshSurfaceCutter::" + "findBoundaryEdgePoints()" ) << "Cannot find the vertex on the edge!!" << " Cannot close face " << faceI << abort(FatalError); @@ -440,7 +439,7 @@ void meshSurfaceCutter::findBoundaryEdgePoints newPoints.append(intersectionPoints[0]); pointTriIndex_[nPoints_] = iPointPatches[0]; nPoints_++; - } + } } else if( searchTri == intersectedNeighbours[1] ) { @@ -474,9 +473,9 @@ void meshSurfaceCutter::findBoundaryEdgePoints pointTriIndex_[nPoints_] = iPointPatches[1]; nPoints_++; - } + } } - + if( searchTri == inward ) { //- face is closed @@ -532,7 +531,7 @@ void meshSurfaceCutter::findBoundaryEdgePoints facesFromFace_[faceI][0] = newF; } } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // } // End namespace Foam diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgesVrtImpl.H b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgesVrtImpl.H index 064bdaa0945c99a54fe00678e5f231ceec705b17..559d38e6ee1920922c81ab4a6a130739a84eb440 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgesVrtImpl.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterEdgesVrtImpl.H @@ -1,6 +1,6 @@ // Info << "Face intersects a vertex. This is tricky" << endl; const point& p = points[faces[searchTri][eI]]; - const labelList& pf = surface_.pointFaces()[faces[searchTri][eI]]; + const constRow pf = surface_.pointFacets()[faces[searchTri][eI]]; DynList<label> patches; patches.append(searchTri); @@ -11,14 +11,16 @@ if( pf[pfI] != searchTri ) { bool store(true); - + forAll(patches, patchI) if( faces[pf[pfI]].region() == faces[patches[patchI]].region() - ) store = false; - - if( store ) patches.append(pf[pfI]); + ) + store = false; + + if( store ) + patches.append(pf[pfI]); } bool foundTri(false); @@ -96,7 +98,7 @@ neighbour = false; break; } - + if( !neighbour ) break; } } diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceCutter.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceCutter.C index ceb917aa2758fc018171fda1f23623b760d97043..1b00da05fe8ca5fdcc76a3185e26a52afd4ad9eb 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceCutter.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceCutter.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -53,17 +52,17 @@ bool meshSurfaceCutter::faceCutter Info << "Point " << f[pI] << " " << mesh_.points()[f[pI]] << endl; # endif - const edgeList& edges = mesh_.addressingData().edges(); + const edgeList& edges = mesh_.addressingData().edges(); const VRWGraph& faceEdges = mesh_.addressingData().faceEdges(); - labelList fEdges(faceEdges.sizeOfRow(faceI)); - forAllRow(faceEdges, faceI, eI) - fEdges[eI] = faceEdges(faceI, eI); - - const labelList& newPointLabels = *newPointLabelPtr_; - const edgeList& edgePoint = *edgePointPtr_; + labelList fEdges(faceEdges.sizeOfRow(faceI)); + forAllRow(faceEdges, faceI, eI) + fEdges[eI] = faceEdges(faceI, eI); + + const labelList& newPointLabels = *newPointLabelPtr_; + const edgeList& edgePoint = *edgePointPtr_; # ifdef DEBUG_meshSurfaceCutter - const DynList<point>& newPoints = *newPointsPtr_; + const DynList<point>& newPoints = *newPointsPtr_; forAll(f, pI) Info << "Original edge " << pI << " " << edges[fEdges[pI]] << endl; # endif diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceDirections.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceDirections.C index 88b398354be9979c5acd34169607eef39609e81b..2d9f1b954b3367473cebc9bf669b3f689f74a77b 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceDirections.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterFaceDirections.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,51 +40,51 @@ void meshSurfaceCutter::checkFaceDirections() labelList own(polyFaces_.size(),-1); labelList nei(nIntFaces_,-1); - help::calculateOwnersAndNeighbours - ( - polyFaces_, - polyCells_, - own, - nei - ); + help::calculateOwnersAndNeighbours + ( + polyFaces_, + polyCells_, + own, + nei + ); //- check if the boundary face normals point outside for(register label faceI=patchStart_[0];faceI < polyFaces_.size();faceI++) { - const cell& c = polyCells_[own[faceI]]; - - const edgeList fEdges = polyFaces_[faceI].edges(); - - forAll(c, fI) - if( faceI != c[fI] ) - { - const edgeList nEdges = polyFaces_[c[fI]].edges(); - - forAll(fEdges, eI) - { - bool found(false); - - forAll(nEdges, eJ) - if( fEdges[eI] == nEdges[eJ] ) - { - if( - ( - (own[c[fI]] == own[faceI]) && - (fEdges[eI].start() == nEdges[eJ].start()) - ) || - ( - (nei[c[fI]] == own[faceI]) && - (fEdges[eI].start() == nEdges[eJ].end()) - ) - ) - polyFaces_[faceI] = - polyFaces_[faceI].reverseFace(); - } - - if( found ) - break; - } - } + const cell& c = polyCells_[own[faceI]]; + + const edgeList fEdges = polyFaces_[faceI].edges(); + + forAll(c, fI) + if( faceI != c[fI] ) + { + const edgeList nEdges = polyFaces_[c[fI]].edges(); + + forAll(fEdges, eI) + { + bool found(false); + + forAll(nEdges, eJ) + if( fEdges[eI] == nEdges[eJ] ) + { + if( + ( + (own[c[fI]] == own[faceI]) && + (fEdges[eI].start() == nEdges[eJ].start()) + ) || + ( + (nei[c[fI]] == own[faceI]) && + (fEdges[eI].start() == nEdges[eJ].end()) + ) + ) + polyFaces_[faceI] = + polyFaces_[faceI].reverseFace(); + } + + if( found ) + break; + } + } } } diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterInternalFaces.C b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterInternalFaces.C index f1f34eadf6dd1869df971a60c24a8d42f1a24302..ee17c9e29e414085011735f9f62a2623278c2528 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterInternalFaces.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceCutter/meshSurfaceCutterInternalFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,47 +29,41 @@ Description #include "surfaceIntersectionsOctree.H" #include "polyMeshGenAddressing.H" -#define DEBUGCutter - -# ifdef DEBUGCutter -#include "triSurfaceSearch.H" -#include "octreeDataTriSurface.H" -#include "octree.H" -# endif +//#define DEBUGCutter // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam { - + void meshSurfaceCutter::findInternalPointsAndIntersections() { - //- create poly edges - const polyMeshGenAddressing& addressingData = mesh_.addressingData(); - const edgeList& edges = addressingData.edges(); - const VRWGraph& faceEdges = addressingData.faceEdges(); + //- create poly edges + const polyMeshGenAddressing& addressingData = mesh_.addressingData(); + const edgeList& edges = addressingData.edges(); + //const VRWGraph& faceEdges = addressingData.faceEdges(); # ifdef DEBUGCutter Info << "Edges " << edges << endl; Info << "faceEdges " << faceEdges << endl; # endif - //- create the octree - surfaceIntersectionsOctree so(surface_, 100, 10); - - const pointFieldPMG& points = mesh_.points(); - - if( !newPointsPtr_ ) - newPointsPtr_ = new DynList<point>(); - DynList<point>& newPoints = *newPointsPtr_; - newPoints.setSize(points.size()); - - if( !newPointLabelPtr_ ) - newPointLabelPtr_ = new labelList(); + //- create the octree + surfaceIntersectionsOctree so(surface_, 100, 10); + + const pointFieldPMG& points = mesh_.points(); + + if( !newPointsPtr_ ) + newPointsPtr_ = new DynList<point>(); + DynList<point>& newPoints = *newPointsPtr_; + newPoints.setSize(points.size()); + + if( !newPointLabelPtr_ ) + newPointLabelPtr_ = new labelList(); labelList& newPointLabels = *newPointLabelPtr_; - newPointLabels.setSize(points.size()); - newPointLabels = -1; - + newPointLabels.setSize(points.size()); + newPointLabels = -1; + const label np = points.size(); nPoints_ = 0; Serr << "Creating internal vertices:"; @@ -88,14 +81,14 @@ void meshSurfaceCutter::findInternalPointsAndIntersections() newPoints.append(points[pI]); nPoints_++; } - + if( index++ >= np / 10 ) { Serr << "."; index = 0; } } - + Info << endl; # ifdef DEBUGCutter @@ -116,12 +109,12 @@ void meshSurfaceCutter::findInternalPointsAndIntersections() pointTriIndex_.setSize(points.size()); - if( !edgePointPtr_ ) - edgePointPtr_ = new edgeList(); + if( !edgePointPtr_ ) + edgePointPtr_ = new edgeList(); edgeList& edgePoint = *edgePointPtr_; - edgePoint.setSize(edges.size()); - edgePoint = edge(-1, -1); - //Info << "Number of edges is " << edges.size() << endl; + edgePoint.setSize(edges.size()); + edgePoint = edge(-1, -1); + //Info << "Number of edges is " << edges.size() << endl; index = 0; @@ -141,14 +134,14 @@ void meshSurfaceCutter::findInternalPointsAndIntersections() { edgePoint[eI].start() = nPoints_; edgePoint[eI].end() = -1; - - # ifdef DEBUGCutter - Info << nl << "1. Points for edge " << eI - << " are " << edges[eI] << endl; - Info << "Start vertex " << points[e.start()] << endl; - Info << "End vertex " << points[e.end()] << endl; - Info << "Intersection " << ss.rawPoint() << endl; - # endif + + # ifdef DEBUGCutter + Info << nl << "1. Points for edge " << eI + << " are " << edges[eI] << endl; + Info << "Start vertex " << points[e.start()] << endl; + Info << "End vertex " << points[e.end()] << endl; + Info << "Intersection " << ss.rawPoint() << endl; + # endif newPoints.append(ss.rawPoint()); pointTriIndex_.newElmt(nPoints_).append(ss.index()); @@ -180,14 +173,14 @@ void meshSurfaceCutter::findInternalPointsAndIntersections() { edgePoint[eI].start() = -1; edgePoint[eI].end() = nPoints_; - - # ifdef DEBUGCutter - Info << nl << "2. Points for edge " << eI - << " are " << edges[eI] << endl; - Info << "Start vertex " << points[e.start()] << endl; - Info << "End vertex " << points[e.end()] << endl; - Info << "Intersection " << ss.rawPoint() << endl; - # endif + + # ifdef DEBUGCutter + Info << nl << "2. Points for edge " << eI + << " are " << edges[eI] << endl; + Info << "Start vertex " << points[e.start()] << endl; + Info << "End vertex " << points[e.end()] << endl; + Info << "Intersection " << ss.rawPoint() << endl; + # endif newPoints.append(ss.rawPoint()); pointTriIndex_.newElmt(nPoints_).append(ss.index()); @@ -224,14 +217,14 @@ void meshSurfaceCutter::findInternalPointsAndIntersections() edgePoint[eI].start() = nPoints_; newPoints.append(ss.rawPoint()); - # ifdef DEBUGCutter - Info << nl << "3. Points for edge " << eI - << " are " << edges[eI] << endl; - Info << "Start vertex " << points[e.start()] << endl; - Info << "End vertex " << points[e.end()] << endl; - Info << "Intersection1 " << ss.rawPoint() << endl; - Info << "Intersection2 " << ss1.rawPoint() << endl; - # endif + # ifdef DEBUGCutter + Info << nl << "3. Points for edge " << eI + << " are " << edges[eI] << endl; + Info << "Start vertex " << points[e.start()] << endl; + Info << "End vertex " << points[e.end()] << endl; + Info << "Intersection1 " << ss.rawPoint() << endl; + Info << "Intersection2 " << ss1.rawPoint() << endl; + # endif pointTriIndex_.newElmt(nPoints_).append(ss.index()); nPoints_++; @@ -243,8 +236,8 @@ void meshSurfaceCutter::findInternalPointsAndIntersections() } else if( ss.hit() || ss1.hit() ) { - Info << "ss " << ss << endl; - Info << "ss1 " << ss1 << endl; + Info << "ss " << ss << endl; + Info << "ss1 " << ss1 << endl; FatalErrorIn ( "void meshSurfaceCutter::createInternalMeshPointsAndFaces()" @@ -304,16 +297,16 @@ void meshSurfaceCutter::findInternalPointsAndIntersections() Info << "edgePoint["<<eI<<"] are "<< edgePoint[eI] << endl; } # endif - + } void meshSurfaceCutter::createInternalMeshPointsAndFaces() { - findInternalPointsAndIntersections(); + findInternalPointsAndIntersections(); const labelList owner = mesh_.owner(); const labelList neighbour = mesh_.neighbour(); - const faceListPMG& faces = mesh_.faces(); + //const faceListPMG& faces = mesh_.faces(); //- Finally, create new internal faces Serr << "Creating internal faces:"; @@ -341,7 +334,7 @@ void meshSurfaceCutter::createInternalMeshPointsAndFaces() # ifdef DEBUGCutter Info << "Cutting face " << faceI << " for cell " << owner[faceI] << " and cell " << neighbour[faceI] << endl; - Info << "Original face " << faces[faceI] << endl; + Info << "Original face " << faces[faceI] << endl; # endif //- create a mesh face from a face of a Voronoi polyhedron @@ -350,11 +343,11 @@ void meshSurfaceCutter::createInternalMeshPointsAndFaces() boundaryCell_[owner[faceI]] = true; boundaryCell_[neighbour[faceI]] = true; } - - # ifdef DEBUGCutter - Info << "New faces for face are " << facesFromFace_[faceI] << endl; - # endif - + + # ifdef DEBUGCutter + Info << "New faces for face are " << facesFromFace_[faceI] << endl; + # endif + if( index++ >= neighbour.size() / 10 ) { Serr << "."; @@ -366,19 +359,19 @@ void meshSurfaceCutter::createInternalMeshPointsAndFaces() Info << endl; //- delete surface topology addressing - const_cast<triSurface&>(surface_).clearTopology(); + const_cast<triSurf&>(surface_).clearAddressing(); //- store internal faces forAll(nFacesInCell_, cI) { nFacesInCell_[cI] = 0; } - + nIntFaces_ = 0; - - polyMeshGenModifier meshModifier(mesh_); - cellListPMG& newCells = meshModifier.cellsAccess(); - faceListPMG& newFaces = meshModifier.facesAccess(); + + polyMeshGenModifier meshModifier(mesh_); + cellListPMG& newCells = meshModifier.cellsAccess(); + faceListPMG& newFaces = meshModifier.facesAccess(); forAll(facesFromFace_, faceI) { @@ -395,13 +388,13 @@ void meshSurfaceCutter::createInternalMeshPointsAndFaces() //- that the owner and/or neighbour cells consist of two parts if( facesFromFace_[faceI].size() > 1 ) { - # ifdef DEBUCutter + # ifdef DEBUCutter Info << "face " << faceI << " " << faces[faceI] << nl << "owner " << owner[faceI] << nl << "neighbour " << neighbour[faceI] << nl << " is decomposed into " << facesFromFace_[faceI] << endl; - # endif + # endif problematicTopology_[owner[faceI]] = true; problematicTopology_[neighbour[faceI]] = true; } @@ -410,20 +403,20 @@ void meshSurfaceCutter::createInternalMeshPointsAndFaces() { const face& f = facesFromFace_[faceI][fJ]; # ifdef DEBUGCutter - Info << "Storing face " << nIntFaces_ << " " << f + Info << "Storing face " << nIntFaces_ << " " << f << " into cells " << owner[faceI] << " and " << neighbour[faceI] << endl; # endif if( f.size() > 2 ) - { - //- store cut internal faces - const label own = owner[faceI]; - const label nei = neighbour[faceI]; - newCells[own][nFacesInCell_[own]++] = nIntFaces_; - newCells[nei][nFacesInCell_[nei]++] = nIntFaces_; - newFaces.newElmt(nIntFaces_++) = f; - } - + { + //- store cut internal faces + const label own = owner[faceI]; + const label nei = neighbour[faceI]; + newCells[own][nFacesInCell_[own]++] = nIntFaces_; + newCells[nei][nFacesInCell_[nei]++] = nIntFaces_; + newFaces.newElmt(nIntFaces_++) = f; + } + } } @@ -468,7 +461,7 @@ void meshSurfaceCutter::createInternalMeshPointsAndFaces() { Info << "Checking closedness for cell " << cellI << " consisting of newFaces " << newCells[cellI] << endl; - + const edgeList edges = newCells[cellI].edges(newFaces); labelList nAppearances(edges.size(), 0); @@ -523,7 +516,7 @@ void meshSurfaceCutter::createInternalMeshPointsAndFaces() ) << "Edge " << edges[eI] << " appears once in cell " << cellI << " and it is not on the boundary" << abort(FatalError); - } + } } # endif } diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceDetectPlanarRegions/meshSurfaceDetectPlanarRegions.C b/meshLibrary/utilities/surfaceTools/meshSurfaceDetectPlanarRegions/meshSurfaceDetectPlanarRegions.C new file mode 100644 index 0000000000000000000000000000000000000000..343a7c9a1096438e213c90991b6a2dc512615eb5 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceDetectPlanarRegions/meshSurfaceDetectPlanarRegions.C @@ -0,0 +1,241 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "meshSurfaceDetectPlanarRegions.H" +#include "meshSurfaceEngine.H" +#include "labelledPoint.H" +#include "helperFunctions.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace meshSurfaceDetectPlanarRegionsHelper +{ + +class meshSurfaceDetectPlanarRegionsNeiOp +{ + // Private data + //- const reference to meshSurfaceEngine + const meshSurfaceEngine& mse_; + + //- angle tolerance + const scalar cosTol_; + + //- face normals + vectorField faceNormals_; + +public: + + // Constructors + //- Construct from meshSurfaceEngine + meshSurfaceDetectPlanarRegionsNeiOp + ( + const meshSurfaceEngine& mse, + const scalar cosTol + ) + : + mse_(mse), + cosTol_(cosTol), + faceNormals_() + { + //- create face-faces addressing outside of a parallel region + mse_.faceFaces(); + + //- calculate face normals + const pointFieldPMG& pts = mse_.points(); + const faceList::subList& bFaces = mse_.boundaryFaces(); + faceNormals_.setSize(bFaces.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; + + vector& fn = faceNormals_[bfI]; + fn = bf.normal(pts); + fn /= mag(fn); + } + } + + // Public member functions + //- return the size (number of boundary faces) + inline label size() const + { + return mse_.boundaryFaces().size(); + } + + //- find neighbours of a boundary face + void operator()(const label bfI, DynList<label>& neiFaces) const + { + neiFaces.clear(); + const VRWGraph& faceFaces = mse_.faceFaces(); + + const vector& fn = faceNormals_[bfI]; + forAllRow(faceFaces, bfI, ffI) + { + const vector& on = faceNormals_[faceFaces(bfI, ffI)]; + + if( (on & fn) > cosTol_ ) + neiFaces.append(faceFaces(bfI, ffI)); + } + } + + //- unify region in case of an MPI parallel run + template<class labelListType> + void collectGroups + ( + std::map<label, DynList<label> >& neiGroups, + const labelListType& elementInGroup, + const DynList<label>& localGroupLabel + ) const + { + /* + const Map<label>& globalToLocal = + mse_.globalToLocalBndEdgeAddressing(); + const Map<label>& otherFaceAtProc = mse_.otherEdgeFaceAtProc(); + + const DynList<label>& neiProcs = mse_.beNeiProcs(); + + std::map<label, DynList<labelledPoint> > exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + forAllRow(bpEdges, bpI, i) + { + const label beI = bpEdges(bpI, i); + + if( !isFeatureEdge_[beI] ) + continue; + + const label groupI = elementInGroup[beI]; + + forAllRow(bpAtProcs, bpI, ppI) + { + const label neiProc = bpAtProcs(bpI, ppI); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelPair(it.key(), localGroupLabel[groupI]) + ); + } + } + } + + LongList<labelPair> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const labelPair& lp = receivedData[i]; + const label groupI = elementInGroup[globalToLocal[lp.first()]]; + + DynList<label>& ng = neiGroups[localGroupLabel[groupI]]; + + //- store the connection over the inter-processor boundary + ng.appendIfNotIn(lp.second()); + } + */ + } +}; + +class meshSurfaceDetectPlanarRegionsSelOp +{ +public: + + // Constructors + //- Null construct + meshSurfaceDetectPlanarRegionsSelOp() + {} + + // Public member functions + //- a dummy operator + bool operator()(const label) const + { + return true; + } +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace meshSurfaceDetectPlanarRegionsHelper + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void meshSurfaceDetectPlanarRegions::findPlanarRegions() +{ + const scalar cosTol = Foam::cos(angleTol_); + + meshSurfaceDetectPlanarRegionsHelper::meshSurfaceDetectPlanarRegionsNeiOp nop + ( + meshSurface_, + cosTol + ); + + meshSurfaceDetectPlanarRegionsHelper::meshSurfaceDetectPlanarRegionsSelOp sop; + + nPlanarRegions_ = help::groupMarking(faceInPlanarRegion_, nop, sop); +} + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +meshSurfaceDetectPlanarRegions::meshSurfaceDetectPlanarRegions +( + const meshSurfaceEngine& meshSurface, + const scalar angleTol +) +: + meshSurface_(meshSurface), + angleTol_(angleTol), + faceInPlanarRegion_(), + nPlanarRegions_(0) +{ + findPlanarRegions(); +} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +meshSurfaceDetectPlanarRegions::~meshSurfaceDetectPlanarRegions() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceDetectPlanarRegions/meshSurfaceDetectPlanarRegions.H b/meshLibrary/utilities/surfaceTools/meshSurfaceDetectPlanarRegions/meshSurfaceDetectPlanarRegions.H new file mode 100644 index 0000000000000000000000000000000000000000..64fc5ecea6d186329b74afc0ae6949a71ec88346 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceDetectPlanarRegions/meshSurfaceDetectPlanarRegions.H @@ -0,0 +1,121 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + meshSurfaceDetectPlanarRegions + +Description + Detects planar regions in the surface of the volume mesh + +SourceFiles + meshSurfaceDetectPlanarRegions.C + +\*---------------------------------------------------------------------------*/ + +#ifndef meshSurfaceDetectPlanarRegions_H +#define meshSurfaceDetectPlanarRegions_H + +#include "polyMeshGenModifier.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class meshSurfaceEngine; + +/*---------------------------------------------------------------------------*\ + Class meshSurfaceDetectPlanarRegions Declaration +\*---------------------------------------------------------------------------*/ + +class meshSurfaceDetectPlanarRegions +{ + // Private data + //- const reference to mesh surface + const meshSurfaceEngine& meshSurface_; + + //- angle deviation tolerance + scalar angleTol_; + + //- planar region index fo each boundary face + labelList faceInPlanarRegion_; + + //- number of detected planar regions + label nPlanarRegions_; + + // Private member functions + //- calculate new boundary and replace the existing one + void findPlanarRegions(); + + //- Disallow default bitwise copy construct + meshSurfaceDetectPlanarRegions(const meshSurfaceDetectPlanarRegions&); + + //- Disallow default bitwise assignment + void operator=(const meshSurfaceDetectPlanarRegions&); + +public: + + // Constructors + + //- Construct from mesh and IOdictionary + meshSurfaceDetectPlanarRegions + ( + const meshSurfaceEngine& meshSurface, + const scalar angleTol = (M_PI / 180.0) + ); + + // Destructor + + ~meshSurfaceDetectPlanarRegions(); + + // Member Functions + //- return the number of detected planar regions + inline label nPlanarRegions() const + { + return nPlanarRegions_; + } + + //- returns a list containing indices of planar regions + inline const labelList& planarRegions() const + { + return faceInPlanarRegion_; + } + + //- return a region index for a given face + inline label planarRegion(const label bfI) const + { + return faceInPlanarRegion_[bfI]; + } +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateBoundaryFaces.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateBoundaryFaces.C index 05ba3ca07db43327010b6cc4f5e31c4a0ed6de88..b82212aa918cc10fd9ed930a7549a43e3817e97e 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateBoundaryFaces.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateBoundaryFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,16 +42,16 @@ namespace Foam void meshSurfaceEdgeExtractor::createBoundaryFaces() { - boundaryFacesGenerator bfg - ( - mesh_, - nFacesInCell_, - nPoints_, - mesh_.boundaries()[0].patchStart(), - boundaryCell_, - pointRegions_, - meshOctree_.surface() - ); + boundaryFacesGenerator bfg + ( + mesh_, + nFacesInCell_, + nPoints_, + mesh_.boundaries()[0].patchStart(), + boundaryCell_, + pointRegions_, + meshOctree_.surface() + ); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateEdgeVertices.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateEdgeVertices.C index bb8b7effb5d85933d7a6f8bd3a6c22e60c4dab54..b2bbf41337f443a2847ff07b099077460be2128f 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateEdgeVertices.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeCreateEdgeVertices.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,112 +42,114 @@ namespace Foam void meshSurfaceEdgeExtractor::createEdgeVertices() { - pointFieldPMG& points = mesh_.points(); - const faceListPMG& faces = mesh_.faces(); - - const edgeList& edges = mesh_.addressingData().edges(); - const VRWGraph& faceEdges = mesh_.addressingData().faceEdges(); - - Map<label> newEdgePoint; - - const label nIntFaces = mesh_.nInternalFaces(); - const label nFaces = faces.size(); - - nPoints_ = points.size(); - - for(label faceI=nIntFaces;faceI<nFaces;++faceI) - { - const face& f = faces[faceI]; - - forAll(f, pI) - { - const label edgeI = faceEdges(faceI, pI); - - if( newEdgePoint.found(edgeI) ) continue; - - const label s = f[pI]; - const label e = f.nextLabel(pI); - - if( !pointRegions_.sizeOfRow(s) || !pointRegions_.sizeOfRow(e) ) - { - Warning << "Boundary vertices " << s << " and " << e - << " are not mapped to the boundary!" << endl; - - continue; - } - - if( pointRegions_(s, 0) != pointRegions_(e, 0) ) - { - point newP; + pointFieldPMG& points = mesh_.points(); + const faceListPMG& faces = mesh_.faces(); + + const edgeList& edges = mesh_.addressingData().edges(); + const VRWGraph& faceEdges = mesh_.addressingData().faceEdges(); + + Map<label> newEdgePoint; + + const label nIntFaces = mesh_.nInternalFaces(); + const label nFaces = faces.size(); + + nPoints_ = points.size(); + + for(label faceI=nIntFaces;faceI<nFaces;++faceI) + { + const face& f = faces[faceI]; + + forAll(f, pI) + { + const label edgeI = faceEdges(faceI, pI); + + if( newEdgePoint.found(edgeI) ) continue; + + const label s = f[pI]; + const label e = f.nextLabel(pI); + + if( !pointRegions_.sizeOfRow(s) || !pointRegions_.sizeOfRow(e) ) + { + Warning << "Boundary vertices " << s << " and " << e + << " are not mapped to the boundary!" << endl; + + continue; + } + + if( pointRegions_(s, 0) != pointRegions_(e, 0) ) + { + point newP; scalar distSq; - - FixedList<point, 2> edgePoints; - FixedList<label, 2> patches; - - edgePoints[0] = points[s]; - edgePoints[1] = points[e]; - patches[0] = pointRegions_(s, 0); - patches[1] = pointRegions_(e, 0); - - const bool found = - meshOctree_.findNearestVertexToTheEdge - ( - edgePoints, - patches, - newP, - distSq - ); - - if( found ) - { - points.append(newP); - } - else - { - points.append - ( - edges[faceEdges(faceI, pI)].centre(points) - ); - } - - pointRegions_.appendList(patches); - - newEdgePoint.insert(edgeI, nPoints_); - ++nPoints_; - } - } - } - - points.setSize(nPoints_); - - //- create new faces - DynList<label> newF(20); - forAll(faces, faceI) - { - const face& f = faces[faceI]; - - newF.clear(); - - forAll(f, eI) - { - newF.append(f[eI]); - if( newEdgePoint.found(faceEdges(faceI, eI)) ) - newF.append(newEdgePoint[faceEdges(faceI, eI)]); - } - - if( newF.size() > f.size() ) - { - //- face must be changed - face& mf = const_cast<face&>(f); - mf.setSize(newF.size()); - forAll(mf, pI) - mf[pI] = newF[pI]; - } - } - - mesh_.clearAddressingData(); - - Info << "Finished creating mesh edges" << endl; + label nse; + + FixedList<point, 2> edgePoints; + FixedList<label, 2> patches; + + edgePoints[0] = points[s]; + edgePoints[1] = points[e]; + patches[0] = pointRegions_(s, 0); + patches[1] = pointRegions_(e, 0); + + const bool found = + meshOctree_.findNearestPointToEdge + ( + newP, + distSq, + nse, + edgePoints, + patches + ); + + if( found ) + { + points.append(newP); + } + else + { + points.append + ( + edges[faceEdges(faceI, pI)].centre(points) + ); + } + + pointRegions_.appendList(patches); + + newEdgePoint.insert(edgeI, nPoints_); + ++nPoints_; + } + } + } + + points.setSize(nPoints_); + + //- create new faces + DynList<label> newF; + forAll(faces, faceI) + { + const face& f = faces[faceI]; + + newF.clear(); + + forAll(f, eI) + { + newF.append(f[eI]); + if( newEdgePoint.found(faceEdges(faceI, eI)) ) + newF.append(newEdgePoint[faceEdges(faceI, eI)]); + } + + if( newF.size() > f.size() ) + { + //- face must be changed + face& mf = const_cast<face&>(f); + mf.setSize(newF.size()); + forAll(mf, pI) + mf[pI] = newF[pI]; + } + } + + mesh_.clearAddressingData(); + + Info << "Finished creating mesh edges" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.C index b9a5c932179aa9d04447714d7e997dc73919de22..2ec7606baf15017e209e3893e335c9fa5e98e517 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,27 +40,27 @@ namespace Foam // Construct from mesh, octree, regions for boundary vertices meshSurfaceEdgeExtractor::meshSurfaceEdgeExtractor ( - polyMeshGen& mesh, - const meshOctree& octree, - const labelList& pointRegion + polyMeshGen& mesh, + const meshOctree& octree, + const labelList& pointRegion ) : - mesh_(mesh), - nPoints_(mesh.points().size()), - boundaryCell_(mesh.cells().size(), false), - nFacesInCell_(mesh.cells().size(), direction(0)), + mesh_(mesh), + nPoints_(mesh.points().size()), + boundaryCell_(mesh.cells().size(), false), + nFacesInCell_(mesh.cells().size(), direction(0)), meshOctree_(octree), pointRegions_(pointRegion.size()) -{ - forAll(pointRegion, pointI) - if( pointRegion[pointI] != -1 ) - pointRegions_.append(pointI, pointRegion[pointI]); - - createEdgeVertices(); - - removeOldBoundaryFaces(); - - createBoundaryFaces(); +{ + forAll(pointRegion, pointI) + if( pointRegion[pointI] != -1 ) + pointRegions_.append(pointI, pointRegion[pointI]); + + createEdgeVertices(); + + removeOldBoundaryFaces(); + + createBoundaryFaces(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // @@ -74,35 +73,35 @@ meshSurfaceEdgeExtractor::~meshSurfaceEdgeExtractor() void meshSurfaceEdgeExtractor::removeOldBoundaryFaces() { - const labelList neighbour_ = mesh_.neighbour(); - polyMeshGenModifier meshModifier_(mesh_); - cellListPMG& cells_ = meshModifier_.cellsAccess(); - - forAll(cells_, cellI) - { - const cell& c = cells_[cellI]; - - cell newC(c); - - forAll(c, fI) - if( neighbour_[c[fI]] != -1 ) - { - boundaryCell_[cellI] = true; - newC[nFacesInCell_[cellI]++] = c[fI]; - } - - if( nFacesInCell_[cellI] < c.size() ) - { - newC.setSize(nFacesInCell_[cellI]); - - cells_[cellI] = newC; - }; - } - - PtrList<writePatch>& boundaries = meshModifier_.boundariesAccess(); - boundaries.setSize(1); - boundaries[0].patchSize() = 0; - meshModifier_.facesAccess().setSize(boundaries[0].patchStart()); + const labelList neighbour_ = mesh_.neighbour(); + polyMeshGenModifier meshModifier_(mesh_); + cellListPMG& cells_ = meshModifier_.cellsAccess(); + + forAll(cells_, cellI) + { + const cell& c = cells_[cellI]; + + cell newC(c); + + forAll(c, fI) + if( neighbour_[c[fI]] != -1 ) + { + boundaryCell_[cellI] = true; + newC[nFacesInCell_[cellI]++] = c[fI]; + } + + if( nFacesInCell_[cellI] < direction(c.size()) ) + { + newC.setSize(nFacesInCell_[cellI]); + + cells_[cellI] = newC; + }; + } + + PtrList<boundaryPatch>& boundaries = meshModifier_.boundariesAccess(); + boundaries.setSize(1); + boundaries[0].patchSize() = 0; + meshModifier_.facesAccess().setSize(boundaries[0].patchStart()); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.H b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.H index 8ba457eae7393a7f1ed0ce2f833c0f1d59d7013b..0d7a69da873e5ea79f38df74adf1c74bbeacdbc5 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor/meshSurfaceEdgeExtractor.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceEdgeExtractor @@ -55,14 +54,14 @@ class meshSurfaceEngine; class meshSurfaceEdgeExtractor { // Private data - //- mesh - polyMeshGen& mesh_; - - label nPoints_; - - boolList boundaryCell_; - - List<direction> nFacesInCell_; + //- mesh + polyMeshGen& mesh_; + + label nPoints_; + + boolList boundaryCell_; + + List<direction> nFacesInCell_; //- reference to the octree const meshOctree& meshOctree_; @@ -71,14 +70,14 @@ class meshSurfaceEdgeExtractor VRWGraph pointRegions_; // Private member functions - //- remove old boundary faces - void removeOldBoundaryFaces(); - + //- remove old boundary faces + void removeOldBoundaryFaces(); + //- create vertices on surface edges void createEdgeVertices(); - - //- create new boundary faces - void createBoundaryFaces(); + + //- create new boundary faces + void createBoundaryFaces(); //- Disallow default bitwise copy construct meshSurfaceEdgeExtractor(const meshSurfaceEdgeExtractor&); @@ -93,9 +92,9 @@ public: //- Construct from mesh data meshSurfaceEdgeExtractor ( - polyMeshGen& mesh, + polyMeshGen& mesh, const meshOctree& octree, - const labelList& pointRegion + const labelList& pointRegion ); // Destructor diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2D.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2D.C new file mode 100644 index 0000000000000000000000000000000000000000..7110c3a2527da7a85b46bfd00dc2da0a6ffd6764 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2D.C @@ -0,0 +1,66 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "meshSurfaceEdgeExtractor2D.H" +#include "demandDrivenData.H" + +#include "meshSurfaceOptimizer.H" + +// #define DEBUGSearch + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +// Construct from mesh, octree, regions for boundary vertices +meshSurfaceEdgeExtractor2D::meshSurfaceEdgeExtractor2D +( + polyMeshGen& mesh, + const meshOctree& octree +) +: + mesh_(mesh), + meshOctree_(octree) +{ + distributeBoundaryFaces(); + + remapBoundaryPoints(); +} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +meshSurfaceEdgeExtractor2D::~meshSurfaceEdgeExtractor2D() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2D.H b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2D.H new file mode 100644 index 0000000000000000000000000000000000000000..25a3620ae6c47d304c45520f0d2697db96015b6a --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2D.H @@ -0,0 +1,104 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + meshSurfaceEdgeExtractor2D + +Description + Stores boundary faces into patches and captures edges and corners + +SourceFiles + meshSurfaceEdgeExtractor2D.C + +\*---------------------------------------------------------------------------*/ + +#ifndef meshSurfaceEdgeExtractor2D_H +#define meshSurfaceEdgeExtractor2D_H + +#include "polyMeshGenModifier.H" +#include "boolList.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class meshOctree; +class meshSurfaceEngine; + +/*---------------------------------------------------------------------------*\ + Class meshSurfaceEdgeExtractor2D Declaration +\*---------------------------------------------------------------------------*/ + +class meshSurfaceEdgeExtractor2D +{ + // Private data + //- mesh + polyMeshGen& mesh_; + + //- octree + const meshOctree& meshOctree_; + + // Private member functions + + //- distribute boundary faces into patches + void distributeBoundaryFaces(); + + //- re-map points after edges have been extracted + void remapBoundaryPoints(); + + //- Disallow default bitwise copy construct + meshSurfaceEdgeExtractor2D(const meshSurfaceEdgeExtractor2D&); + + //- Disallow default bitwise assignment + void operator=(const meshSurfaceEdgeExtractor2D&); + +public: + + // Constructors + + //- Construct from mesh data + meshSurfaceEdgeExtractor2D + ( + polyMeshGen& mesh, + const meshOctree& octree + ); + + // Destructor + + ~meshSurfaceEdgeExtractor2D(); + + // Member Functions +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2DDistributeFaces.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2DDistributeFaces.C new file mode 100644 index 0000000000000000000000000000000000000000..5a3d9bc9b8c7437cbbea778513e0a3b9e16d8563 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractor2D/meshSurfaceEdgeExtractor2DDistributeFaces.C @@ -0,0 +1,158 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "demandDrivenData.H" +#include "meshSurfaceEdgeExtractor2D.H" +#include "meshOctree.H" +#include "triSurf.H" +#include "meshSurfaceEngine.H" +#include "meshSurfaceMapper2D.H" +#include "polyMeshGen2DEngine.H" +#include "helperFunctions.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGMapping + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void meshSurfaceEdgeExtractor2D::distributeBoundaryFaces() +{ + polyMeshGen2DEngine mesh2DEngine(mesh_); + const boolList& activeFace = mesh2DEngine.activeFace(); + const boolList& zMinPoint = mesh2DEngine.zMinPoints(); + const boolList& zMaxPoint = mesh2DEngine.zMaxPoints(); + + const pointFieldPMG& points = mesh_.points(); + const faceListPMG& faces = mesh_.faces(); + const labelList& owner = mesh_.owner(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + + const triSurf& surf = meshOctree_.surface(); + const geometricSurfacePatchList& surfPatches = surf.patches(); + + //- copy boundary faces and their owner face + VRWGraph bndFaces; + labelLongList origFaceLabel; + + forAll(boundaries, patchI) + { + const label start = boundaries[patchI].patchStart(); + const label size = boundaries[patchI].patchSize(); + + for(label fI=0;fI<size;++fI) + { + const label faceI = start + fI; + const face& bf = faces[faceI]; + + bndFaces.appendList(bf); + origFaceLabel.append(faceI); + } + } + + //- project face centres onto their nearest location on the surface mesh + wordList patchNames(surfPatches.size()+2); + forAll(surfPatches, ptchI) + patchNames[ptchI] = surfPatches[ptchI].name(); + + const label bottomEmptyId = patchNames.size() - 2; + const label topEmptyId = patchNames.size() - 1; + + patchNames[bottomEmptyId] = "bottomEmptyFaces"; + patchNames[topEmptyId] = "topEmptyFaces"; + + labelLongList bndFaceOwner(bndFaces.size()); + labelLongList bndFacePatch(bndFaces.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(bndFaces, bfI) + { + const label faceI = origFaceLabel[bfI]; + const face& f = faces[faceI]; + + bndFaceOwner[bfI] = owner[faceI]; + + if( !activeFace[faceI] ) + { + if( zMinPoint[f[0]] ) + { + bndFacePatch[bfI] = bottomEmptyId; + } + else if( zMaxPoint[f[0]] ) + { + bndFacePatch[bfI] = topEmptyId; + } + } + else + { + //- this face is active + const point c = f.centre(points); + + //- find the patch index of the nearest location on the surface mesh + point mapPoint; + scalar distSq; + label patchI, nt; + meshOctree_.findNearestSurfacePoint(mapPoint, distSq, nt, patchI, c); + + bndFacePatch[bfI] = patchI; + } + } + + //- replace the boundary + polyMeshGenModifier(mesh_).replaceBoundary + ( + patchNames, + bndFaces, + bndFaceOwner, + bndFacePatch + ); +} + +void meshSurfaceEdgeExtractor2D::remapBoundaryPoints() +{ + meshSurfaceEngine mse(mesh_); + meshSurfaceMapper2D mapper(mse, meshOctree_); + + mapper.adjustZCoordinates(); + + mapper.mapVerticesOntoSurfacePatches(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.C index 1eab59d5390efcc708617ed80129838c82bb8757..8ad0dc8a9b1c6c1467012851c6ccb28769bf679f 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,7 +29,9 @@ Description #include "meshSurfaceEngine.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif // #define DEBUGSearch @@ -43,12 +44,14 @@ namespace Foam meshSurfaceEngine& meshSurfaceEdgeExtractorFUN::surfaceEngine() { + # ifdef USE_OMP if( omp_in_parallel() ) FatalErrorIn ( "meshSurfaceEngine& meshSurfaceEdgeExtractorFUN::surfaceEngine()" ) << "Cannot create surface engine with a parallel region" << exit(FatalError); + # endif if( !surfaceEnginePtr_ ) surfaceEnginePtr_ = new meshSurfaceEngine(mesh_); diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.H b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.H index f186435da84024dc78ef50cb904ae801562e279c..071238fc192b8041bf5211eb97cc34f921693ff0 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUN.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceEdgeExtractorFUN diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUNDistributeFaces.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUNDistributeFaces.C index 4687b3c6b54d10ebc58ee0eba1ff01f3492b1ee6..068b285317241bee77fb2036bc66a3613b57cf0c 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUNDistributeFaces.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorFUN/meshSurfaceEdgeExtractorFUNDistributeFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,7 +38,9 @@ Description #include "meshSurfaceCheckEdgeTypes.H" #include "meshSurfaceEngine.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGMapping @@ -59,13 +60,13 @@ void meshSurfaceEdgeExtractorFUN::distributeBoundaryFaces() const pointFieldPMG& points = mse.points(); //- set size of patchNames, newBoundaryFaces_ and newBoundaryOwners_ - const triSurface& surface = meshOctree_.surface(); + const triSurf& surface = meshOctree_.surface(); const label nPatches = surface.patches().size(); wordList patchNames(nPatches); VRWGraph newBoundaryFaces; - labelListPMG newBoundaryOwners(bFaces.size()); - labelListPMG newBoundaryPatches(bFaces.size()); + labelLongList newBoundaryOwners(bFaces.size()); + labelLongList newBoundaryPatches(bFaces.size()); //- set patchNames forAll(surface.patches(), patchI) @@ -80,16 +81,18 @@ void meshSurfaceEdgeExtractorFUN::distributeBoundaryFaces() //- find the region for face by finding the patch nearest //- to the face centre + # ifdef USE_OMP # pragma omp parallel for if( bFaces.size() > 100 ) schedule(guided) + # endif forAll(bFaces, bfI) { const point c = bFaces[bfI].centre(points); - label facePatch; + label facePatch, nt; point p; scalar distSq; - meshOctree_.findNearestSurfacePoint(p, distSq, facePatch, c); + meshOctree_.findNearestSurfacePoint(p, distSq, nt, facePatch, c); if( (facePatch > -1) && (facePatch < nPatches) ) { @@ -157,7 +160,7 @@ void meshSurfaceEdgeExtractorFUN::improveQualityOfFundamentalSheets() meshSurfaceCheckEdgeTypes edgeCheck(mse); label id = mesh_.addPointSubset("convexEdges"); - labelListPMG helper; + labelLongList helper; edgeCheck.convexEdges(helper); forAll(helper, i) { diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.C index 8cfa3503ec10c5e8def2d35da4e9a6010d3c895d..c4e1ceafe1604711d70571c4e93ffe343478bc2e 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,6 +29,7 @@ Description #include "demandDrivenData.H" #include "correctEdgesBetweenPatches.H" +#include "meshSurfaceOptimizer.H" // #define DEBUGSearch @@ -43,25 +43,24 @@ namespace Foam // Construct from mesh, octree, regions for boundary vertices meshSurfaceEdgeExtractorNonTopo::meshSurfaceEdgeExtractorNonTopo ( - polyMeshGen& mesh, - const meshOctree& octree + polyMeshGen& mesh, + const meshOctree& octree ) : - mesh_(mesh), - meshOctree_(octree) -{ - distributeBoundaryFaces(); - + mesh_(mesh), + meshOctree_(octree) +{ + distributeBoundaryFaces(); + + remapBoundaryPoints(); + correctEdgesBetweenPatches featureEdges(mesh); - - remapBoundaryPoints(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // meshSurfaceEdgeExtractorNonTopo::~meshSurfaceEdgeExtractorNonTopo() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.H b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.H index e6ffae5d6cfda453fb0f0bf1c8ddef63fabd1f8f..514f6ec76527f571f1fe9027c32912baa82f3561 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopo.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceEdgeExtractorNonTopo @@ -55,19 +54,19 @@ class meshSurfaceEngine; class meshSurfaceEdgeExtractorNonTopo { // Private data - //- mesh - polyMeshGen& mesh_; - - //- octree - const meshOctree& meshOctree_; + //- mesh + polyMeshGen& mesh_; + + //- octree + const meshOctree& meshOctree_; // Private member functions - - //- distribute boundary faces into patches - void distributeBoundaryFaces(); - - //- re-map points after edges have been extracted - void remapBoundaryPoints(); + + //- distribute boundary faces into patches + void distributeBoundaryFaces(); + + //- re-map points after edges have been extracted + void remapBoundaryPoints(); //- Disallow default bitwise copy construct meshSurfaceEdgeExtractorNonTopo(const meshSurfaceEdgeExtractorNonTopo&); @@ -82,7 +81,7 @@ public: //- Construct from mesh data meshSurfaceEdgeExtractorNonTopo ( - polyMeshGen& mesh, + polyMeshGen& mesh, const meshOctree& octree ); diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopoDistributeFaces.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopoDistributeFaces.C index 849b9c5c888aee7019174d29052e2a7d0c8e2368..b8a7ff0e0a3039829e0ffea3a586ff97002efef9 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopoDistributeFaces.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEdgeExtractorNonTopo/meshSurfaceEdgeExtractorNonTopoDistributeFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,8 +32,11 @@ Description #include "meshSurfaceEngine.H" #include "meshSurfaceMapper.H" #include "helperFunctions.H" +#include "edgeExtractor.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGMapping @@ -47,67 +49,12 @@ namespace Foam void meshSurfaceEdgeExtractorNonTopo::distributeBoundaryFaces() { - meshSurfaceEngine mse(mesh_); - - const faceList::subList& bFaces = mse.boundaryFaces(); - const labelList& faceOwner = mse.faceOwners(); - const pointFieldPMG& points = mse.points(); - - //- set size of patchNames, newBoundaryFaces_ and newBoundaryOwners_ - const triSurface& surface = meshOctree_.surface(); - const label nPatches = surface.patches().size(); - - wordList patchNames(nPatches); - VRWGraph newBoundaryFaces; - labelListPMG newBoundaryOwners(bFaces.size()); - labelListPMG newBoundaryPatches(bFaces.size()); - - //- set patchNames - forAll(surface.patches(), patchI) - patchNames[patchI] = surface.patches()[patchI].name(); - - //- append boundary faces - forAll(bFaces, bfI) - { - newBoundaryFaces.appendList(bFaces[bfI]); - newBoundaryOwners[bfI] = faceOwner[bfI]; - } - - //- find the region for face by finding the patch nearest - //- to the face centre - # pragma omp parallel for if( bFaces.size() > 100 ) schedule(guided) - forAll(bFaces, bfI) - { - const point c = bFaces[bfI].centre(points); - - label facePatch; - point p; - scalar distSq; - - meshOctree_.findNearestSurfacePoint(p, distSq, facePatch, c); - - if( (facePatch > -1) && (facePatch < nPatches) ) - { - newBoundaryPatches[bfI] = facePatch; - } - else - { - FatalErrorIn - ( - "void meshSurfaceEdgeExtractorNonTopo::" - "distributeBoundaryFaces()" - ) << "Cannot distribute a face " << bFaces[bfI] << " into any " - << "surface patch!. Exiting.." << exit(FatalError); - } - } - - polyMeshGenModifier(mesh_).replaceBoundary - ( - patchNames, - newBoundaryFaces, - newBoundaryOwners, - newBoundaryPatches - ); + edgeExtractor extractor(mesh_, meshOctree_); + + Info << "Extracting edges" << endl; + extractor.extractEdges(); + + extractor.updateMeshPatches(); } void meshSurfaceEdgeExtractorNonTopo::remapBoundaryPoints() diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.C index 1e3cd6e807af7cf0ec8da6a9e6b49db3f1d4f83d..8df41b735a8ad61b6b96de3f5f112748dfa9ddf4 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,7 +28,9 @@ Description #include "meshSurfaceEngine.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif // #define DEBUGSearch @@ -40,13 +41,13 @@ namespace Foam // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // -// Construct from surface. Holds reference! meshSurfaceEngine::meshSurfaceEngine(polyMeshGen& mesh) : - mesh_(mesh), + mesh_(mesh), + activePatch_(-1), boundaryPointsPtr_(NULL), boundaryFacesPtr_(NULL), - boundaryFacePatchPtr_(NULL), + boundaryFacePatchPtr_(NULL), boundaryFaceOwnersPtr_(NULL), pointFacesPtr_(NULL), pointInFacePtr_(NULL), @@ -56,12 +57,13 @@ meshSurfaceEngine::meshSurfaceEngine(polyMeshGen& mesh) edgesPtr_(NULL), bpEdgesPtr_(NULL), edgeFacesPtr_(NULL), - faceEdgesPtr_(NULL), - faceFacesPtr_(NULL), + faceEdgesPtr_(NULL), + edgePatchesPtr_(NULL), + faceFacesPtr_(NULL), pointNormalsPtr_(NULL), - faceNormalsPtr_(NULL), + faceNormalsPtr_(NULL), faceCentresPtr_(NULL), - + globalBoundaryPointLabelPtr_(NULL), globalBoundaryPointToLocalPtr_(NULL), bpProcsPtr_(NULL), @@ -75,585 +77,62 @@ meshSurfaceEngine::meshSurfaceEngine(polyMeshGen& mesh) globalBoundaryFaceLabelPtr_(NULL) { calculateBoundaryFaces(); - calculateBoundaryNodes(); -} - -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -meshSurfaceEngine::~meshSurfaceEngine() -{ - clearOut(); -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -const polyMeshGen& meshSurfaceEngine::mesh() const -{ - return mesh_; -} - -const pointFieldPMG& meshSurfaceEngine::points() const -{ - return mesh_.points(); -} - -const faceListPMG& meshSurfaceEngine::faces() const -{ - return mesh_.faces(); -} - -const cellListPMG& meshSurfaceEngine::cells() const -{ - return mesh_.cells(); -} - -const labelList& meshSurfaceEngine::bp() const -{ - if( !bppPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const labelList& meshSurfaceEngine::bp() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateBoundaryFaces(); - calculateBoundaryNodes(); - } - - return *bppPtr_; -} - -const labelList& meshSurfaceEngine::boundaryPoints() const -{ - if( !boundaryPointsPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const labelList& meshSurfaceEngine::boundaryPoints() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateBoundaryNodes(); - } - - return *boundaryPointsPtr_; -} - -const faceList::subList& meshSurfaceEngine::boundaryFaces() const -{ - if( !boundaryFacesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const faceList::subList&" - "meshSurfaceEngine::boundaryFaces() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateBoundaryFaces(); - } - - return *boundaryFacesPtr_; -} - -const labelList& meshSurfaceEngine::boundaryFacePatches() const -{ - if( !boundaryFacePatchPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const labelList&" - " meshSurfaceEngine::boundaryFacePatches() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateBoundaryFacePatches(); - } - - return *boundaryFacePatchPtr_; -} - -const labelList& meshSurfaceEngine::faceOwners() const -{ - if( !boundaryFaceOwnersPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const labelList& meshSurfaceEngine::faceOwners() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateBoundaryOwners(); - } - - return *boundaryFaceOwnersPtr_; -} - -const VRWGraph& meshSurfaceEngine::pointFaces() const -{ - if( !pointFacesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::pointFaces() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculatePointFaces(); - } - - return *pointFacesPtr_; -} - -const VRWGraph& meshSurfaceEngine::pointInFaces() const -{ - if( !pointInFacePtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::pointInFaces() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculatePointFaces(); - } - - return *pointInFacePtr_; -} - -const VRWGraph& meshSurfaceEngine::pointPatches() const -{ - if( !pointPatchesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::pointPatches() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculatePointPatches(); - } - - return *pointPatchesPtr_; -} - -const VRWGraph& meshSurfaceEngine::pointPoints() const -{ - if( !pointPointsPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::pointPoints() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculatePointPoints(); - } - - return *pointPointsPtr_; -} - -const vectorField& meshSurfaceEngine::pointNormals() const -{ - if( !pointNormalsPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const vectorField& meshSurfaceEngine::pointNormals() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculatePointNormals(); - } - - return *pointNormalsPtr_; -} - -const vectorField& meshSurfaceEngine::faceNormals() const -{ - if( !faceNormalsPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const vectorField& meshSurfaceEngine::faceNormals() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateFaceNormals(); - } - - return *faceNormalsPtr_; -} - -const vectorField& meshSurfaceEngine::faceCentres() const -{ - if( !faceCentresPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const vectorField& meshSurfaceEngine::faceCentres() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateFaceCentres(); - } - - return *faceCentresPtr_; -} - -const edgeList& meshSurfaceEngine::edges() const -{ - if( !edgesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const edgeList& meshSurfaceEngine::edges() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateEdgesAndAddressing(); - } - - return *edgesPtr_; + calculateBoundaryNodes(); } -const VRWGraph& meshSurfaceEngine::boundaryPointEdges() const -{ - if( !bpEdgesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::boundaryPointEdges() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateEdgesAndAddressing(); - } - - return *bpEdgesPtr_; -} - -const VRWGraph& meshSurfaceEngine::edgeFaces() const -{ - if( !edgeFacesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::edgeFaces() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateEdgeFacesAddressing(); - } - - return *edgeFacesPtr_; -} - -const VRWGraph& meshSurfaceEngine::faceEdges() const -{ - if( !faceEdgesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::faceEdges() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateFaceEdgesAddressing(); - } - - return *faceEdgesPtr_; -} - -const VRWGraph& meshSurfaceEngine::faceFaces() const -{ - if( !faceFacesPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::faceFaces() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calculateFaceFacesAddressing(); - } - - return *faceFacesPtr_; -} - -const labelList& meshSurfaceEngine::globalBoundaryPointLabel() const -{ - if( !globalBoundaryPointLabelPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const labelList&" - " meshSurfaceEngine::globalBoundaryPointLabel() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryPointLabels(); - } - - return *globalBoundaryPointLabelPtr_; -} - -const Map<label>& meshSurfaceEngine::globalToLocalBndPointAddressing() const -{ - if( !globalBoundaryPointToLocalPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const Map<label>&" - " meshSurfaceEngine::globalToLocalBndPointAddressing() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryPointLabels(); - } - - return *globalBoundaryPointToLocalPtr_; -} - -const VRWGraph& meshSurfaceEngine::bpAtProcs() const -{ - if( !globalBoundaryPointLabelPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::bpAtProcs() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryPointLabels(); - } - - return *bpProcsPtr_; -} - -const DynList<label>& meshSurfaceEngine::bpNeiProcs() const -{ - if( !bpNeiProcsPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const DynList<label>& meshSurfaceEngine::bpNeiProcs() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryPointLabels(); - } - - return *bpNeiProcsPtr_; -} - -const labelList& meshSurfaceEngine::globalBoundaryEdgeLabel() const -{ - if( !globalBoundaryEdgeLabelPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const labelList&" - " meshSurfaceEngine::globalBoundaryEdgeLabel() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryEdgeLabels(); - } - - return *globalBoundaryEdgeLabelPtr_; -} - -const Map<label>& meshSurfaceEngine::globalToLocalBndEdgeAddressing() const -{ - if( !globalBoundaryEdgeToLocalPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const Map<label>&" - " meshSurfaceEngine::globalToLocalBndEdgeAddressing() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryEdgeLabels(); - } - - return *globalBoundaryEdgeToLocalPtr_; -} - -const VRWGraph& meshSurfaceEngine::beAtProcs() const -{ - if( !globalBoundaryEdgeLabelPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const VRWGraph& meshSurfaceEngine::beAtProcs() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryEdgeLabels(); - } - - return *beProcsPtr_; -} +meshSurfaceEngine::meshSurfaceEngine(polyMeshGen &mesh, const label patchI) +: + mesh_(mesh), + activePatch_(patchI), + boundaryPointsPtr_(NULL), + boundaryFacesPtr_(NULL), + boundaryFacePatchPtr_(NULL), + boundaryFaceOwnersPtr_(NULL), + pointFacesPtr_(NULL), + pointInFacePtr_(NULL), + pointPatchesPtr_(NULL), + bppPtr_(NULL), + pointPointsPtr_(NULL), + edgesPtr_(NULL), + bpEdgesPtr_(NULL), + edgeFacesPtr_(NULL), + faceEdgesPtr_(NULL), + edgePatchesPtr_(NULL), + faceFacesPtr_(NULL), + pointNormalsPtr_(NULL), + faceNormalsPtr_(NULL), + faceCentresPtr_(NULL), -const DynList<label>& meshSurfaceEngine::beNeiProcs() const + globalBoundaryPointLabelPtr_(NULL), + globalBoundaryPointToLocalPtr_(NULL), + bpProcsPtr_(NULL), + bpNeiProcsPtr_(NULL), + globalBoundaryEdgeLabelPtr_(NULL), + globalBoundaryEdgeToLocalPtr_(NULL), + beProcsPtr_(NULL), + beNeiProcsPtr_(NULL), + otherEdgeFaceAtProcPtr_(NULL), + otherEdgeFacePatchPtr_(NULL), + globalBoundaryFaceLabelPtr_(NULL) { - if( !beNeiProcsPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const DynList<label>& meshSurfaceEngine::beNeiProcs() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryEdgeLabels(); - } - - return *beNeiProcsPtr_; + calculateBoundaryFaces(); + calculateBoundaryNodes(); } -const Map<label>& meshSurfaceEngine::otherEdgeFaceAtProc() const -{ - if( !otherEdgeFaceAtProcPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const Map<label>&" - " meshSurfaceEngine::otherEdgeFaceAtProc() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcAddressingForProcEdges(); - } - - return *otherEdgeFaceAtProcPtr_; -} +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // -const Map<label>& meshSurfaceEngine::otherEdgeFacePatch() const +meshSurfaceEngine::~meshSurfaceEngine() { - if( !otherEdgeFacePatchPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const Map<label>&" - " meshSurfaceEngine::otherEdgeFacePatch() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcAddressingForProcEdges(); - } - - return *otherEdgeFacePatchPtr_; + clearOut(); } -const labelList& meshSurfaceEngine::globalBoundaryFaceLabel() const -{ - if( !globalBoundaryFaceLabelPtr_ ) - { - # ifdef FULLDEBUG - if( omp_in_parallel() ) - FatalErrorIn - ( - "const labelList&" - " meshSurfaceEngine::globalBoundaryFaceLabel() const" - ) << "Calculating addressing inside a parallel region." - << " This is not thread safe" << exit(FatalError); - # endif - - calcGlobalBoundaryFaceLabels(); - } - - return *globalBoundaryFaceLabelPtr_; -} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshSurfaceEngine::clearOut() { deleteDemandDrivenData(boundaryPointsPtr_); deleteDemandDrivenData(boundaryFacesPtr_); - deleteDemandDrivenData(boundaryFacePatchPtr_); + deleteDemandDrivenData(boundaryFacePatchPtr_); deleteDemandDrivenData(boundaryFaceOwnersPtr_); deleteDemandDrivenData(pointFacesPtr_); deleteDemandDrivenData(pointInFacePtr_); @@ -661,14 +140,15 @@ void meshSurfaceEngine::clearOut() deleteDemandDrivenData(bppPtr_); deleteDemandDrivenData(pointPointsPtr_); deleteDemandDrivenData(pointNormalsPtr_); - deleteDemandDrivenData(faceNormalsPtr_); + deleteDemandDrivenData(faceNormalsPtr_); deleteDemandDrivenData(faceCentresPtr_); deleteDemandDrivenData(edgesPtr_); deleteDemandDrivenData(bpEdgesPtr_); deleteDemandDrivenData(edgeFacesPtr_); - deleteDemandDrivenData(faceEdgesPtr_); - deleteDemandDrivenData(faceFacesPtr_); - + deleteDemandDrivenData(faceEdgesPtr_); + deleteDemandDrivenData(edgePatchesPtr_); + deleteDemandDrivenData(faceFacesPtr_); + deleteDemandDrivenData(globalBoundaryPointLabelPtr_); deleteDemandDrivenData(globalBoundaryPointToLocalPtr_); deleteDemandDrivenData(bpProcsPtr_); diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.H b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.H index 497bb6de7b85c4bc31611d18d53afe62eeba168d..e0759b4c678577380c721036b8c74590c097953d 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngine.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceEngine @@ -56,17 +55,20 @@ namespace Foam class meshSurfaceEngine { // Private data - //- mesh - polyMeshGen& mesh_; + //- reference to the mesh + polyMeshGen& mesh_; + + //- number of active patch + const label activePatch_; //- boundary points mutable labelList* boundaryPointsPtr_; //- boundary faces mutable faceList::subList* boundaryFacesPtr_; - - //- patches boundary faces are in - mutable labelList* boundaryFacePatchPtr_; + + //- patches boundary faces are in + mutable labelList* boundaryFacePatchPtr_; //- face owners mutable labelList* boundaryFaceOwnersPtr_; @@ -74,7 +76,7 @@ class meshSurfaceEngine //- point faces addressing mutable VRWGraph* pointFacesPtr_; mutable VRWGraph* pointInFacePtr_; - + //- point-patches addressing mutable VRWGraph* pointPatchesPtr_; @@ -84,60 +86,63 @@ class meshSurfaceEngine //- point points addressing mutable VRWGraph* pointPointsPtr_; - //- edges + //- edges mutable edgeList* edgesPtr_; - + //- boundary point-edges addressing mutable VRWGraph* bpEdgesPtr_; //- edge faces addressing mutable VRWGraph* edgeFacesPtr_; - - //- face edges addressing - mutable VRWGraph* faceEdgesPtr_; - - //- face-faces addressing - mutable VRWGraph* faceFacesPtr_; + + //- face edges addressing + mutable VRWGraph* faceEdgesPtr_; + + //- edge-patches addressing + mutable VRWGraph* edgePatchesPtr_; + + //- face-faces addressing + mutable VRWGraph* faceFacesPtr_; //- point normals mutable vectorField* pointNormalsPtr_; - - //- face normals - mutable vectorField* faceNormalsPtr_; - + + //- face normals + mutable vectorField* faceNormalsPtr_; + //- face centres mutable vectorField* faceCentresPtr_; - + // Private data for parallel execution - + //- global boundary point label mutable labelList* globalBoundaryPointLabelPtr_; - + //- global boundary point to local addressing mutable Map<label>* globalBoundaryPointToLocalPtr_; - + //- boundary point-processors addressing mutable VRWGraph* bpProcsPtr_; - + //- neighbour processors for communication when sending point data mutable DynList<label>* bpNeiProcsPtr_; - + //- global boundary edge label mutable labelList* globalBoundaryEdgeLabelPtr_; - + //- global boundary edge to local addressing mutable Map<label>* globalBoundaryEdgeToLocalPtr_; - + //- boundary edge-processors addressing mutable VRWGraph* beProcsPtr_; - + //- neighbour processors for communication when sending edge data mutable DynList<label>* beNeiProcsPtr_; - + //- processor containing other face and face-patch addressing mutable Map<label>* otherEdgeFaceAtProcPtr_; mutable Map<label>* otherEdgeFacePatchPtr_; - + //- global label for boundary faces mutable labelList* globalBoundaryFaceLabelPtr_; @@ -145,35 +150,36 @@ class meshSurfaceEngine //- calculate boundary nodes, faces and addressing void calculateBoundaryFaces() const; - void calculateBoundaryOwners() const; - void calculateBoundaryNodes() const; - - void calculateBoundaryFacePatches() const; + void calculateBoundaryOwners() const; + void calculateBoundaryNodes() const; + + void calculateBoundaryFacePatches() const; void calculatePointFaces() const; - + void calculatePointPatches() const; void calculatePointPoints() const; void calculatePointNormals() const; - void calculateFaceNormals() const; + void calculateFaceNormals() const; void calculateFaceCentres() const; - + void updatePointNormalsAtProcBoundaries() const; void calculateEdgesAndAddressing() const; void calculateFaceEdgesAddressing() const; - void calculateEdgeFacesAddressing() const; - void calculateFaceFacesAddressing() const; - + void calculateEdgeFacesAddressing() const; + void calculateEdgePatchesAddressing() const; + void calculateFaceFacesAddressing() const; + // Private member functions for parallel runs - + void calcGlobalBoundaryPointLabels() const; void calcGlobalBoundaryEdgeLabels() const; void calcAddressingForProcEdges() const; void calcGlobalBoundaryFaceLabels() const; - + // Private member functions void clearOut(); @@ -186,89 +192,94 @@ class meshSurfaceEngine public: - friend class meshSurfaceEngineModifier; - + friend class meshSurfaceEngineModifier; + // Constructors //- Construct from mesh meshSurfaceEngine(polyMeshGen& mesh); + //- Construct from mesh and patch + meshSurfaceEngine(polyMeshGen &mesh, const label patchI); + // Destructor ~meshSurfaceEngine(); // Member Functions - const polyMeshGen& mesh() const; - const pointFieldPMG& points() const; - const faceListPMG& faces() const; - const cellListPMG& cells() const; + inline const polyMeshGen& mesh() const; + inline const pointFieldPMG& points() const; + inline const faceListPMG& faces() const; + inline const cellListPMG& cells() const; + + inline const labelList& boundaryPoints() const; + + inline const faceList::subList& boundaryFaces() const; + + //- patch label for each boundary face + inline const labelList& boundaryFacePatches() const; + + inline const labelList& faceOwners() const; + + inline const VRWGraph& pointFaces() const; + inline const VRWGraph& pointInFaces() const; + + //inline const VRWGraph& pointPatches() const; + + inline const VRWGraph& pointPoints() const; + + inline const vectorField& pointNormals() const; + + inline const vectorField& faceNormals() const; - const labelList& boundaryPoints() const; + inline const vectorField& faceCentres() const; - const faceList::subList& boundaryFaces() const; - - //- patch label for each boundary face - const labelList& boundaryFacePatches() const; + inline const labelList& bp() const; - const labelList& faceOwners() const; + inline const edgeList& edges() const; - const VRWGraph& pointFaces() const; - const VRWGraph& pointInFaces() const; - - const VRWGraph& pointPatches() const; + inline const VRWGraph& boundaryPointEdges() const; - const VRWGraph& pointPoints() const; + inline const VRWGraph& edgeFaces() const; - const vectorField& pointNormals() const; - - const vectorField& faceNormals() const; - - const vectorField& faceCentres() const; + inline const VRWGraph& faceEdges() const; - const labelList& bp() const; + inline const VRWGraph& edgePatches() const; - const edgeList& edges() const; - - const VRWGraph& boundaryPointEdges() const; + inline const VRWGraph& faceFaces() const; - const VRWGraph& edgeFaces() const; - - const VRWGraph& faceEdges() const; - - const VRWGraph& faceFaces() const; - // Functions for parallel runs //- global boundary point label - const labelList& globalBoundaryPointLabel() const; - + inline const labelList& globalBoundaryPointLabel() const; + //- global point label to local label. Only for processors points - const Map<label>& globalToLocalBndPointAddressing() const; - + inline const Map<label>& globalToLocalBndPointAddressing() const; + //- processors which contain the vertex - const VRWGraph& bpAtProcs() const; - + inline const VRWGraph& bpAtProcs() const; + //- communication matrix for sending point data - const DynList<label>& bpNeiProcs() const; - + inline const DynList<label>& bpNeiProcs() const; + //- global boundary edge label - const labelList& globalBoundaryEdgeLabel() const; - + inline const labelList& globalBoundaryEdgeLabel() const; + //- global boundary edge label to local label. Only for processor edges - const Map<label>& globalToLocalBndEdgeAddressing() const; - + inline const Map<label>& globalToLocalBndEdgeAddressing() const; + //- processors which contain the edges - const VRWGraph& beAtProcs() const; - + inline const VRWGraph& beAtProcs() const; + //- communication matrix for sending edge data - const DynList<label>& beNeiProcs() const; - + inline const DynList<label>& beNeiProcs() const; + //- patch label and processor label at which the other surface face //- sharing processor edge is located. Only for processor edges - const Map<label>& otherEdgeFaceAtProc() const; - const Map<label>& otherEdgeFacePatch() const; - + inline const Map<label>& otherEdgeFaceAtProc() const; + inline const Map<label>& otherEdgeFacePatch() const; + //- global boundary face label - const labelList& globalBoundaryFaceLabel() const; + inline const labelList& globalBoundaryFaceLabel() const; }; @@ -278,6 +289,10 @@ public: // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +#include "meshSurfaceEngineI.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + #endif // ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineCalculateBoundaryNodesAndFaces.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineCalculateBoundaryNodesAndFaces.C index 9608847691dca623e00bc65e1f737b2264879dbd..f79069fea7b732b78040d09869131ad104e92651 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineCalculateBoundaryNodesAndFaces.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineCalculateBoundaryNodesAndFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,7 +36,10 @@ Description #include <map> #include <set> + +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -48,34 +50,58 @@ namespace Foam void meshSurfaceEngine::calculateBoundaryFaces() const { - if( mesh_.boundaries().size() != 0 ) - { - const faceListPMG& faces = mesh_.faces(); - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + if( mesh_.boundaries().size() != 0 ) + { + const faceListPMG& faces = mesh_.faces(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); label nBoundaryFaces(0); - forAll(boundaries, patchI) - nBoundaryFaces += boundaries[patchI].patchSize(); + if( activePatch_ < 0 ) + { + //- take all patches + forAll(boundaries, patchI) + nBoundaryFaces += boundaries[patchI].patchSize(); - boundaryFacesPtr_ = - new faceList::subList - ( - faces, - nBoundaryFaces, - boundaries[0].patchStart() - ); + boundaryFacesPtr_ = + new faceList::subList + ( + faces, + nBoundaryFaces, + boundaries[0].patchStart() + ); + } + else if( activePatch_ < boundaries.size() ) + { + nBoundaryFaces = boundaries[activePatch_].patchSize(); + + boundaryFacesPtr_ = + new faceList::subList + ( + faces, + nBoundaryFaces, + boundaries[activePatch_].patchStart() + ); + } + else + { + FatalErrorIn + ( + "void meshSurfaceEngine::calculateBoundaryFaces() const" + ) << "Cannot select boundary faces. Invalid patch index " + << activePatch_ << exit(FatalError); + } reduce(nBoundaryFaces, sumOp<label>()); Info << "Found " << nBoundaryFaces << " boundary faces " << endl; - } - else - { - FatalErrorIn - ( - "void meshSurfaceEngine::calculateBoundaryFaces() const" - ) << "Boundary faces are not at the end of the face list!" - << exit(FatalError); - } + } + else + { + FatalErrorIn + ( + "void meshSurfaceEngine::calculateBoundaryFaces() const" + ) << "Boundary faces are not at the end of the face list!" + << exit(FatalError); + } } void meshSurfaceEngine::calculateBoundaryOwners() const @@ -85,15 +111,17 @@ void meshSurfaceEngine::calculateBoundaryOwners() const const faceList::subList& boundaryFaces = this->boundaryFaces(); if( !boundaryFaceOwnersPtr_ ) - boundaryFaceOwnersPtr_ = new labelList(boundaryFaces.size()); + boundaryFaceOwnersPtr_ = new labelList(boundaryFaces.size()); labelList& owners = *boundaryFaceOwnersPtr_; const label start = mesh_.boundaries()[0].patchStart(); + # ifdef USE_OMP # pragma omp parallel for schedule(static, 1) + # endif forAll(boundaryFaces, fI) - owners[fI] = owner[start+fI]; + owners[fI] = owner[start+fI]; } void meshSurfaceEngine::calculateBoundaryNodes() const @@ -108,8 +136,10 @@ void meshSurfaceEngine::calculateBoundaryNodes() const boolList isBndPoint(bp.size(), false); + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); # pragma omp parallel for num_threads(nThreads) schedule(static, 1) + # endif forAll(boundaryFaces, bfI) { const face& bf = boundaryFaces[bfI]; @@ -127,7 +157,7 @@ void meshSurfaceEngine::calculateBoundaryNodes() const if( Pstream::parRun() ) { const faceListPMG& faces = mesh_.faces(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); //- exchange information with processors @@ -143,7 +173,7 @@ void meshSurfaceEngine::calculateBoundaryNodes() const const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - labelListPMG dts; + labelLongList dts; labelHashSet addedPoint; for(label faceI=start;faceI<end;++faceI) { @@ -208,7 +238,9 @@ void meshSurfaceEngine::calculateBoundaryNodes() const boundaryPoints.setSize(pointI); //- fill the boundaryPoints list + # ifdef USE_OMP # pragma omp parallel for num_threads(nThreads) schedule(static, 1) + # endif forAll(bp, bpI) { if( bp[bpI] != -1 ) @@ -223,7 +255,7 @@ void meshSurfaceEngine::calculateBoundaryFacePatches() const labelList& facePatch = *boundaryFacePatchPtr_; label faceI(0); - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { const label nFaces = boundaries[patchI].patchSize(); @@ -252,18 +284,28 @@ void meshSurfaceEngine::calculatePointFaces() const //- create boundary points const labelList& bp = this->bp(); - labelListPMG npf; + labelLongList npf; + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( bPoints.size() < 1000 ) nThreads = 1; + # else + const label nThreads(1); + # endif label minRow(INT_MAX), maxRow(0); List<List<LongList<labelPair> > > dataForOtherThreads(nThreads); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif List<LongList<labelPair> >& dot = dataForOtherThreads[threadI]; dot.setSize(nThreads); @@ -271,7 +313,9 @@ void meshSurfaceEngine::calculatePointFaces() const //- find min and max entry in the graph //- they are used for assigning ranges of values local for each process label localMinRow(minRow), localMaxRow(0); + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(bFaces, bfI) { const face& bf = bFaces[bfI]; @@ -285,7 +329,9 @@ void meshSurfaceEngine::calculatePointFaces() const ++localMaxRow; + # ifdef USE_OMP # pragma omp critical + # endif { minRow = Foam::min(minRow, localMinRow); minRow = Foam::max(minRow, 0); @@ -294,21 +340,29 @@ void meshSurfaceEngine::calculatePointFaces() const npf.setSize(maxRow); } + # ifdef USE_OMP # pragma omp barrier + # endif //- initialise appearances + # ifdef USE_OMP # pragma omp for schedule(static) + # endif for(label i=0;i<maxRow;++i) npf[i] = 0; + # ifdef USE_OMP # pragma omp barrier + # endif const label range = (maxRow - minRow) / nThreads + 1; const label localMin = minRow + threadI * range; const label localMax = Foam::min(localMin + range, maxRow); //- find the number of appearances of each element in the original graph + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(bFaces, bfI) { const face& bf = bFaces[bfI]; @@ -330,7 +384,9 @@ void meshSurfaceEngine::calculatePointFaces() const } } + # ifdef USE_OMP # pragma omp barrier + # endif //- count the appearances which are not local to the processor for(label i=0;i<nThreads;++i) @@ -342,16 +398,22 @@ void meshSurfaceEngine::calculatePointFaces() const ++npf[data[j].first()]; } + # ifdef USE_OMP # pragma omp barrier + # endif //- allocate graph + # ifdef USE_OMP # pragma omp master + # endif { VRWGraphSMPModifier(pointFacesAddr).setSizeAndRowSize(npf); VRWGraphSMPModifier(pointInFaceAddr).setSizeAndRowSize(npf); } + # ifdef USE_OMP # pragma omp barrier + # endif for(label i=localMin;i<localMax;++i) npf[i] = 0; @@ -377,7 +439,9 @@ void meshSurfaceEngine::calculatePointFaces() const } //- update data local to the processor + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(bFaces, bfI) { const face& bf = bFaces[bfI]; @@ -427,17 +491,25 @@ void meshSurfaceEngine::calculatePointPatches() const const labelList& facePatch = boundaryFacePatches(); const VRWGraph& pFaces = pointFaces(); + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); + # endif labelList npPatches(pFaces.size()); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(npPatches, i) npPatches[i] = 0; + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(pFaces, bpI) { DynList<label> pf; @@ -447,14 +519,18 @@ void meshSurfaceEngine::calculatePointPatches() const npPatches[bpI] = pf.size(); } + # ifdef USE_OMP # pragma omp barrier # pragma omp master + # endif VRWGraphSMPModifier(pPatches).setSizeAndRowSize(npPatches); + # ifdef USE_OMP # pragma omp barrier # pragma omp for schedule(static) + # endif forAll(pFaces, bpI) { DynList<label> pf; @@ -471,7 +547,7 @@ void meshSurfaceEngine::calculatePointPatches() const const VRWGraph& bpAtProcs = this->bpAtProcs(); const Map<label>& globalToLocal = globalToLocalBndPointAddressing(); - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAllConstIter(Map<label>, globalToLocal, iter) { @@ -487,11 +563,11 @@ void meshSurfaceEngine::calculatePointPatches() const { exchangeData.insert ( - std::make_pair(neiProc, labelListPMG()) + std::make_pair(neiProc, labelLongList()) ); } - labelListPMG& dataToSend = exchangeData[neiProc]; + labelLongList& dataToSend = exchangeData[neiProc]; //- prepare data which will be sent //- data is sent as follows @@ -506,7 +582,7 @@ void meshSurfaceEngine::calculatePointPatches() const } //- exchange data with other processors - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); label counter(0); @@ -532,16 +608,25 @@ void meshSurfaceEngine::calculatePointPoints() const const VRWGraph& pFaces = this->pointFaces(); const labelList& bp = this->bp(); + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); + # endif + labelList npp(boundaryPoints.size()); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(npp, i) npp[i] = 0; + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(pFaces, bpI) { DynList<label> pPoints; @@ -559,13 +644,18 @@ void meshSurfaceEngine::calculatePointPoints() const npp[bpI] = pPoints.size(); } + # ifdef USE_OMP # pragma omp barrier # pragma omp master + # endif VRWGraphSMPModifier(pointPoints).setSizeAndRowSize(npp); + # ifdef USE_OMP # pragma omp barrier + # pragma omp for schedule(static) + # endif forAll(pFaces, bpI) { DynList<label> pPoints; @@ -595,12 +685,12 @@ void meshSurfaceEngine::calculatePointPoints() const this->globalToLocalBndPointAddressing(); const VRWGraph& bpAtProcs = this->bpAtProcs(); - std::map<label, labelListPMG> exchangeData; + std::map<label, labelLongList> exchangeData; forAllConstIter(Map<label>, globalToLocal, iter) { const label bpI = iter(); - DynList<label> neiToSend(10); + DynList<label> neiToSend; forAllRow(pointPoints, bpI, j) { const label bpJ = pointPoints(bpI, j); @@ -615,11 +705,11 @@ void meshSurfaceEngine::calculatePointPoints() const continue; if( exchangeData.find(neiProc) == exchangeData.end() ) - exchangeData.insert(std::make_pair(neiProc,labelListPMG())); + exchangeData.insert(std::make_pair(neiProc,labelLongList())); if( neiToSend.size() != 0 ) { - labelListPMG& dts = exchangeData[neiProc]; + labelLongList& dts = exchangeData[neiProc]; dts.append(globalPointLabel[bpI]); dts.append(neiToSend.size()); forAll(neiToSend, i) @@ -628,7 +718,7 @@ void meshSurfaceEngine::calculatePointPoints() const } } - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); label counter(0); @@ -653,24 +743,25 @@ void meshSurfaceEngine::calculatePointNormals() const pointNormalsPtr_ = new vectorField(pFaces.size()); - const label size = pFaces.size(); - # pragma omp parallel for if( size > 1000 ) - for(label pI=0;pI<size;++pI) + # ifdef USE_OMP + # pragma omp parallel for if( pFaces.size() > 1000 ) schedule(dynamic, 50) + # endif + forAll(pFaces, pI) { vector normal(vector::zero); forAllRow(pFaces, pI, pfI) normal += fNormals[pFaces(pI, pfI)]; - const scalar d = mag(normal); - if( d > VSMALL ) - { - normal /= d; - } - else - { - normal = vector::zero; - } + const scalar d = mag(normal); + if( d > VSMALL ) + { + normal /= d; + } + else + { + normal = vector::zero; + } (*pointNormalsPtr_)[pI] = normal; } @@ -680,19 +771,20 @@ void meshSurfaceEngine::calculatePointNormals() const void meshSurfaceEngine::calculateFaceNormals() const { - const faceList::subList& bFaces = this->boundaryFaces(); - const pointFieldPMG& points = mesh_.points(); + const faceList::subList& bFaces = this->boundaryFaces(); + const pointFieldPMG& points = mesh_.points(); - faceNormalsPtr_ = new vectorField(bFaces.size()); + faceNormalsPtr_ = new vectorField(bFaces.size()); - const label size = bFaces.size(); - # pragma omp parallel for if( size > 1000 ) - for(label bfI=0;bfI<size;++bfI) - { - const face& bf = bFaces[bfI]; + # ifdef USE_OMP + # pragma omp parallel for if( bFaces.size() > 1000 ) + # endif + forAll(bFaces, bfI) + { + const face& bf = bFaces[bfI]; - faceNormalsPtr_->operator[](bfI) = bf.normal(points); - } + faceNormalsPtr_->operator[](bfI) = bf.normal(points); + } } void meshSurfaceEngine::calculateFaceCentres() const @@ -700,12 +792,13 @@ void meshSurfaceEngine::calculateFaceCentres() const const faceList::subList& bFaces = this->boundaryFaces(); const pointFieldPMG& points = mesh_.points(); - faceCentresPtr_ = new vectorField(bFaces.size()); + faceCentresPtr_ = new vectorField(bFaces.size()); - const label size = bFaces.size(); - # pragma omp parallel for if( size > 1000 ) - for(label bfI=0;bfI<size;++bfI) - faceCentresPtr_->operator[](bfI) = bFaces[bfI].centre(points); + # ifdef USE_OMP + # pragma omp parallel for if( bFaces.size() > 1000 ) + # endif + forAll(bFaces, bfI) + faceCentresPtr_->operator[](bfI) = bFaces[bfI].centre(points); } void meshSurfaceEngine::updatePointNormalsAtProcBoundaries() const @@ -766,8 +859,10 @@ void meshSurfaceEngine::updatePointNormalsAtProcBoundaries() const } //- normalize vectors + # ifdef USE_OMP # pragma omp parallel for if( bpAtProcs.size() > 1000 ) \ schedule(guided) + # endif forAll(bpAtProcs, bpI) { if( bpAtProcs.sizeOfRow(bpI) == 0 ) @@ -800,19 +895,27 @@ void meshSurfaceEngine::calculateEdgesAndAddressing() const bpEdgesPtr_ = new VRWGraph(); VRWGraph& bpEdges = *bpEdgesPtr_; + # ifdef USE_OMP label nThreads = 3 * omp_get_num_procs(); if( pFaces.size() < 1000 ) nThreads = 1; + # else + const label nThreads(1); + # endif labelList nEdgesForThread(nThreads); label edgeI(0); + # ifdef USE_OMP # pragma omp parallel num_threads(nThreads) + # endif { LongList<edge> edgesHelper; + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(bFaces, bfI) { const face& bf = bFaces[bfI]; @@ -853,22 +956,33 @@ void meshSurfaceEngine::calculateEdgesAndAddressing() const //- this enables other threads to see the number of edges //- generated by each thread - nEdgesForThread[omp_get_thread_num()] = edgesHelper.size(); + # ifdef USE_OMP + const label threadI = omp_get_thread_num(); + # else + const label threadI(0); + # endif + nEdgesForThread[threadI] = edgesHelper.size(); + # ifdef USE_OMP # pragma omp critical + # endif edgeI += edgesHelper.size(); + # ifdef USE_OMP # pragma omp barrier # pragma omp master + # endif edgesPtr_->setSize(edgeI); + # ifdef USE_OMP # pragma omp barrier + # endif //- find the starting position of the edges generated by this thread //- in the global list of edges label localStart(0); - for(label i=0;i<omp_get_thread_num();++i) + for(label i=0;i<threadI;++i) localStart += nEdgesForThread[i]; //- store edges into the global list @@ -892,7 +1006,7 @@ void meshSurfaceEngine::calculateEdgesAndAddressing() const //- boundary faces. This procedure is needed to identify boundary //- edges which are not part of any boundary face on their processor const faceListPMG& faces = mesh_.faces(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); //- send boundary edges to neighbour processors @@ -901,7 +1015,7 @@ void meshSurfaceEngine::calculateEdgesAndAddressing() const const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - labelListPMG dts; + labelLongList dts; for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; @@ -923,11 +1037,11 @@ void meshSurfaceEngine::calculateEdgesAndAddressing() const } OPstream toOtherProc - ( + ( Pstream::blocking, - procBoundaries[patchI].neiProcNo(), - dts.byteSize() - ); + procBoundaries[patchI].neiProcNo(), + dts.byteSize() + ); toOtherProc << dts; } @@ -988,26 +1102,34 @@ void meshSurfaceEngine::calculateFaceEdgesAddressing() const const VRWGraph& pointFaces = this->pointFaces(); faceEdgesPtr_ = new VRWGraph(bFaces.size()); - VRWGraph& faceEdges = *faceEdgesPtr_; + VRWGraph& faceEdges = *faceEdgesPtr_; labelList nfe(bFaces.size()); + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(bFaces, bfI) nfe[bfI] = bFaces[bfI].size(); + # ifdef USE_OMP # pragma omp barrier # pragma omp master + # endif VRWGraphSMPModifier(faceEdges).setSizeAndRowSize(nfe); + # ifdef USE_OMP # pragma omp barrier # pragma omp for schedule(static) + # endif forAll(edges, edgeI) { const edge ee = edges[edgeI]; @@ -1034,7 +1156,7 @@ void meshSurfaceEngine::calculateFaceEdgesAddressing() const void meshSurfaceEngine::calculateEdgeFacesAddressing() const { const faceList::subList& bFaces = this->boundaryFaces(); - const VRWGraph& pointFaces = this->pointFaces(); + const VRWGraph& pointFaces = this->pointFaces(); const edgeList& edges = this->edges(); const labelList& bp = this->bp(); @@ -1043,15 +1165,21 @@ void meshSurfaceEngine::calculateEdgeFacesAddressing() const labelList nef(edges.size()); + # ifdef USE_OMP const label nThreads = 3 * omp_get_num_procs(); # pragma omp parallel num_threads(nThreads) + # endif { + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(nef, edgeI) nef[edgeI] = 0; + # ifdef USE_OMP # pragma omp for schedule(static) + # endif forAll(edges, edgeI) { const edge& ee = edges[edgeI]; @@ -1074,14 +1202,18 @@ void meshSurfaceEngine::calculateEdgeFacesAddressing() const } } + # ifdef USE_OMP # pragma omp barrier # pragma omp master + # endif VRWGraphSMPModifier(edgeFaces).setSizeAndRowSize(nef); + # ifdef USE_OMP # pragma omp barrier # pragma omp for schedule(static) + # endif forAll(edges, edgeI) { const edge& ee = edges[edgeI]; @@ -1109,21 +1241,59 @@ void meshSurfaceEngine::calculateEdgeFacesAddressing() const } } +void meshSurfaceEngine::calculateEdgePatchesAddressing() const +{ + edgePatchesPtr_ = new VRWGraph(); + VRWGraph& edgePatches = *edgePatchesPtr_; + + const VRWGraph& edgeFaces = this->edgeFaces(); + const labelList& facePatch = this->boundaryFacePatches(); + + edgePatches.setSize(edgeFaces.size()); + + forAll(edgeFaces, eI) + { + DynList<label> ePatches; + + forAllRow(edgeFaces, eI, i) + { + const label patchI = facePatch[edgeFaces(eI, i)]; + + ePatches.appendIfNotIn(patchI); + } + + edgePatches.setRow(eI, ePatches); + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = globalToLocalBndEdgeAddressing(); + const Map<label>& otherPatch = this->otherEdgeFacePatch(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + edgePatches.appendIfNotIn(beI, otherPatch[beI]); + } + } +} + void meshSurfaceEngine::calculateFaceFacesAddressing() const { - const VRWGraph& edgeFaces = this->edgeFaces(); + const VRWGraph& edgeFaces = this->edgeFaces(); - const faceList::subList& bFaces = boundaryFaces(); - faceFacesPtr_ = new VRWGraph(bFaces.size()); - VRWGraph& faceFaces = *faceFacesPtr_; + const faceList::subList& bFaces = boundaryFaces(); + faceFacesPtr_ = new VRWGraph(bFaces.size()); + VRWGraph& faceFaces = *faceFacesPtr_; - forAll(bFaces, bfI) - faceFaces.setRowSize(bfI, bFaces[bfI].size()); + forAll(bFaces, bfI) + faceFaces.setRowSize(bfI, bFaces[bfI].size()); - labelList nAppearances(bFaces.size(), 0); + labelList nAppearances(bFaces.size(), 0); - forAll(edgeFaces, efI) - { + forAll(edgeFaces, efI) + { if( edgeFaces.sizeOfRow(efI) == 2 ) { const label f0 = edgeFaces(efI, 0); @@ -1137,17 +1307,17 @@ void meshSurfaceEngine::calculateFaceFacesAddressing() const const label f0 = edgeFaces(efI, 0); faceFaces(f0, nAppearances[f0]++) = -1; } - else if( Pstream::parRun() && (edgeFaces.sizeOfRow(efI) != 0 ) ) - { - FatalErrorIn - ( - "void meshSurfaceEngine::calculateFaceFacesAddressing() const" - ) << "The surface of the mesh is invalid!" - << " The number of faces containing edge " << efI - << " is " << edgeFaces.sizeOfRow(efI) + else if( Pstream::parRun() && (edgeFaces.sizeOfRow(efI) != 0 ) ) + { + FatalErrorIn + ( + "void meshSurfaceEngine::calculateFaceFacesAddressing() const" + ) << "The surface of the mesh is invalid!" + << " The number of faces containing edge " << efI + << " is " << edgeFaces.sizeOfRow(efI) << " Cannot continue" << exit(FatalError); - } - } + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineI.H b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineI.H new file mode 100644 index 0000000000000000000000000000000000000000..dc5d6cfcfd6581d6a6c8e4d1d19b084d98d1686f --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineI.H @@ -0,0 +1,633 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "meshSurfaceEngine.H" +#include "demandDrivenData.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +// #define DEBUGSearch + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +inline const polyMeshGen& meshSurfaceEngine::mesh() const +{ + return mesh_; +} + +inline const pointFieldPMG& meshSurfaceEngine::points() const +{ + return mesh_.points(); +} + +inline const faceListPMG& meshSurfaceEngine::faces() const +{ + return mesh_.faces(); +} + +inline const cellListPMG& meshSurfaceEngine::cells() const +{ + return mesh_.cells(); +} + +inline const labelList& meshSurfaceEngine::bp() const +{ + if( !bppPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelList& meshSurfaceEngine::bp() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateBoundaryFaces(); + calculateBoundaryNodes(); + } + + return *bppPtr_; +} + +inline const labelList& meshSurfaceEngine::boundaryPoints() const +{ + if( !boundaryPointsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelList& meshSurfaceEngine::boundaryPoints() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateBoundaryNodes(); + } + + return *boundaryPointsPtr_; +} + +inline const faceList::subList& meshSurfaceEngine::boundaryFaces() const +{ + if( !boundaryFacesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const faceList::subList&" + "meshSurfaceEngine::boundaryFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateBoundaryFaces(); + } + + return *boundaryFacesPtr_; +} + +inline const labelList& meshSurfaceEngine::boundaryFacePatches() const +{ + if( !boundaryFacePatchPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelList&" + " meshSurfaceEngine::boundaryFacePatches() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateBoundaryFacePatches(); + } + + return *boundaryFacePatchPtr_; +} + +inline const labelList& meshSurfaceEngine::faceOwners() const +{ + if( !boundaryFaceOwnersPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelList& meshSurfaceEngine::faceOwners() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateBoundaryOwners(); + } + + return *boundaryFaceOwnersPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::pointFaces() const +{ + if( !pointFacesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::pointFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculatePointFaces(); + } + + return *pointFacesPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::pointInFaces() const +{ + if( !pointInFacePtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::pointInFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculatePointFaces(); + } + + return *pointInFacePtr_; +} +/* +inline const VRWGraph& meshSurfaceEngine::pointPatches() const +{ + if( !pointPatchesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::pointPatches() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculatePointPatches(); + } + + return *pointPatchesPtr_; +} +*/ + +inline const VRWGraph& meshSurfaceEngine::pointPoints() const +{ + if( !pointPointsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::pointPoints() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculatePointPoints(); + } + + return *pointPointsPtr_; +} + +inline const vectorField& meshSurfaceEngine::pointNormals() const +{ + if( !pointNormalsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const vectorField& meshSurfaceEngine::pointNormals() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculatePointNormals(); + } + + return *pointNormalsPtr_; +} + +inline const vectorField& meshSurfaceEngine::faceNormals() const +{ + if( !faceNormalsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const vectorField& meshSurfaceEngine::faceNormals() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateFaceNormals(); + } + + return *faceNormalsPtr_; +} + +inline const vectorField& meshSurfaceEngine::faceCentres() const +{ + if( !faceCentresPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const vectorField& meshSurfaceEngine::faceCentres() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateFaceCentres(); + } + + return *faceCentresPtr_; +} + +inline const edgeList& meshSurfaceEngine::edges() const +{ + if( !edgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const edgeList& meshSurfaceEngine::edges() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateEdgesAndAddressing(); + } + + return *edgesPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::boundaryPointEdges() const +{ + if( !bpEdgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::boundaryPointEdges() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateEdgesAndAddressing(); + } + + return *bpEdgesPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::edgeFaces() const +{ + if( !edgeFacesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::edgeFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateEdgeFacesAddressing(); + } + + return *edgeFacesPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::faceEdges() const +{ + if( !faceEdgesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::faceEdges() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateFaceEdgesAddressing(); + } + + return *faceEdgesPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::edgePatches() const +{ + if( !edgePatchesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::edgePatches() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateEdgePatchesAddressing(); + } + + return *edgePatchesPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::faceFaces() const +{ + if( !faceFacesPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::faceFaces() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calculateFaceFacesAddressing(); + } + + return *faceFacesPtr_; +} + +inline const labelList& meshSurfaceEngine::globalBoundaryPointLabel() const +{ + if( !globalBoundaryPointLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelList&" + " meshSurfaceEngine::globalBoundaryPointLabel() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryPointLabels(); + } + + return *globalBoundaryPointLabelPtr_; +} + +inline const Map<label>& +meshSurfaceEngine::globalToLocalBndPointAddressing() const +{ + if( !globalBoundaryPointToLocalPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const Map<label>&" + " meshSurfaceEngine::globalToLocalBndPointAddressing() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryPointLabels(); + } + + return *globalBoundaryPointToLocalPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::bpAtProcs() const +{ + if( !globalBoundaryPointLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::bpAtProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryPointLabels(); + } + + return *bpProcsPtr_; +} + +inline const DynList<label>& meshSurfaceEngine::bpNeiProcs() const +{ + if( !bpNeiProcsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const DynList<label>& meshSurfaceEngine::bpNeiProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryPointLabels(); + } + + return *bpNeiProcsPtr_; +} + +inline const labelList& meshSurfaceEngine::globalBoundaryEdgeLabel() const +{ + if( !globalBoundaryEdgeLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelList&" + " meshSurfaceEngine::globalBoundaryEdgeLabel() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryEdgeLabels(); + } + + return *globalBoundaryEdgeLabelPtr_; +} + +inline const Map<label>& +meshSurfaceEngine::globalToLocalBndEdgeAddressing() const +{ + if( !globalBoundaryEdgeToLocalPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const Map<label>&" + " meshSurfaceEngine::globalToLocalBndEdgeAddressing() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryEdgeLabels(); + } + + return *globalBoundaryEdgeToLocalPtr_; +} + +inline const VRWGraph& meshSurfaceEngine::beAtProcs() const +{ + if( !globalBoundaryEdgeLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const VRWGraph& meshSurfaceEngine::beAtProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryEdgeLabels(); + } + + return *beProcsPtr_; +} + +inline const DynList<label>& meshSurfaceEngine::beNeiProcs() const +{ + if( !beNeiProcsPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const DynList<label>& meshSurfaceEngine::beNeiProcs() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryEdgeLabels(); + } + + return *beNeiProcsPtr_; +} + +inline const Map<label>& meshSurfaceEngine::otherEdgeFaceAtProc() const +{ + if( !otherEdgeFaceAtProcPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const Map<label>&" + " meshSurfaceEngine::otherEdgeFaceAtProc() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcAddressingForProcEdges(); + } + + return *otherEdgeFaceAtProcPtr_; +} + +inline const Map<label>& meshSurfaceEngine::otherEdgeFacePatch() const +{ + if( !otherEdgeFacePatchPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const Map<label>&" + " meshSurfaceEngine::otherEdgeFacePatch() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcAddressingForProcEdges(); + } + + return *otherEdgeFacePatchPtr_; +} + +inline const labelList& meshSurfaceEngine::globalBoundaryFaceLabel() const +{ + if( !globalBoundaryFaceLabelPtr_ ) + { + # ifdef USE_OMP + if( omp_in_parallel() ) + FatalErrorIn + ( + "const labelList&" + " meshSurfaceEngine::globalBoundaryFaceLabel() const" + ) << "Calculating addressing inside a parallel region." + << " This is not thread safe" << exit(FatalError); + # endif + + calcGlobalBoundaryFaceLabels(); + } + + return *globalBoundaryFaceLabelPtr_; +} + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.C index b8f1fb2eb5cbe81e8348462b617e20aac7f257ef..6dde1caa2413ec11b062c8425e2da9cc9577d1b0 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,40 +41,36 @@ namespace Foam // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // -// Construct from meshSurfaceEngine. Holds reference! meshSurfaceEngineModifier::meshSurfaceEngineModifier ( - meshSurfaceEngine& surfaceEngine + meshSurfaceEngine& surfaceEngine ) : - surfaceEngine_(surfaceEngine) -{ -} + surfaceEngine_(surfaceEngine) +{} meshSurfaceEngineModifier::meshSurfaceEngineModifier ( - const meshSurfaceEngine& surfaceEngine + const meshSurfaceEngine& surfaceEngine ) : - surfaceEngine_(const_cast<meshSurfaceEngine&>(surfaceEngine)) -{ -} + surfaceEngine_(const_cast<meshSurfaceEngine&>(surfaceEngine)) +{} // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // meshSurfaceEngineModifier::~meshSurfaceEngineModifier() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshSurfaceEngineModifier::moveBoundaryVertexNoUpdate ( - const label bpI, - const point& newP + const label bpI, + const point& newP ) { - surfaceEngine_.mesh_.points()[surfaceEngine_.boundaryPoints()[bpI]] = newP; + surfaceEngine_.mesh_.points()[surfaceEngine_.boundaryPoints()[bpI]] = newP; } void meshSurfaceEngineModifier::moveBoundaryVertex @@ -86,104 +81,104 @@ void meshSurfaceEngineModifier::moveBoundaryVertex { const labelList& bPoints = surfaceEngine_.boundaryPoints(); pointFieldPMG& points = surfaceEngine_.mesh_.points(); - points[bPoints[bpI]] = newP; - + points[bPoints[bpI]] = newP; + if( surfaceEngine_.faceCentresPtr_ ) { vectorField& faceCentres = *surfaceEngine_.faceCentresPtr_; const VRWGraph& pFaces = surfaceEngine_.pointFaces(); - const faceList::subList& bFaces = surfaceEngine_.boundaryFaces(); - + const faceList::subList& bFaces = surfaceEngine_.boundaryFaces(); + forAllRow(pFaces, bpI, pfI) { const label bfI = pFaces(bpI, pfI); - + faceCentres[bfI] = bFaces[bfI].centre(points); } } - + if( surfaceEngine_.faceNormalsPtr_ ) { vectorField& faceNormals = *surfaceEngine_.faceNormalsPtr_; const VRWGraph& pFaces = surfaceEngine_.pointFaces(); - const faceList::subList& bFaces = surfaceEngine_.boundaryFaces(); - + const faceList::subList& bFaces = surfaceEngine_.boundaryFaces(); + forAllRow(pFaces, bpI, pfI) { const label bfI = pFaces(bpI, pfI); - + faceNormals[bfI] = bFaces[bfI].normal(points); } } if( surfaceEngine_.pointNormalsPtr_ ) - { + { const vectorField& faceNormals = *surfaceEngine_.faceNormalsPtr_; - const VRWGraph& pFaces = surfaceEngine_.pointFaces(); - const VRWGraph& pPoints = surfaceEngine_.pointPoints(); - - vectorField& pn = *surfaceEngine_.pointNormalsPtr_; - vector n(vector::zero); - forAllRow(pFaces, bpI, pfI) - n += faceNormals[pFaces(bpI, pfI)]; - - const scalar l = mag(n); - if( l > VSMALL ) - { - n /= l; - } - else - { - n = vector::zero; - } - - pn[bpI] = n; - - //- change normal of vertices connected to bpI - forAllRow(pPoints, bpI, ppI) - { - const label bpJ = pPoints(bpI, ppI); - n = vector::zero; - forAllRow(pFaces, bpJ, pfI) - n += faceNormals[pFaces(bpJ, pfI)]; - - const scalar d = mag(n); - if( d > VSMALL ) - { - n /= d; - } - else - { - n = vector::zero; - } - - pn[bpJ] = n; - } - } + const VRWGraph& pFaces = surfaceEngine_.pointFaces(); + const VRWGraph& pPoints = surfaceEngine_.pointPoints(); + + vectorField& pn = *surfaceEngine_.pointNormalsPtr_; + vector n(vector::zero); + forAllRow(pFaces, bpI, pfI) + n += faceNormals[pFaces(bpI, pfI)]; + + const scalar l = mag(n); + if( l > VSMALL ) + { + n /= l; + } + else + { + n = vector::zero; + } + + pn[bpI] = n; + + //- change normal of vertices connected to bpI + forAllRow(pPoints, bpI, ppI) + { + const label bpJ = pPoints(bpI, ppI); + n = vector::zero; + forAllRow(pFaces, bpJ, pfI) + n += faceNormals[pFaces(bpJ, pfI)]; + + const scalar d = mag(n); + if( d > VSMALL ) + { + n /= d; + } + else + { + n = vector::zero; + } + + pn[bpJ] = n; + } + } } void meshSurfaceEngineModifier::syncVerticesAtParallelBoundaries() { if( !Pstream::parRun() ) return; - + const Map<label>& globalToLocal = surfaceEngine_.globalToLocalBndPointAddressing(); - labelListPMG syncNodes; + labelLongList syncNodes; forAllConstIter(Map<label>, globalToLocal, it) syncNodes.append(it()); - + syncVerticesAtParallelBoundaries(syncNodes); } void meshSurfaceEngineModifier::syncVerticesAtParallelBoundaries ( - const labelListPMG& syncNodes + const labelLongList& syncNodes ) { if( !Pstream::parRun() ) return; - + const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); const labelList& globalLabel = surfaceEngine_.globalBoundaryPointLabel(); @@ -192,84 +187,94 @@ void meshSurfaceEngineModifier::syncVerticesAtParallelBoundaries const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); const pointFieldPMG& points = surfaceEngine_.mesh().points(); - + std::map<label, LongList<labelledPoint> > exchangeData; forAll(neiProcs, i) exchangeData.insert ( std::make_pair(neiProcs[i], LongList<labelledPoint>()) ); - + //- construct the map forAll(syncNodes, snI) { const label bpI = syncNodes[snI]; + + if( bpAtProcs.sizeOfRow(bpI) == 0 ) + continue; + point p = points[bPoints[bpI]] / bpAtProcs.sizeOfRow(bpI); - moveBoundaryVertex(bpI, p); - + moveBoundaryVertexNoUpdate(bpI, p); + forAllRow(bpAtProcs, bpI, i) { const label neiProc = bpAtProcs(bpI, i); if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append(labelledPoint(globalLabel[bpI], p)); } } - + //- exchange the data with other processors LongList<labelledPoint> receivedData; help::exchangeMap(exchangeData, receivedData); - + //- adjust the coordinates forAll(receivedData, i) { const labelledPoint& lp = receivedData[i]; const label bpI = globalToLocal[lp.pointLabel()]; const point newP = points[bPoints[bpI]] + lp.coordinates(); - moveBoundaryVertex(bpI, newP); + moveBoundaryVertexNoUpdate(bpI, newP); } } void meshSurfaceEngineModifier::updateGeometry ( - const labelListPMG& updateBndNodes + const labelLongList& updateBndNodes ) { const pointFieldPMG& points = surfaceEngine_.points(); const faceList::subList& bFaces = surfaceEngine_.boundaryFaces(); const VRWGraph& pFaces = surfaceEngine_.pointFaces(); - + const labelList& bp = surfaceEngine_.bp(); + boolList updateFaces(bFaces.size(), false); - label size = updateBndNodes.size(); - # pragma omp parallel for if( size > 1000 ) - for(label i=0;i<size;++i) + # ifdef USE_OMP + # pragma omp parallel for if( updateBndNodes.size() > 1000 ) + # endif + forAll(updateBndNodes, i) { const label bpI = updateBndNodes[i]; forAllRow(pFaces, bpI, j) updateFaces[pFaces(bpI, j)] = true; } - + if( surfaceEngine_.faceCentresPtr_ ) { vectorField& faceCentres = *surfaceEngine_.faceCentresPtr_; - - size = updateFaces.size(); - # pragma omp parallel for if( size > 1000 ) schedule(dynamic, 100) - for(label bfI=0;bfI<size;++bfI) + + # ifdef USE_OMP + # pragma omp parallel for if( updateFaces.size() > 1000 ) \ + schedule(dynamic, 100) + # endif + forAll(updateFaces, bfI) { if( updateFaces[bfI] ) faceCentres[bfI] = bFaces[bfI].centre(points); } } - + if( surfaceEngine_.faceNormalsPtr_ ) { vectorField& faceNormals = *surfaceEngine_.faceNormalsPtr_; - - size = updateFaces.size(); - # pragma omp parallel for if( size > 1000 ) schedule(dynamic, 100) - for(label bfI=0;bfI<size;++bfI) + + # ifdef USE_OMP + # pragma omp parallel for if( updateFaces.size() > 1000 ) \ + schedule(dynamic, 100) + # endif + forAll(updateFaces, bfI) { if( updateFaces[bfI] ) faceNormals[bfI] = bFaces[bfI].normal(points); @@ -277,21 +282,39 @@ void meshSurfaceEngineModifier::updateGeometry } if( surfaceEngine_.pointNormalsPtr_ ) - { + { const vectorField& faceNormals = surfaceEngine_.faceNormals(); - const VRWGraph& pFaces = surfaceEngine_.pointFaces(); - - vectorField& pn = *surfaceEngine_.pointNormalsPtr_; - size = updateBndNodes.size(); - # pragma omp parallel for if( size > 1000 ) schedule(dynamic, 100) - for(label i=0;i<size;++i) + + boolList updateBndPoint(pFaces.size(), false); + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(updateBndNodes, i) { const label bpI = updateBndNodes[i]; - + + forAllRow(pFaces, bpI, pfI) + { + const face& bf = bFaces[pFaces(bpI, pfI)]; + + forAll(bf, pI) + updateBndPoint[bp[bf[pI]]] = true; + } + } + + vectorField& pn = *surfaceEngine_.pointNormalsPtr_; + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 100) + # endif + forAll(updateBndPoint, bpI) + { + if( !updateBndPoint[bpI] ) + continue; + vector n(vector::zero); forAllRow(pFaces, bpI, pfI) n += faceNormals[pFaces(bpI, pfI)]; - + const scalar l = mag(n); if( l > VSMALL ) { @@ -301,20 +324,122 @@ void meshSurfaceEngineModifier::updateGeometry { n = vector::zero; } - + pn[bpI] = n; } - } + + if( Pstream::parRun() ) + { + //- update point normals at inter-processor boundaries + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndPointAddressing(); + const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); + const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); + + //- make sure that the points ar updated on all processors + std::map<label, labelLongList> exchangeNodeLabels; + forAll(neiProcs, i) + exchangeNodeLabels[neiProcs[i]].clear(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + if( updateBndPoint[bpI] ) + { + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeNodeLabels[neiProc].append(it.key()); + } + } + } + + labelLongList receivedNodes; + help::exchangeMap(exchangeNodeLabels, receivedNodes); + + forAll(receivedNodes, i) + updateBndPoint[globalToLocal[receivedNodes[i]]] = true; + + + //- start updating point normals + std::map<label, LongList<labelledPoint> > exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + //- prepare data for sending + forAllConstIter(Map<label>, globalToLocal, iter) + { + const label bpI = iter(); + + if( !updateBndPoint[bpI] ) + continue; + + vector& n = pn[bpI]; + n = vector::zero; + + forAllRow(pFaces, bpI, pfI) + n += faceNormals[pFaces(bpI, pfI)]; + + forAllRow(bpAtProcs, bpI, procI) + { + const label neiProc = bpAtProcs(bpI, procI); + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append(labelledPoint(iter.key(), n)); + } + } + + //- exchange data with other procs + LongList<labelledPoint> receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const label bpI = globalToLocal[receivedData[i].pointLabel()]; + pn[bpI] += receivedData[i].coordinates(); + } + + //- normalize vectors + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + if( !updateBndPoint[bpI] ) + continue; + + vector normal = pn[bpI]; + const scalar d = mag(normal); + if( d > VSMALL ) + { + normal /= d; + } + else + { + normal = vector::zero; + } + + pn[bpI] = normal; + } + } + } } void meshSurfaceEngineModifier::updateGeometry() { - labelListPMG updateBndNodes(surfaceEngine_.boundaryPoints().size()); - + labelLongList updateBndNodes(surfaceEngine_.boundaryPoints().size()); + + # ifdef USE_OMP # pragma omp parallel for if( updateBndNodes.size() > 10000 ) + # endif forAll(updateBndNodes, bpI) updateBndNodes[bpI] = bpI; - + updateGeometry(updateBndNodes); } diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.H b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.H index 14adb707685a492116b8c81c55710838336cc1cb..5d8c9c01c050af59eef376d93174e8f3e913bf9c 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineModifier.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceEngineModifier @@ -44,14 +43,14 @@ namespace Foam { /*---------------------------------------------------------------------------*\ - Class meshSurfaceEngineModifier Declaration + Class meshSurfaceEngineModifier Declaration \*---------------------------------------------------------------------------*/ class meshSurfaceEngineModifier { // Private data //- reference to the meshSurfaceEngine - meshSurfaceEngine& surfaceEngine_; + meshSurfaceEngine& surfaceEngine_; //- Disallow default bitwise copy construct meshSurfaceEngineModifier(const meshSurfaceEngineModifier&); @@ -60,26 +59,26 @@ class meshSurfaceEngineModifier void operator=(const meshSurfaceEngineModifier&); public: - + // Constructors //- Construct from reference to meshSurfaceEngine meshSurfaceEngineModifier(meshSurfaceEngine& surfaceEngine); - //- Construct from const reference to meshSurfaceEngine - meshSurfaceEngineModifier(const meshSurfaceEngine& surfaceEngine); + //- Construct from const reference to meshSurfaceEngine + meshSurfaceEngineModifier(const meshSurfaceEngine& surfaceEngine); // Destructor ~meshSurfaceEngineModifier(); // Member Functions - - //- relocate the selected boundary vertex - void moveBoundaryVertexNoUpdate(const label bpI, const point& newP); - + + //- relocate the selected boundary vertex + void moveBoundaryVertexNoUpdate(const label bpI, const point& newP); + //- relocate the selected boundary vertex and update geometry data - void moveBoundaryVertex(const label bpI, const point& newP); + void moveBoundaryVertex(const label bpI, const point& newP); //- update normals of boundary vertices at processor boundaries inline void updateVertexNormals() @@ -90,13 +89,13 @@ public: //- updates faceCentres, face normal, and point normals //- of the boundary faces attached to the selected boundary points - void updateGeometry(const labelListPMG&); + void updateGeometry(const labelLongList&); void updateGeometry(); //- makes sure that all surface vertices at parallel boundaries //- have the same coordinates void syncVerticesAtParallelBoundaries(); - void syncVerticesAtParallelBoundaries(const labelListPMG&); + void syncVerticesAtParallelBoundaries(const labelLongList&); }; diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineParallelAddressing.C b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineParallelAddressing.C index 2d773de4b121733b169a4634e0c1a9f3ab26b4b8..b0c778fe70119b300f10b5e37151765469d1b23d 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineParallelAddressing.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceEngine/meshSurfaceEngineParallelAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,6 +32,7 @@ Description #include "helperFunctionsPar.H" #include <map> +#include <set> // #define DEBUGSearch @@ -40,39 +40,39 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const { if( !globalBoundaryPointLabelPtr_ ) globalBoundaryPointLabelPtr_ = new labelList(); - + const labelList& bPoints = this->boundaryPoints(); labelList& globalPointLabel = *globalBoundaryPointLabelPtr_; globalPointLabel.setSize(bPoints.size()); globalPointLabel = -1; - + if( !bpProcsPtr_ ) bpProcsPtr_ = new VRWGraph(bPoints.size()); - + if( !globalBoundaryPointToLocalPtr_ ) globalBoundaryPointToLocalPtr_ = new Map<label>(); - + if( !bpNeiProcsPtr_ ) - bpNeiProcsPtr_ = new DynList<label>(10); - + bpNeiProcsPtr_ = new DynList<label>(); + if( !Pstream::parRun() ) return; - + VRWGraph& bpAtProcs = *bpProcsPtr_; - + //- find local points for the given processor const faceListPMG& faces = mesh_.faces(); const labelList& bp = this->bp(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - + //- find which processor contain a given bnd point forAll(procBoundaries, patchI) { @@ -97,20 +97,20 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const } } } - + //- exchange data with other processor and update bpAtProcs //- continue this process as long as there is some change bool finished; do { finished = true; - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - - labelListPMG dts; + + labelLongList dts; labelHashSet addedPoint; for(label faceI=start;faceI<end;++faceI) { @@ -132,16 +132,16 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const dts.append(bpAtProcs(bpI, i)); } } - + OPstream toOtherProc - ( + ( Pstream::blocking, - procBoundaries[patchI].neiProcNo(), - dts.byteSize() - ); + procBoundaries[patchI].neiProcNo(), + dts.byteSize() + ); toOtherProc << dts; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -151,9 +151,9 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { @@ -171,7 +171,7 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const } } } - + reduce(finished, minOp<bool>()); } while( !finished ); @@ -185,7 +185,7 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const forAllRow(bpAtProcs, bpI, procI) if( bpAtProcs(bpI, procI) < pMin ) pMin = bpAtProcs(bpI, procI); - + if( pMin == Pstream::myProcNo() ) { ++nLocalPoints; @@ -199,7 +199,7 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const { ++nLocalPoints; } - + //- give local points their labels label startPoint(0); labelList nPointsAtProc(Pstream::nProcs()); @@ -212,18 +212,18 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const forAll(localPoints, pI) if( localPoints[pI] ) globalPointLabel[pI] = startPoint++; - + //- send labels to non-local points do { finished = true; - + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); - - labelListPMG dts; + + labelLongList dts; labelHashSet addedPoint; for(label faceI=start;faceI<end;++faceI) { @@ -235,7 +235,7 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const { if( addedPoint.found(bpI) ) continue; - + addedPoint.insert(bpI); //- data is sent as follows //- 1. face position in patch @@ -247,16 +247,16 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const } } } - + OPstream toOtherProc - ( + ( Pstream::blocking, - procBoundaries[patchI].neiProcNo(), - dts.byteSize() - ); + procBoundaries[patchI].neiProcNo(), + dts.byteSize() + ); toOtherProc << dts; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -266,16 +266,16 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { const face& f = faces[start+receivedData[counter++]]; const label pI = receivedData[counter++]; const label globalLabel = receivedData[counter++]; - + if( globalPointLabel[bp[f[pI]]] == -1 ) { globalPointLabel[bp[f[pI]]] = globalLabel; @@ -288,32 +288,32 @@ void meshSurfaceEngine::calcGlobalBoundaryPointLabels() const "void meshSurfaceEngine::" "calcGlobalBoundaryPointLabels() const" ) << "Point labels in proc boundary " - << procBoundaries[patchI].patchName() - << " face " << f << " pI = " << pI - << nl << " label " << globalPointLabel[bp[f[pI]]] - << nl << " other global label " << globalLabel - << " do not match!" << abort(FatalError); + << procBoundaries[patchI].patchName() + << " face " << f << " pI = " << pI + << nl << " label " << globalPointLabel[bp[f[pI]]] + << nl << " other global label " << globalLabel + << " do not match!" << abort(FatalError); } } } - + reduce(finished, minOp<bool>()); } while( !finished ); - + //- create globalToLocal addressing forAll(bpAtProcs, bpI) { if( bpAtProcs.sizeOfRow(bpI) != 0 ) { globalBoundaryPointToLocalPtr_->insert(globalPointLabel[bpI], bpI); - + forAllRow(bpAtProcs, bpI, j) { const label procI = bpAtProcs(bpI, j); - + if( procI == Pstream::myProcNo() ) continue; - + bpNeiProcsPtr_->appendIfNotIn(procI); } } @@ -324,34 +324,37 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const { if( !globalBoundaryEdgeLabelPtr_ ) globalBoundaryEdgeLabelPtr_ = new labelList(); - + const edgeList& bEdges = this->edges(); - + labelList& globalEdgeLabel = *globalBoundaryEdgeLabelPtr_; globalEdgeLabel.setSize(bEdges.size()); globalEdgeLabel = -1; - + if( !beProcsPtr_ ) beProcsPtr_ = new VRWGraph(bEdges.size()); - + if( !globalBoundaryEdgeToLocalPtr_ ) globalBoundaryEdgeToLocalPtr_ = new Map<label>(); - + if( !beNeiProcsPtr_ ) - beNeiProcsPtr_ = new DynList<label>(10); - + beNeiProcsPtr_ = new DynList<label>(); + if( !Pstream::parRun() ) return; - + VRWGraph& beAtProcs = *beProcsPtr_; - + const faceListPMG& faces = mesh_.faces(); const labelList& bp = this->bp(); const VRWGraph& pEdges = this->boundaryPointEdges(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); - + //- find which processors contain a given bnd edge + typedef std::set<std::pair<label, label> > procEdgeMap; + List<procEdgeMap> facesWithProcBndEdges(procBoundaries.size()); + forAll(procBoundaries, patchI) { const label start = procBoundaries[patchI].patchStart(); @@ -359,12 +362,13 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; + forAll(f, eI) { - const edge e = f.faceEdge(eI); - - if( bp[e.start()] != -1 ) + if( bp[f[eI]] != -1 ) { + const edge e = f.faceEdge(eI); + const label bpI = bp[e.start()]; label edgeI(-1); forAllRow(pEdges, bpI, peI) @@ -373,9 +377,14 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const edgeI = pEdges(bpI, peI); break; } - + if( edgeI != -1 ) { + facesWithProcBndEdges[patchI].insert + ( + std::make_pair(faceI, eI) + ); + beAtProcs.appendIfNotIn ( edgeI, @@ -391,64 +400,63 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const } } } - + //- exchange data with other processor and update beAtProcs //- continue this process as long as there is some change bool finished; do { finished = true; - - forAll(procBoundaries, patchI) + + forAll(facesWithProcBndEdges, patchI) { const label start = procBoundaries[patchI].patchStart(); - const label end = start + procBoundaries[patchI].patchSize(); - - labelListPMG dts; - for(label faceI=start;faceI<end;++faceI) + const procEdgeMap& procBndEdges = facesWithProcBndEdges[patchI]; + + labelLongList dts; + forAllConstIter(procEdgeMap, procBndEdges, it) { - const face& f = faces[faceI]; - forAll(f, eI) + const std::pair<label, label>& fPair = *it; + + const face& f = faces[fPair.first]; + const edge e = f.faceEdge(fPair.second); + + if( bp[e.start()] != -1 ) { - const edge e = f.faceEdge(eI); - - if( bp[e.start()] != -1 ) - { - const label bpI = bp[e.start()]; - label edgeI(-1); - forAllRow(pEdges, bpI, peI) - if( bEdges[pEdges(bpI, peI)] == e ) - { - edgeI = pEdges(bpI, peI); - break; - } - - if( edgeI != -1 ) + const label bpI = bp[e.start()]; + label edgeI(-1); + forAllRow(pEdges, bpI, peI) + if( bEdges[pEdges(bpI, peI)] == e ) { - //- data is sent as follows - //- 1. face position in patch - //- 2. local edge position in face - //- 3. number of processors for edge - //- 4. proc labels - dts.append(faceI-start); - dts.append((f.size()-eI-1)%f.size()); - dts.append(beAtProcs.sizeOfRow(edgeI)); - forAllRow(beAtProcs, edgeI, i) - dts.append(beAtProcs(edgeI, i)); + edgeI = pEdges(bpI, peI); + break; } + + if( edgeI != -1 ) + { + //- data is sent as follows + //- 1. face position in patch + //- 2. local edge position in face + //- 3. number of processors for edge + //- 4. proc labels + dts.append(fPair.first-start); + dts.append((f.size()-fPair.second-1)%f.size()); + dts.append(beAtProcs.sizeOfRow(edgeI)); + forAllRow(beAtProcs, edgeI, i) + dts.append(beAtProcs(edgeI, i)); } } } - + OPstream toOtherProc - ( + ( Pstream::blocking, - procBoundaries[patchI].neiProcNo(), - dts.byteSize() - ); + procBoundaries[patchI].neiProcNo(), + dts.byteSize() + ); toOtherProc << dts; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -458,37 +466,43 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { - const face& f = faces[start+receivedData[counter++]]; + const label faceI = start+receivedData[counter++]; + const face& f = faces[faceI]; const label eI = receivedData[counter++]; - + const edge e = f.faceEdge(eI); label edgeI(-1); forAllRow(pEdges, bp[e.start()], peI) if( bEdges[pEdges(bp[e.start()], peI)] == e ) edgeI = pEdges(bp[e.start()], peI); - + const label nProcs = receivedData[counter++]; for(label i=0;i<nProcs;++i) { const label neiProc = receivedData[counter++]; if( !beAtProcs.contains(edgeI, neiProc) ) { + facesWithProcBndEdges[patchI].insert + ( + std::make_pair(faceI, eI) + ); + beAtProcs.append(edgeI, neiProc); finished = false; } } } } - + reduce(finished, minOp<bool>()); } while( !finished ); - + //- start calculating global edge labels label nLocalEdges(0); boolList localEdges(bEdges.size(), true); @@ -499,7 +513,7 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const forAllRow(beAtProcs, bpI, procI) if( beAtProcs(bpI, procI) < pMin ) pMin = beAtProcs(bpI, procI); - + if( pMin == Pstream::myProcNo() ) { ++nLocalEdges; @@ -513,7 +527,7 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const { ++nLocalEdges; } - + //- give local points their labels label startEdge(0); labelList nEdgesAtProc(Pstream::nProcs()); @@ -522,7 +536,7 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const Pstream::scatterList(nEdgesAtProc); for(label i=0;i<Pstream::myProcNo();++i) startEdge += nEdgesAtProc[i]; - + forAll(localEdges, pI) if( localEdges[pI] ) globalEdgeLabel[pI] = startEdge++; @@ -531,54 +545,54 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const do { finished = true; - - forAll(procBoundaries, patchI) + + forAll(facesWithProcBndEdges, patchI) { const label start = procBoundaries[patchI].patchStart(); - const label end = start + procBoundaries[patchI].patchSize(); - - labelListPMG dts; - for(label faceI=start;faceI<end;++faceI) + const procEdgeMap& procBndEdges = facesWithProcBndEdges[patchI]; + + labelLongList dts; + forAllConstIter(procEdgeMap, procBndEdges, it) { + const label faceI = it->first; const face& f = faces[faceI]; - forAll(f, eI) + + const label eI = it->second; + const edge e = f.faceEdge(eI); + + if( bp[e.start()] != -1 ) { - const edge e = f.faceEdge(eI); - - if( bp[e.start()] != -1 ) - { - const label bpI = bp[e.start()]; - label edgeI(-1); - forAllRow(pEdges, bpI, peI) - if( bEdges[pEdges(bpI, peI)] == e ) - { - edgeI = pEdges(bpI, peI); - break; - } - - if( (edgeI != -1) && (globalEdgeLabel[edgeI] != -1) ) + const label bpI = bp[e.start()]; + label edgeI(-1); + forAllRow(pEdges, bpI, peI) + if( bEdges[pEdges(bpI, peI)] == e ) { - //- data is sent as follows - //- 1. face position in patch - //- 2. local edge position in face - //- 3. global edge label - dts.append(faceI-start); - dts.append((f.size()-eI-1)%f.size()); - dts.append(globalEdgeLabel[edgeI]); + edgeI = pEdges(bpI, peI); + break; } + + if( (edgeI != -1) && (globalEdgeLabel[edgeI] != -1) ) + { + //- data is sent as follows + //- 1. face position in patch + //- 2. local edge position in face + //- 3. global edge label + dts.append(faceI-start); + dts.append((f.size()-eI-1)%f.size()); + dts.append(globalEdgeLabel[edgeI]); } } } - + OPstream toOtherProc - ( + ( Pstream::blocking, - procBoundaries[patchI].neiProcNo(), - dts.byteSize() - ); + procBoundaries[patchI].neiProcNo(), + dts.byteSize() + ); toOtherProc << dts; } - + forAll(procBoundaries, patchI) { IPstream fromOtherProc @@ -588,23 +602,23 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const ); labelList receivedData; fromOtherProc >> receivedData; - + const label start = procBoundaries[patchI].patchStart(); - + label counter(0); while( counter < receivedData.size() ) { const face& f = faces[start+receivedData[counter++]]; const label eI = receivedData[counter++]; - + const edge e = f.faceEdge(eI); label edgeI(-1); forAllRow(pEdges, bp[e.start()], peI) if( bEdges[pEdges(bp[e.start()], peI)] == e ) edgeI = pEdges(bp[e.start()], peI); - + const label globalLabel = receivedData[counter++]; - + if( globalEdgeLabel[edgeI] == -1 ) { globalEdgeLabel[edgeI] = globalLabel; @@ -620,29 +634,28 @@ void meshSurfaceEngine::calcGlobalBoundaryEdgeLabels() const } } } - + reduce(finished, minOp<bool>()); } while( !finished ); - + //- create globalToLocal addressing forAll(beAtProcs, beI) { if( beAtProcs.sizeOfRow(beI) != 0 ) { globalBoundaryEdgeToLocalPtr_->insert(globalEdgeLabel[beI], beI); - + forAllRow(beAtProcs, beI, j) { const label procI = beAtProcs(beI, j); - + if( procI == Pstream::myProcNo() ) continue; - + beNeiProcsPtr_->appendIfNotIn(procI); } } } - } void meshSurfaceEngine::calcAddressingForProcEdges() const @@ -652,23 +665,67 @@ void meshSurfaceEngine::calcAddressingForProcEdges() const const VRWGraph& eFaces = this->edgeFaces(); const VRWGraph& beAtProcs = this->beAtProcs(); const Map<label>& globalToLocal = this->globalToLocalBndEdgeAddressing(); - - std::map<label, labelListPMG> exchangeData; + const DynList<label>& beNeiProcs = this->beNeiProcs(); + + std::map<label, labelLongList> exchangeData; + forAll(beNeiProcs, i) + exchangeData.insert(std::make_pair(beNeiProcs[i], labelLongList())); + //- check if it the surface is manifold over inter-processor edges + Map<label> nFacesAtEdge; forAllConstIter(Map<label>, globalToLocal, iter) { const label beI = iter(); - + nFacesAtEdge.insert(beI, eFaces.sizeOfRow(beI)); + + forAllRow(beAtProcs, beI, i) + { + const label neiProc = beAtProcs(beI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + labelLongList& dts = exchangeData[neiProc]; + dts.append(iter.key()); + dts.append(eFaces.sizeOfRow(beI)); + } + } + + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + for(label counter=0;counter<receivedData.size();) + { + const label beI = globalToLocal[receivedData[counter++]]; + nFacesAtEdge[beI] += receivedData[counter++]; + } + + forAllConstIter(Map<label>, nFacesAtEdge, iter) + { + if( iter() != 2 ) + FatalErrorIn + ( + "void meshSurfaceEngine::calcAddressingForProcEdges() const" + ) << "Surface is not manifold at boundary edge " + << iter.key() << exit(FatalError); + } + + //- find the processor which contains other face containing an edge + //- at inter-processor boundary + exchangeData.clear(); + forAll(beNeiProcs, i) + exchangeData.insert(std::make_pair(beNeiProcs[i], labelLongList())); + + forAllConstIter(Map<label>, globalToLocal, iter) + { + const label beI = iter(); + forAllRow(beAtProcs, beI, procI) { const label neiProc = beAtProcs(beI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - - if( exchangeData.find(neiProc) == exchangeData.end() ) - exchangeData.insert(std::make_pair(neiProc, labelListPMG())); - + if( eFaces.sizeOfRow(beI) == 1 ) { exchangeData[neiProc].append(globalEdgeLabel[beI]); @@ -679,7 +736,7 @@ void meshSurfaceEngine::calcAddressingForProcEdges() const } } } - + //- exchange edge-face patches with other processors std::map<label, labelList> receivedMap; help::exchangeMap(exchangeData, receivedMap); @@ -715,17 +772,17 @@ void meshSurfaceEngine::calcAddressingForProcEdges() const void meshSurfaceEngine::calcGlobalBoundaryFaceLabels() const { const faceList::subList& bFaces = boundaryFaces(); - + if( !globalBoundaryFaceLabelPtr_ ) globalBoundaryFaceLabelPtr_ = new labelList(bFaces.size()); - + labelList& globalFaceLabel = *globalBoundaryFaceLabelPtr_; - + labelList nFacesAtProc(Pstream::nProcs()); nFacesAtProc[Pstream::myProcNo()] = bFaces.size(); Pstream::gatherList(nFacesAtProc); Pstream::scatterList(nFacesAtProc); - + label startFace(0); for(label i=0;i<Pstream::myProcNo();++i) startFace += nFacesAtProc[i]; diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.C b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.C index d60f30d81fda8a117e7cbb60eb7b56b22d4234a6..b1bfbb60e9479b572defe7dec441003b34dfc4de 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -55,7 +54,8 @@ void meshSurfaceMapper::createTriSurfacePartitioner() const void meshSurfaceMapper::clearOut() { - deleteDemandDrivenData(surfaceEnginePartitionerPtr_); + if( deletePartitioner_ ) + deleteDemandDrivenData(surfaceEnginePartitionerPtr_); deleteDemandDrivenData(surfPartitionerPtr_); } @@ -70,6 +70,27 @@ meshSurfaceMapper::meshSurfaceMapper surfaceEngine_(mse), meshOctree_(octree), surfaceEnginePartitionerPtr_(NULL), + deletePartitioner_(true), + surfPartitionerPtr_(NULL) +{ + if( Pstream::parRun() ) + { + //- allocate bpAtProcs and other addressing + //- this is done here to prevent possible deadlocks + surfaceEngine_.bpAtProcs(); + } +} + +meshSurfaceMapper::meshSurfaceMapper +( + const meshSurfacePartitioner& mPart, + const meshOctree& octree +) +: + surfaceEngine_(mPart.surfaceEngine()), + meshOctree_(octree), + surfaceEnginePartitionerPtr_(&mPart), + deletePartitioner_(false), surfPartitionerPtr_(NULL) { if( Pstream::parRun() ) diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.H b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.H index ee3770248a260d531fcc2a66a140b462a4f2c8a0..433c73b667f2c416b050811e10543d8704b7af67 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapper.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfaceMapper @@ -38,7 +37,7 @@ SourceFiles #include "labelList.H" #include "pointField.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "parMapperHelper.H" #include <map> @@ -68,7 +67,8 @@ class meshSurfaceMapper const meshOctree& meshOctree_; //- mesh surface partitioner - mutable meshSurfacePartitioner* surfaceEnginePartitionerPtr_; + mutable const meshSurfacePartitioner* surfaceEnginePartitionerPtr_; + const bool deletePartitioner_; //- triSurface partitioner mutable triSurfacePartitioner* surfPartitionerPtr_; @@ -99,19 +99,19 @@ class meshSurfaceMapper // Private member functions //- map corner nodes to the boundary - void mapCorners(const labelListPMG& nodesToMap); + void mapCorners(const labelLongList& nodesToMap); //- find mapping distance for selected points void findMappingDistance ( - const labelListPMG& nodesToMap, + const labelLongList& nodesToMap, std::map<label, scalar>& mappingDistance ) const; // Private member functions needed for parallel execution //- check if nodes at parallel boundaries are selected at all processors - void selectNodesAtParallelBnd(const labelListPMG&); + void selectNodesAtParallelBnd(const labelLongList&); //- map to the smallest distance //- makes sense for parallel calculations, only @@ -130,6 +130,9 @@ public: //- Construct from meshSurfaceEngine and octree meshSurfaceMapper(const meshSurfaceEngine&, const meshOctree&); + //- Construct from meshSurfacePartitioner and octree + meshSurfaceMapper(const meshSurfacePartitioner&, const meshOctree&); + // Destructor ~meshSurfaceMapper(); @@ -145,7 +148,7 @@ public: //- projects selected surface vertices to their nearest location //- on the surface mesh - void mapVerticesOntoSurface(const labelListPMG& nodesToMap); + void mapVerticesOntoSurface(const labelLongList& nodesToMap); //- projects corner and edge vertices onto their nearest location //- on the surface mesh @@ -153,7 +156,7 @@ public: //- projects selected edge vertices onto their nearest //- locations on the surface mesh - void mapEdgeNodes(const labelListPMG& nodesToMap); + void mapEdgeNodes(const labelLongList& nodesToMap); //- projects surface vertices onto the surface with respect //- to the surface patch they belong to. Edges and corner are respected @@ -161,7 +164,7 @@ public: //- projects selected surface vertices onto the surface with respect //- to the surface patch they belong to. Edges and corner are respected - void mapVerticesOntoSurfacePatches(const labelListPMG& nodesToMap); + void mapVerticesOntoSurfacePatches(const labelLongList& nodesToMap); //- a combination of mapping and smoothing intended for better //- feature capturing diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperCornersAndEdges.C b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperCornersAndEdges.C index 811104e50134c985be09c0206095296561fd2883..4d1f0c1056d70648f6f9e42c3d34f2759fcd1f1c 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperCornersAndEdges.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperCornersAndEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,7 +35,10 @@ Description #include "labelledScalar.H" #include "helperFunctionsPar.H" + +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGMapping @@ -44,12 +46,12 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshSurfaceMapper::findMappingDistance ( - const labelListPMG& nodesToMap, + const labelLongList& nodesToMap, std::map<label, scalar>& mappingDistance ) const { @@ -57,27 +59,27 @@ void meshSurfaceMapper::findMappingDistance const VRWGraph& pFaces = surfaceEngine_.pointFaces(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); const pointFieldPMG& points = surfaceEngine_.points(); - + //- generate search distance for corner nodes mappingDistance.clear(); forAll(nodesToMap, i) { const label bpI = nodesToMap[i]; - + mappingDistance.insert(std::make_pair(bpI, 0.0)); std::map<label, scalar>::iterator mIter = mappingDistance.find(bpI); - + const point& p = points[bPoints[bpI]]; forAllRow(pFaces, bpI, pfI) { const scalar d = magSqr(faceCentres[pFaces(bpI, pfI)] - p); mIter->second = Foam::max(mIter->second, d); } - + //- safety factor mIter->second *= 4.0; } - + if( Pstream::parRun() ) { //- make sure that corner nodesd at parallel boundaries @@ -87,7 +89,7 @@ void meshSurfaceMapper::findMappingDistance surfaceEngine_.globalBoundaryPointLabel(); const Map<label>& globalToLocal = surfaceEngine_.globalToLocalBndPointAddressing(); - + //- create the map for exchanging data std::map<label, DynList<labelledScalar> > exchangeData; const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); @@ -95,107 +97,113 @@ void meshSurfaceMapper::findMappingDistance exchangeData.insert ( std::make_pair(neiProcs[i], DynList<labelledScalar>())); - + forAll(nodesToMap, nI) { const label bpI = nodesToMap[nI]; - + forAllRow(bpAtProcs, bpI, i) { const label neiProc = bpAtProcs(bpI, i); if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append ( labelledScalar(globalPointLabel[bpI], mappingDistance[bpI]) ); } } - + //- exchange data between processors LongList<labelledScalar> receivedData; help::exchangeMap(exchangeData, receivedData); - + //- select the maximum mapping distance for processor points forAll(receivedData, i) { const labelledScalar& ls = receivedData[i]; - + const label bpI = globalToLocal[ls.scalarLabel()]; - + //- choose the maximum value for the mapping distance std::map<label, scalar>::iterator mIter = mappingDistance.find(bpI); mIter->second = Foam::max(mIter->second, ls.value()); } } } - -void meshSurfaceMapper::mapCorners(const labelListPMG& nodesToMap) + +void meshSurfaceMapper::mapCorners(const labelLongList& nodesToMap) { const triSurfacePartitioner& sPartitioner = surfacePartitioner(); const labelList& surfCorners = sPartitioner.corners(); - const pointField& sPoints = meshOctree_.surface().localPoints(); + const pointField& sPoints = meshOctree_.surface().points(); const List<DynList<label> >& cornerPatches = sPartitioner.cornerPatches(); - + const meshSurfacePartitioner& mPart = meshPartitioner(); const labelHashSet& corners = mPart.corners(); - + const VRWGraph& pPatches = mPart.pointPatches(); + const pointFieldPMG& points = surfaceEngine_.points(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pPatches = surfaceEngine_.pointPatches(); - + std::map<label, scalar> mappingDistance; findMappingDistance(nodesToMap, mappingDistance); - + //- for every corner in the mesh surface find the nearest corner in the //- triSurface meshSurfaceEngineModifier sMod(surfaceEngine_); - - const label size = nodesToMap.size(); - # pragma omp parallel for if( size > 10 ) - for(label cornerI=0;cornerI<size;++cornerI) + + # ifdef USE_OMP + # pragma omp parallel for if( nodesToMap.size() > 10 ) + # endif + forAll(nodesToMap, cornerI) { const label bpI = nodesToMap[cornerI]; if( !corners.found(bpI) ) FatalErrorIn ( - "meshSurfaceMapper::mapCorners(const labelListPMG&)" + "meshSurfaceMapper::mapCorners(const labelLongList&)" ) << "Trying to map a point that is not a corner" << abort(FatalError); - + const point& p = points[bPoints[bpI]]; const scalar maxDist = mappingDistance[bpI]; - + //- find the nearest position to the given point patches + const DynList<label> patches = pPatches[bpI]; + point mapPointApprox(p); scalar distSqApprox; + label iter(0); while( iter++ < 20 ) { point newP(vector::zero); - forAllRow(pPatches, bpI, patchI) + forAll(patches, patchI) { point np; + label nt; meshOctree_.findNearestSurfacePointInRegion ( np, distSqApprox, - pPatches(bpI, patchI), + nt, + patches[patchI], mapPointApprox ); - + newP += np; } - - newP /= pPatches.sizeOfRow(bpI); + + newP /= patches.size(); if( magSqr(newP - mapPointApprox) < 1e-8 * maxDist ) break; - + mapPointApprox = newP; } distSqApprox = magSqr(mapPointApprox - p); - + //- find the nearest triSurface corner for the given corner scalar distSq(mappingDistance[bpI]); point mapPoint(p); @@ -203,20 +211,20 @@ void meshSurfaceMapper::mapCorners(const labelListPMG& nodesToMap) { const label cornerID = surfCorners[scI]; const point& sp = sPoints[cornerID]; - + if( Foam::magSqr(sp - p) < distSq ) { bool store(true); const DynList<label>& cPatches = cornerPatches[scI]; - forAllRow(pPatches, bpI, i) + forAll(patches, i) { - if( !cPatches.contains(pPatches(bpI, i)) ) + if( !cPatches.contains(patches[i]) ) { store = false; break; } } - + if( store ) { mapPoint = sp; @@ -224,52 +232,54 @@ void meshSurfaceMapper::mapCorners(const labelListPMG& nodesToMap) } } } - + if( distSq > 1.2 * distSqApprox ) { mapPoint = mapPointApprox; } - + //- move the point to the nearest corner sMod.moveBoundaryVertexNoUpdate(bpI, mapPoint); } - + sMod.updateGeometry(nodesToMap); } -void meshSurfaceMapper::mapEdgeNodes(const labelListPMG& nodesToMap) +void meshSurfaceMapper::mapEdgeNodes(const labelLongList& nodesToMap) { const pointFieldPMG& points = surfaceEngine_.points(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); - const VRWGraph& pPatches = surfaceEngine_.pointPatches(); - + + const meshSurfacePartitioner& mPart = meshPartitioner(); + const VRWGraph& pPatches = mPart.pointPatches(); + //- find mapping distance for selected vertices std::map<label, scalar> mappingDistance; findMappingDistance(nodesToMap, mappingDistance); - + const VRWGraph* bpAtProcsPtr(NULL); if( Pstream::parRun() ) bpAtProcsPtr = &surfaceEngine_.bpAtProcs(); - + LongList<parMapperHelper> parallelBndNodes; - + meshSurfaceEngineModifier sMod(surfaceEngine_); - + //- map point to the nearest vertex on the triSurface - const label size = nodesToMap.size(); - # pragma omp parallel for shared(parallelBndNodes) if( size > 100 ) - for(label i=0;i<size;++i) + # ifdef USE_OMP + # pragma omp parallel for shared(parallelBndNodes) \ + if( nodesToMap.size() > 100 ) + # endif + forAll(nodesToMap, i) { const label bpI = nodesToMap[i]; const point& p = points[bPoints[bpI]]; - - //- find patches at this edge vertex - DynList<label> patches; - forAllRow(pPatches, bpI, j) - patches.append(pPatches(bpI, j)); - + + //- find patches at this edge point + DynList<label> patches = pPatches[bpI]; + const scalar maxDist = mappingDistance[bpI]; - + //- find approximate position of the vertex on the edge point mapPointApprox(p); scalar distSqApprox; @@ -280,37 +290,40 @@ void meshSurfaceMapper::mapEdgeNodes(const labelListPMG& nodesToMap) forAll(patches, patchI) { point np; + label nt; meshOctree_.findNearestSurfacePointInRegion ( np, distSqApprox, + nt, patches[patchI], mapPointApprox ); - + newP += np; } - + newP /= patches.size(); if( magSqr(newP - mapPointApprox) < 1e-8 * maxDist ) break; - + mapPointApprox = newP; } distSqApprox = magSqr(mapPointApprox - p); - + //- find the nearest vertex on the triSurface feature edge point mapPoint; scalar distSq; - meshOctree_.findNearestEdgePoint(p, patches, mapPoint, distSq); - + label nse; + meshOctree_.findNearestEdgePoint(mapPoint, distSq, nse, p, patches); + //- use the vertex with the smallest mapping distance if( distSq > 1.2 * distSqApprox ) { mapPoint = mapPointApprox; distSq = distSqApprox; } - + //- check if the mapping distance is within the given tolerances if( distSq > maxDist ) { @@ -320,13 +333,15 @@ void meshSurfaceMapper::mapEdgeNodes(const labelListPMG& nodesToMap) distSq = mappingDistance[bpI]; mapPoint = f * (mapPoint - p) + p; } - + //- move the point to the nearest edge vertex sMod.moveBoundaryVertexNoUpdate(bpI, mapPoint); - + if( bpAtProcsPtr && bpAtProcsPtr->sizeOfRow(bpI) ) { + # ifdef USE_OMP # pragma omp critical + # endif parallelBndNodes.append ( parMapperHelper @@ -339,27 +354,27 @@ void meshSurfaceMapper::mapEdgeNodes(const labelListPMG& nodesToMap) ); } } - + sMod.updateGeometry(nodesToMap); - + mapToSmallestDistance(parallelBndNodes); } - + void meshSurfaceMapper::mapCornersAndEdges() { const meshSurfacePartitioner& mPart = meshPartitioner(); const labelHashSet& cornerPoints = mPart.corners(); - labelListPMG selectedPoints; + labelLongList selectedPoints; forAllConstIter(labelHashSet, cornerPoints, it) selectedPoints.append(it.key()); - + mapCorners(selectedPoints); - + selectedPoints.clear(); - const labelHashSet& edgePoints = mPart.edgeNodes(); + const labelHashSet& edgePoints = mPart.edgePoints(); forAllConstIter(labelHashSet, edgePoints, it) selectedPoints.append(it.key()); - + mapEdgeNodes(selectedPoints); } diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperMapVertices.C b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperMapVertices.C index 1f620c3a71fe586f3ee8d40cf796f4e4a42366c0..fcbc8c342aa352aec2bc97faa9f8b3e5f96bbb3c 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperMapVertices.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperMapVertices.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,7 +36,9 @@ Description #include <map> +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGMapping @@ -48,51 +49,51 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Private member functions - -void meshSurfaceMapper::selectNodesAtParallelBnd(const labelListPMG& selNodes) + +void meshSurfaceMapper::selectNodesAtParallelBnd(const labelLongList& selNodes) { if( !Pstream::parRun() ) return; - - std::map<label, labelListPMG> exchangeData; + + std::map<label, labelLongList> exchangeData; const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); forAll(neiProcs, i) - exchangeData.insert(std::make_pair(neiProcs[i], labelListPMG())); - + exchangeData.insert(std::make_pair(neiProcs[i], labelLongList())); + const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); const labelList& globalPointLabel = surfaceEngine_.globalBoundaryPointLabel(); const Map<label>& globalToLocal = surfaceEngine_.globalToLocalBndPointAddressing(); - + boolList selectedNode(bpAtProcs.size(), false); - + forAll(selNodes, i) { const label bpI = selNodes[i]; - + selectedNode[bpI] = true; - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append(globalPointLabel[bpI]); } } - + //- exchange data - labelListPMG receivedData; + labelLongList receivedData; help::exchangeMap(exchangeData, receivedData); - + forAll(receivedData, i) { if( !selectedNode[globalToLocal[receivedData[i]]] ) { selectedNode[globalToLocal[receivedData[i]]] = true; - const_cast<labelListPMG&>(selNodes).append + const_cast<labelLongList&>(selNodes).append ( globalToLocal[receivedData[i]] ); @@ -104,7 +105,7 @@ void meshSurfaceMapper::mapToSmallestDistance(LongList<parMapperHelper>& parN) { if( !Pstream::parRun() ) return; - + std::map<label, LongList<parMapperHelper> > exchangeData; const DynList<label>& neiProcs = surfaceEngine_.bpNeiProcs(); forAll(neiProcs, i) @@ -112,26 +113,26 @@ void meshSurfaceMapper::mapToSmallestDistance(LongList<parMapperHelper>& parN) ( std::make_pair(neiProcs[i], LongList<parMapperHelper>()) ); - + const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); const labelList& globalPointLabel = surfaceEngine_.globalBoundaryPointLabel(); const Map<label>& globalToLocal = surfaceEngine_.globalToLocalBndPointAddressing(); - + Map<label> bpToList(parN.size()); - + forAll(parN, i) { const label bpI = parN[i].globalLabel(); bpToList.insert(bpI, i); - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append ( parMapperHelper @@ -144,51 +145,56 @@ void meshSurfaceMapper::mapToSmallestDistance(LongList<parMapperHelper>& parN) ); } } - + //- exchange data LongList<parMapperHelper> receivedData; help::exchangeMap(exchangeData, receivedData); - + //- select the point with the smallest moving distance meshSurfaceEngineModifier surfModifier(surfaceEngine_); forAll(receivedData, i) { const parMapperHelper& ph = receivedData[i]; - + const label bpI = globalToLocal[ph.globalLabel()]; - + parMapperHelper& phOrig = parN[bpToList[bpI]]; if( phOrig.movingDistance() < ph.movingDistance() ) { - surfModifier.moveBoundaryVertex(bpI, ph.coordinates()); + surfModifier.moveBoundaryVertexNoUpdate(bpI, ph.coordinates()); phOrig = ph; } } - - surfModifier.updateVertexNormals(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void meshSurfaceMapper::mapNodeToPatch(const label bpI, const label patchI) { - label patch; + label patch, nt; point mapPoint; scalar dSq; - + const pointFieldPMG& points = surfaceEngine_.points(); const labelList& bPoints = surfaceEngine_.boundaryPoints(); const point p = points[bPoints[bpI]]; - + if( patchI < 0 ) { - meshOctree_.findNearestSurfacePoint(mapPoint, dSq, patch, p); + meshOctree_.findNearestSurfacePoint(mapPoint, dSq, nt, patch, p); } else { - meshOctree_.findNearestSurfacePointInRegion(mapPoint, dSq, patchI, p); + meshOctree_.findNearestSurfacePointInRegion + ( + mapPoint, + dSq, + nt, + patchI, + p + ); } - + meshSurfaceEngineModifier surfModifier(surfaceEngine_); surfModifier.moveBoundaryVertex(bpI, mapPoint); } @@ -196,57 +202,62 @@ void meshSurfaceMapper::mapNodeToPatch(const label bpI, const label patchI) void meshSurfaceMapper::mapVerticesOntoSurface() { Info << "Mapping vertices onto surface" << endl; - - labelListPMG nodesToMap(surfaceEngine_.boundaryPoints().size()); + + labelLongList nodesToMap(surfaceEngine_.boundaryPoints().size()); forAll(nodesToMap, i) nodesToMap[i] = i; - + mapVerticesOntoSurface(nodesToMap); - + Info << "Finished mapping vertices onto surface" << endl; } -void meshSurfaceMapper::mapVerticesOntoSurface(const labelListPMG& nodesToMap) +void meshSurfaceMapper::mapVerticesOntoSurface(const labelLongList& nodesToMap) { - const labelList& boundaryPoints = surfaceEngine_.boundaryPoints(); + const labelList& boundaryPoints = surfaceEngine_.boundaryPoints(); const pointFieldPMG& points = surfaceEngine_.points(); - + const VRWGraph* bpAtProcsPtr(NULL); if( Pstream::parRun() ) bpAtProcsPtr = &surfaceEngine_.bpAtProcs(); - - meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); LongList<parMapperHelper> parallelBndNodes; - + + # ifdef USE_OMP const label size = nodesToMap.size(); # pragma omp parallel for if( size > 1000 ) shared(parallelBndNodes) \ schedule(dynamic, Foam::max(1, size / (3 * omp_get_max_threads()))) - for(label i=0;i<size;++i) + # endif + forAll(nodesToMap, i) { const label bpI = nodesToMap[i]; - - # ifdef DEBUGMapping + + # ifdef DEBUGMapping Info << nl << "Mapping vertex " << bpI << " with coordinates " << points[boundaryPoints[bpI]] << endl; - # endif - - label patch; + # endif + + label patch, nt; point mapPoint; scalar dSq; - + meshOctree_.findNearestSurfacePoint ( mapPoint, dSq, + nt, patch, points[boundaryPoints[bpI]] ); - - surfaceModifier.moveBoundaryVertexNoUpdate(bpI, mapPoint); - + + surfaceModifier.moveBoundaryVertexNoUpdate(bpI, mapPoint); + if( bpAtProcsPtr && bpAtProcsPtr->sizeOfRow(bpI) ) { + # ifdef USE_OMP # pragma omp critical + # endif parallelBndNodes.append ( parMapperHelper @@ -258,43 +269,46 @@ void meshSurfaceMapper::mapVerticesOntoSurface(const labelListPMG& nodesToMap) ) ); } - - # ifdef DEBUGMapping + + # ifdef DEBUGMapping Info << "Mapped point " << points[boundaryPoints[bpI]] << endl; - # endif + # endif } - - surfaceModifier.updateGeometry(nodesToMap); - + + //- make sure that the points are at the nearest location on the surface mapToSmallestDistance(parallelBndNodes); + + //- re-calculate face normals, point normals, etc. + surfaceModifier.updateGeometry(nodesToMap); } void meshSurfaceMapper::mapVerticesOntoSurfacePatches() { Info << "Mapping vertices with respect to surface patches" << endl; - - labelListPMG nodesToMap(surfaceEngine_.boundaryPoints().size()); + + labelLongList nodesToMap(surfaceEngine_.boundaryPoints().size()); forAll(nodesToMap, i) nodesToMap[i] = i; - + mapVerticesOntoSurfacePatches(nodesToMap); - + Info << "Finished mapping vertices with respect to surface patches" << endl; } void meshSurfaceMapper::mapVerticesOntoSurfacePatches ( - const labelListPMG& nodesToMap + const labelLongList& nodesToMap ) { const meshSurfacePartitioner& mPart = meshPartitioner(); const labelHashSet& cornerPoints = mPart.corners(); - const labelHashSet& edgePoints = mPart.edgeNodes(); - + const labelHashSet& edgePoints = mPart.edgePoints(); + const VRWGraph& pointPatches = mPart.pointPatches(); + boolList treatedPoint(surfaceEngine_.boundaryPoints().size(), false); - + //- find corner and edge points - labelListPMG selectedCorners, selectedEdges; + labelLongList selectedCorners, selectedEdges; forAll(nodesToMap, i) { if( cornerPoints.found(nodesToMap[i]) ) @@ -308,45 +322,50 @@ void meshSurfaceMapper::mapVerticesOntoSurfacePatches selectedEdges.append(nodesToMap[i]); } } - + //- map the remaining selected points const labelList& bPoints = surfaceEngine_.boundaryPoints(); const pointFieldPMG& points = surfaceEngine_.points(); - const VRWGraph& pointPatches = surfaceEngine_.pointPatches(); - + const VRWGraph* bpAtProcsPtr(NULL); if( Pstream::parRun() ) bpAtProcsPtr = &surfaceEngine_.bpAtProcs(); - - meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); LongList<parMapperHelper> parallelBndNodes; - + + # ifdef USE_OMP const label size = nodesToMap.size(); # pragma omp parallel for if( size > 1000 ) shared(parallelBndNodes) \ schedule(dynamic, Foam::max(1, size / (3 * omp_get_max_threads()))) - for(label nI=0;nI<size;++nI) + # endif + forAll(nodesToMap, nI) { const label bpI = nodesToMap[nI]; - + if( treatedPoint[bpI] ) continue; - + const point& p = points[bPoints[bpI]]; point mapPoint; scalar dSq; + label nt; meshOctree_.findNearestSurfacePointInRegion ( mapPoint, dSq, + nt, pointPatches(bpI, 0), p ); - + surfaceModifier.moveBoundaryVertexNoUpdate(bpI, mapPoint); - + if( bpAtProcsPtr && bpAtProcsPtr->sizeOfRow(bpI) ) { + # ifdef USE_OMP # pragma omp critical + # endif parallelBndNodes.append ( parMapperHelper @@ -358,19 +377,22 @@ void meshSurfaceMapper::mapVerticesOntoSurfacePatches ) ); } - - # ifdef DEBUGMapping + + # ifdef DEBUGMapping Info << "Mapped point " << points[boundaryPoints[bpI]] << endl; - # endif + # endif } - - surfaceModifier.updateGeometry(nodesToMap); - + + //- map vertices at inter-processor boundaries to the nearest location + //- on the surface mapToSmallestDistance(parallelBndNodes); - + + //- update face normals, point normals, etc. + surfaceModifier.updateGeometry(nodesToMap); + //- map edge nodes mapEdgeNodes(selectedEdges); - + //- map corner vertices mapCorners(selectedCorners); } diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperPremapVertices.C b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperPremapVertices.C index 4a90cd2e121f679ce44970eebda59c25591c8521..6d4f415a22f022971f747a7e4a39a530535a2d0e 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperPremapVertices.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/meshSurfaceMapperPremapVertices.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -31,9 +30,12 @@ Description #include "meshSurfaceMapper.H" #include "meshOctree.H" #include "refLabelledPoint.H" +#include "refLabelledPointScalar.H" #include "helperFunctionsPar.H" +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGMapping @@ -47,119 +49,141 @@ namespace Foam void meshSurfaceMapper::preMapVertices(const label nIterations) { Info << "Smoothing mesh surface before mapping. Iteration:" << flush; - + const labelList& boundaryPoints = surfaceEngine_.boundaryPoints(); const pointFieldPMG& points = surfaceEngine_.points(); const vectorField& faceCentres = surfaceEngine_.faceCentres(); const VRWGraph& pointFaces = surfaceEngine_.pointFaces(); - - List<labelledPoint> preMapPositions(boundaryPoints.size()); - + const VRWGraph& pointInFace = surfaceEngine_.pointInFaces(); + const faceList::subList& bFaces = surfaceEngine_.boundaryFaces(); + + List<labelledPointScalar> preMapPositions(boundaryPoints.size()); + List<DynList<scalar, 6> > faceCentreDistances(bFaces.size()); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(bFaces, bfI) + { + const point& c = faceCentres[bfI]; + const face& bf = bFaces[bfI]; + + faceCentreDistances[bfI].setSize(bf.size()); + + forAll(bf, pI) + { + faceCentreDistances[bfI][pI] = magSqr(points[bf[pI]] - c); + } + } + for(label iterI=0;iterI<nIterations;++iterI) { //- use the shrinking laplace first + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(pointFaces, bpI) { - labelledPoint lp(0, vector::zero); - - forAllRow(pointFaces, bpI, bfI) + labelledPointScalar lp(bpI, vector::zero, 0.0); + + const point& p = points[boundaryPoints[bpI]]; + + forAllRow(pointFaces, bpI, pfI) { - ++lp.pointLabel(); - lp.coordinates() += faceCentres[pointFaces(bpI, bfI)]; + const label bfI = pointFaces(bpI, pfI); + const point& fc = faceCentres[pointFaces(bpI, pfI)]; + const label pos = pointInFace(bpI, pfI); + const scalar w + ( + max(magSqr(p - fc) / faceCentreDistances[bfI][pos], SMALL) + ); + lp.coordinates() += w * faceCentres[bfI]; + lp.scalarValue() += w; } - + preMapPositions[bpI] = lp; } - + + //- pointer needed in case of parallel calculation + const VRWGraph* bpAtProcsPtr(NULL); + if( Pstream::parRun() ) { const VRWGraph& bpAtProcs = surfaceEngine_.bpAtProcs(); + bpAtProcsPtr = &bpAtProcs; const labelList& globalPointLabel = surfaceEngine_.globalBoundaryPointLabel(); const Map<label>& globalToLocal = surfaceEngine_.globalToLocalBndPointAddressing(); - + //- collect data to be sent to other processors - std::map<label, LongList<refLabelledPoint> > exchangeData; + std::map<label, LongList<labelledPointScalar> > exchangeData; forAll(surfaceEngine_.bpNeiProcs(), i) exchangeData.insert ( std::make_pair ( surfaceEngine_.bpNeiProcs()[i], - LongList<refLabelledPoint>() + LongList<labelledPointScalar>() ) ); - + forAllConstIter(Map<label>, globalToLocal, it) { const label bpI = it(); - + forAllRow(bpAtProcs, bpI, procI) { const label neiProc = bpAtProcs(bpI, procI); - + if( neiProc == Pstream::myProcNo() ) continue; - + exchangeData[neiProc].append ( - refLabelledPoint + labelledPointScalar ( globalPointLabel[bpI], - preMapPositions[bpI] + preMapPositions[bpI].coordinates(), + preMapPositions[bpI].scalarValue() ) ); } } - + //- exchange data with other processors - LongList<refLabelledPoint> receivedData; + LongList<labelledPointScalar> receivedData; help::exchangeMap(exchangeData, receivedData); - + //- combine collected data with the available data forAll(receivedData, i) { - const refLabelledPoint& rlp = receivedData[i]; - const labelledPoint& lps = rlp.lPoint(); - - const label bpI = globalToLocal[rlp.objectLabel()]; - - labelledPoint& lp = preMapPositions[bpI]; - lp.pointLabel() += lps.pointLabel(); + const labelledPointScalar& lps = receivedData[i]; + + const label bpI = globalToLocal[lps.pointLabel()]; + + labelledPointScalar& lp = preMapPositions[bpI]; lp.coordinates() += lps.coordinates(); + lp.scalarValue() += lps.scalarValue(); } } - - //- calculate coordinates of points for searching - label size = preMapPositions.size(); - # pragma omp parallel for shared(size) - for(label bpI=0;bpI<size;++bpI) - { - labelledPoint& lp = preMapPositions[bpI]; - - if( lp.pointLabel() == 0 ) - { - Warning << "Surface point " << bpI - << " has no supporting faces" << endl; - continue; - } - - lp.coordinates() /= lp.pointLabel(); - } - + //- create the surface modifier and move the surface points meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); - - size = boundaryPoints.size(); - # pragma omp parallel for if( size > 1000 ) shared(size) \ - schedule(dynamic, Foam::max(100, size / (3 * omp_get_max_threads()))) - for(label bpI=0;bpI<size;++bpI) + LongList<parMapperHelper> parallelBndNodes; + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(boundaryPoints, bpI) { + labelledPointScalar& lps = preMapPositions[bpI]; + + lps.coordinates() /= lps.scalarValue(); + const point& p = points[boundaryPoints[bpI]]; - - label patch; + + label patch, nearestTri; point pMap = p; scalar dSq; @@ -167,21 +191,43 @@ void meshSurfaceMapper::preMapVertices(const label nIterations) ( pMap, dSq, + nearestTri, patch, - preMapPositions[bpI].coordinates() + lps.coordinates() ); - + const point newP = 0.5 * (pMap + p); - + surfaceModifier.moveBoundaryVertexNoUpdate(bpI, newP); + + if( bpAtProcsPtr && bpAtProcsPtr->sizeOfRow(bpI) ) + { + # ifdef USE_OMP + # pragma omp critical + # endif + parallelBndNodes.append + ( + parMapperHelper + ( + newP, + dSq, + bpI, + patch + ) + ); + } } - + + //- make sure that the vertices at inter-processor boundaries + //- are mapped onto the same location + mapToSmallestDistance(parallelBndNodes); + + //- update the surface geometry of the surfaceModifier.updateGeometry(); - surfaceModifier.syncVerticesAtParallelBoundaries(); - + Info << "." << flush; } - + Info << endl; } diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/parMapperHelper.H b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/parMapperHelper.H index 0c5bcd73ba160fa5790eaf2fa999b6c7bff91281..db311a77cdf460d60d4e3a5cbb8be8b4f4e154cc 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/parMapperHelper.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper/parMapperHelper.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class parMapperHelper diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2D.C b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2D.C new file mode 100644 index 0000000000000000000000000000000000000000..8358ab61779f8365badd368c0f74dcf4e198d168 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2D.C @@ -0,0 +1,166 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "meshSurfaceMapper2D.H" +#include "meshSurfaceEngine.H" +#include "meshSurfacePartitioner.H" +#include "polyMeshGen2DEngine.H" +#include "triSurf.H" +#include "triSurfacePartitioner.H" +#include "demandDrivenData.H" +#include "meshOctree.H" +#include "helperFunctions.H" + +// #define DEBUGSearch + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void meshSurfaceMapper2D::findActiveBoundaryEdges() +{ + const VRWGraph& edgeFaces = surfaceEngine_.edgeFaces(); + + const polyMeshGen2DEngine& mesh2DEngine = this->mesh2DEngine(); + const boolList& activeFace = mesh2DEngine.activeFace(); + + const label startFace = surfaceEngine_.mesh().boundaries()[0].patchStart(); + + activeBoundaryEdges_.clear(); + + //- check which edges are at the boundary + forAll(edgeFaces, edgeI) + { + if( edgeFaces.sizeOfRow(edgeI) == 2 ) + { + const bool active0 = activeFace[startFace + edgeFaces(edgeI, 0)]; + const bool active1 = activeFace[startFace + edgeFaces(edgeI, 1)]; + + if( active0 && active1 ) + activeBoundaryEdges_.append(edgeI); + } + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndEdgeAddressing(); + const Map<label>& otherProc = surfaceEngine_.otherEdgeFaceAtProc(); + + const DynList<label>& neiProcs = surfaceEngine_.beNeiProcs(); + + std::map<label, labelLongList> exchangeData; + forAll(neiProcs, i) + exchangeData[neiProcs[i]].clear(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label beI = it(); + + if( activeFace[startFace + edgeFaces(beI, 0)] ) + { + exchangeData[otherProc[beI]].append(it.key()); + } + } + + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + forAll(receivedData, i) + { + const label beI = globalToLocal[receivedData[i]]; + + if( activeFace[startFace + edgeFaces(beI, 0)] ) + activeBoundaryEdges_.append(beI); + } + } +} + +void meshSurfaceMapper2D::create2DEngine() const +{ + polyMeshGen& mesh = const_cast<polyMeshGen&>(surfaceEngine_.mesh()); + mesh2DEnginePtr_ = new polyMeshGen2DEngine(mesh); +} + +void meshSurfaceMapper2D::createTriSurfacePartitioner() const +{ + surfPartitionerPtr_ = new triSurfacePartitioner(meshOctree_.surface()); +} + +void meshSurfaceMapper2D::createMeshSurfacePartitioner() const +{ + meshPartitionerPtr_ = new meshSurfacePartitioner(surfaceEngine_); +} + +void meshSurfaceMapper2D::clearOut() +{ + deleteDemandDrivenData(mesh2DEnginePtr_); + deleteDemandDrivenData(surfPartitionerPtr_); + deleteDemandDrivenData(meshPartitionerPtr_); +} + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +meshSurfaceMapper2D::meshSurfaceMapper2D +( + const meshSurfaceEngine& mse, + const meshOctree& octree +) +: + surfaceEngine_(mse), + meshOctree_(octree), + mesh2DEnginePtr_(NULL), + surfPartitionerPtr_(NULL), + meshPartitionerPtr_(NULL) +{ + if( Pstream::parRun() ) + { + //- allocate bpAtProcs and other addressing + //- this is done here to prevent possible deadlocks + surfaceEngine_.bpAtProcs(); + } + + findActiveBoundaryEdges(); + + createMeshSurfacePartitioner(); +} + +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + +meshSurfaceMapper2D::~meshSurfaceMapper2D() +{ + clearOut(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2D.H b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2D.H new file mode 100644 index 0000000000000000000000000000000000000000..21ed49afcc89bc7a82bfb3f595b20f8c28883b91 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2D.H @@ -0,0 +1,198 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + meshSurfaceMapper2D + +Description + Maps vertices of a 2D onto the nearest points on the geometry + +SourceFiles + meshSurfaceMapper2D.C + +\*---------------------------------------------------------------------------*/ + +#ifndef meshSurfaceMapper2D_H +#define meshSurfaceMapper2D_H + +#include "labelList.H" +#include "pointField.H" +#include "labelLongList.H" +#include "parMapperHelper.H" +#include "boundBox.H" + +#include <map> + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// Forward declarations +class meshOctree; +class polyMeshGen; +class polyMeshGen2DEngine; +class meshSurfaceEngine; +class meshSurfacePartitioner; +class triSurfacePartitioner; + +/*---------------------------------------------------------------------------*\ + Class meshSurfaceMapper2D Declaration +\*---------------------------------------------------------------------------*/ + +class meshSurfaceMapper2D +{ + // Private data + //- reference to mesh surface + const meshSurfaceEngine& surfaceEngine_; + + //- reference to the octree + const meshOctree& meshOctree_; + + //- mesh 2D engine + mutable polyMeshGen2DEngine* mesh2DEnginePtr_; + + //- triSurface partitioner + mutable triSurfacePartitioner* surfPartitionerPtr_; + + //- mesh surface partitioner + mutable meshSurfacePartitioner* meshPartitionerPtr_; + + //- labels of edges which are at the boundary which shall be mapped + //- onto the surface + labelLongList activeBoundaryEdges_; + + // Private member functions + //- find active boundary edges + void findActiveBoundaryEdges(); + + //- create a 2D engine + void create2DEngine() const; + + //- create and return mesh 2D engine + inline const polyMeshGen2DEngine& mesh2DEngine() const + { + if( !mesh2DEnginePtr_ ) + create2DEngine(); + + return *mesh2DEnginePtr_; + } + + //- create surface partitioner + void createTriSurfacePartitioner() const; + + //- create and reurn surface partitioner + inline const triSurfacePartitioner& surfacePartitioner() const + { + if( !surfPartitionerPtr_ ) + createTriSurfacePartitioner(); + + return *surfPartitionerPtr_; + } + + //- create mesh surface partitioner + void createMeshSurfacePartitioner() const; + + //- create and return mesh surface partitioner + inline const meshSurfacePartitioner& meshPartitioner() const + { + if( !meshPartitionerPtr_ ) + createMeshSurfacePartitioner(); + + return *meshPartitionerPtr_; + } + + //- delete dynamically allocated data + void clearOut(); + + // Private member functions needed for parallel execution + //- find mapping distance for corner points + void findMappingDistance + ( + const labelLongList&, + std::map<label, scalar>& + ) const; + + //- map to the location with the smallest distance + void mapToSmallestDistance(LongList<parMapperHelper>&); + + //- Disallow default bitwise copy construct + meshSurfaceMapper2D(const meshSurfaceMapper2D&); + + //- Disallow default bitwise assignment + void operator=(const meshSurfaceMapper2D&); + +public: + + // Constructors + + //- Construct from meshSurfaceEngine and octree + meshSurfaceMapper2D(const meshSurfaceEngine&, const meshOctree&); + + // Destructor + + ~meshSurfaceMapper2D(); + + // Member Functions + + //- adjust z coordinates of the mesh to the ones in the surface mesh + void adjustZCoordinates(); + + //- projects surface vertices onto their nearest location + //- on the surface mesh + void mapVerticesOntoSurface(); + + //- projects selected edge to their nearest location + //- on the surface mesh + void mapVerticesOntoSurface(const labelLongList& edgesToMap); + + //- projects edges with corners onto their nearest location + //- on the surface mesh + void mapCorners(); + + //- projects selected edges with corners onto their nearest + //- locations on the surface mesh + void mapCorners(const labelLongList& edgesToMap); + + //- projects surface edges onto the surface with respect + //- to the surface patch they belong to. Corners are respected + void mapVerticesOntoSurfacePatches(); + + //- projects selected surface edges onto the surface with respect + //- to the surface patch they belong to. Corners are respected + void mapVerticesOntoSurfacePatches(const labelLongList& edgesToMap); + + //- a combination of mapping and smoothing intended for better + //- feature capturing + void preMapVertices(const label nIterations = 2); +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2DMapVertices.C b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2DMapVertices.C new file mode 100644 index 0000000000000000000000000000000000000000..1f89dfff849d66379eb1e5b4ac0eda6f0c9d1e42 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2DMapVertices.C @@ -0,0 +1,603 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "meshOctree.H" +#include "triSurf.H" +#include "triSurfacePartitioner.H" +#include "meshSurfaceMapper2D.H" +#include "meshSurfaceEngine.H" +#include "polyMeshGen2DEngine.H" +#include "meshSurfaceEngineModifier.H" +#include "meshSurfacePartitioner.H" +#include "labelledScalar.H" +#include "polyMeshGenAddressing.H" +#include "boundBox.H" + +#include "helperFunctionsPar.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGMapping + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void meshSurfaceMapper2D::findMappingDistance +( + const labelLongList& edgesToMap, + std::map<label, scalar>& mappingDistance +) const +{ + const vectorField& faceCentres = surfaceEngine_.faceCentres(); + const VRWGraph& eFaces = surfaceEngine_.edgeFaces(); + const edgeList& edges = surfaceEngine_.edges(); + const pointFieldPMG& points = surfaceEngine_.points(); + + //- generate search distance for corner edges + mappingDistance.clear(); + forAll(edgesToMap, i) + { + const label beI = edgesToMap[i]; + + mappingDistance.insert(std::make_pair(beI, 0.0)); + std::map<label, scalar>::iterator mIter = mappingDistance.find(beI); + + const point p = edges[beI].centre(points); + forAllRow(eFaces, beI, efI) + { + const scalar d = magSqr(faceCentres[eFaces(beI, efI)] - p); + mIter->second = Foam::max(mIter->second, d); + } + + //- safety factor + mIter->second *= 4.0; + } + + if( Pstream::parRun() ) + { + //- make sure that corner edges at parallel boundaries + //- have the same range in which they accept the corners + const VRWGraph& beAtProcs = surfaceEngine_.beAtProcs(); + const labelList& globalEdgeLabel = + surfaceEngine_.globalBoundaryEdgeLabel(); + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndEdgeAddressing(); + + //- create the map for exchanging data + std::map<label, DynList<labelledScalar> > exchangeData; + const DynList<label>& neiProcs = surfaceEngine_.beNeiProcs(); + forAll(neiProcs, i) + exchangeData.insert + ( + std::make_pair(neiProcs[i], DynList<labelledScalar>())); + + forAll(edgesToMap, eI) + { + const label beI = edgesToMap[eI]; + + forAllRow(beAtProcs, beI, i) + { + const label neiProc = beAtProcs(beI, i); + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + labelledScalar(globalEdgeLabel[beI], mappingDistance[beI]) + ); + } + } + + //- exchange data between processors + LongList<labelledScalar> receivedData; + help::exchangeMap(exchangeData, receivedData); + + //- select the maximum mapping distance for processor points + forAll(receivedData, i) + { + const labelledScalar& ls = receivedData[i]; + + const label beI = globalToLocal[ls.scalarLabel()]; + + //- choose the maximum value for the mapping distance + std::map<label, scalar>::iterator mIter = mappingDistance.find(beI); + mIter->second = Foam::max(mIter->second, ls.value()); + } + } +} + +void meshSurfaceMapper2D::mapToSmallestDistance(LongList<parMapperHelper>& parE) +{ + if( !Pstream::parRun() ) + return; + + std::map<label, LongList<parMapperHelper> > exchangeData; + const DynList<label>& neiProcs = surfaceEngine_.beNeiProcs(); + forAll(neiProcs, i) + exchangeData.insert + ( + std::make_pair(neiProcs[i], LongList<parMapperHelper>()) + ); + + const labelList& bp = surfaceEngine_.bp(); + const edgeList& edges = surfaceEngine_.edges(); + const VRWGraph& beAtProcs = surfaceEngine_.beAtProcs(); + const labelList& globalEdgeLabel = + surfaceEngine_.globalBoundaryEdgeLabel(); + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndEdgeAddressing(); + const pointFieldPMG& points = surfaceEngine_.points(); + + Map<label> beToList(parE.size()); + + forAll(parE, i) + { + const label beI = parE[i].globalLabel(); + beToList.insert(beI, i); + + forAllRow(beAtProcs, beI, procI) + { + const label neiProc = beAtProcs(beI, procI); + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + parMapperHelper + ( + parE[i].coordinates(), + parE[i].movingDistance(), + globalEdgeLabel[beI], + parE[i].pointPatch() + ) + ); + } + } + + //- exchange data + LongList<parMapperHelper> receivedData; + help::exchangeMap(exchangeData, receivedData); + + //- select the point with the smallest moving distance + meshSurfaceEngineModifier surfModifier(surfaceEngine_); + forAll(receivedData, i) + { + const parMapperHelper& ph = receivedData[i]; + + const label beI = globalToLocal[ph.globalLabel()]; + + parMapperHelper& phOrig = parE[beToList[beI]]; + if( phOrig.movingDistance() < ph.movingDistance() ) + { + const edge& e = edges[beI]; + + point newP = ph.coordinates(); + + newP.z() = points[e.start()].z(); + surfModifier.moveBoundaryVertex(bp[e.start()], newP); + + newP.z() = points[e.end()].z(); + surfModifier.moveBoundaryVertex(bp[e.end()], newP); + + phOrig = ph; + } + } + + surfModifier.updateVertexNormals(); +} + +void meshSurfaceMapper2D::adjustZCoordinates() +{ + //- create the bounding box of the surface mesh + const boundBox sbb(meshOctree_.surface().points()); + + const labelList& bp = surfaceEngine_.bp(); + const pointFieldPMG& points = surfaceEngine_.points(); + + meshSurfaceEngineModifier modifier(surfaceEngine_); + + const polyMeshGen2DEngine& mesh2DEngine = this->mesh2DEngine(); + const boolList& minZPoint = mesh2DEngine.zMinPoints(); + const boolList& maxZPoint = mesh2DEngine.zMaxPoints(); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(minZPoint, pointI) + { + point newP = points[pointI]; + + if( minZPoint[pointI] ) + { + newP.z() = sbb.min().z(); + } + else if( maxZPoint[pointI] ) + { + newP.z() = sbb.max().z(); + } + else + { + FatalErrorIn + ( + "void meshSurfaceMapper2D::adjustZCoordinates()" + ) << "This mesh is not in the x-y plane!" << exit(FatalError); + } + + modifier.moveBoundaryVertexNoUpdate(bp[pointI], newP); + } + + modifier.updateGeometry(); +} + +void meshSurfaceMapper2D::mapVerticesOntoSurface() +{ + labelLongList edgesToMap; + + forAll(activeBoundaryEdges_, beI) + edgesToMap.append(activeBoundaryEdges_[beI]); + + mapVerticesOntoSurface(edgesToMap); +} + +void meshSurfaceMapper2D::mapVerticesOntoSurface(const labelLongList& edgesToMap) +{ + const edgeList& edges = surfaceEngine_.edges(); + const labelList& bp = surfaceEngine_.bp(); + const pointFieldPMG& points = surfaceEngine_.points(); + + const VRWGraph* beAtProcsPtr(NULL); + if( Pstream::parRun() ) + beAtProcsPtr = &surfaceEngine_.beAtProcs(); + + labelLongList nodesToMap; + forAll(edgesToMap, i) + { + const edge& e = edges[edgesToMap[i]]; + nodesToMap.append(bp[e.start()]); + nodesToMap.append(bp[e.end()]); + } + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + LongList<parMapperHelper> parallelBndEdges; + + # ifdef USE_OMP + const label size = edgesToMap.size(); + # pragma omp parallel for if( size > 1000 ) shared(parallelBndEdges) \ + schedule(dynamic, Foam::max(1, size / (3 * omp_get_max_threads()))) + # endif + forAll(edgesToMap, i) + { + const label beI = edgesToMap[i]; + const edge& e = edges[beI]; + + # ifdef DEBUGMapping + Info << nl << "Mapping edge " << beI << " with nodes " + << e << endl; + # endif + + label patch, nt; + point mapPoint; + scalar dSq; + + meshOctree_.findNearestSurfacePoint + ( + mapPoint, + dSq, + nt, + patch, + points[e.start()] + ); + + mapPoint.z() = points[e.start()].z(); + surfaceModifier.moveBoundaryVertexNoUpdate(bp[e.start()], mapPoint); + + mapPoint.z() = points[e.end()].z(); + surfaceModifier.moveBoundaryVertexNoUpdate(bp[e.end()], mapPoint); + + if( beAtProcsPtr && beAtProcsPtr->sizeOfRow(beI) ) + { + # ifdef USE_OMP + # pragma omp critical + # endif + parallelBndEdges.append + ( + parMapperHelper + ( + mapPoint, + dSq, + beI, + patch + ) + ); + } + + # ifdef DEBUGMapping + Info << "Mapped edge " << edges[beI] << endl; + # endif + } + + surfaceModifier.updateGeometry(nodesToMap); + + mapToSmallestDistance(parallelBndEdges); +} + +void meshSurfaceMapper2D::mapCorners() +{ + const edgeList& edges = surfaceEngine_.edges(); + + const meshSurfacePartitioner& mPart = meshPartitioner(); + const labelHashSet& cornerPoints = mPart.corners(); + + labelLongList selectedEdges; + forAll(activeBoundaryEdges_, eI) + { + const edge& e = edges[activeBoundaryEdges_[eI]]; + + if( cornerPoints.found(e.start()) || cornerPoints.found(e.end()) ) + selectedEdges.append(activeBoundaryEdges_[eI]); + } + + mapCorners(selectedEdges); +} + +void meshSurfaceMapper2D::mapCorners(const labelLongList& edgesToMap) +{ + const meshSurfacePartitioner& mPart = meshPartitioner(); + const labelHashSet& corners = mPart.corners(); + const VRWGraph& pPatches = mPart.pointPatches(); + + const pointFieldPMG& points = surfaceEngine_.points(); + const edgeList& edges = surfaceEngine_.edges(); + const labelList& bp = surfaceEngine_.bp(); + + std::map<label, scalar> mappingDistance; + findMappingDistance(edgesToMap, mappingDistance); + + //- for every corner in the mesh surface find the nearest corner in the + //- triSurface + meshSurfaceEngineModifier sMod(surfaceEngine_); + + # ifdef USE_OMP + # pragma omp parallel for if( edgesToMap.size() > 10 ) + # endif + forAll(edgesToMap, eI) + { + const label beI = edgesToMap[eI]; + const edge& be = edges[beI]; + + const label bps = bp[be.start()]; + const label bpe = bp[be.end()]; + + DynList<label> ePatches; + forAllRow(pPatches, bps, i) + { + if( pPatches.contains(bpe, pPatches(bps, i)) ) + ePatches.append(pPatches(bps, i)); + } + + if( !corners.found(bps) || !corners.found(bpe) ) + FatalErrorIn + ( + "meshSurfaceMapper2D::mapCorners(const labelLongList&)" + ) << "Trying to map a point that is not a corner" + << abort(FatalError); + + const point& p = points[be.start()]; + const scalar maxDist = mappingDistance[beI]; + + //- find the nearest position to the given point patches + point mapPointApprox(p); + scalar distSqApprox; + + label iter(0); + while( iter++ < 20 ) + { + point newP(vector::zero); + forAll(ePatches, epI) + { + point np; + label nt; + meshOctree_.findNearestSurfacePointInRegion + ( + np, + distSqApprox, + nt, + ePatches[epI], + mapPointApprox + ); + + newP += np; + } + + newP /= ePatches.size(); + if( magSqr(newP - mapPointApprox) < 1e-8 * maxDist ) + break; + + mapPointApprox = newP; + } + + distSqApprox = magSqr(mapPointApprox - p); + + //- find the nearest triSurface corner for the given corner + scalar distSq; + point mapPoint; + label nse; + meshOctree_.findNearestEdgePoint(mapPoint, distSq, nse, p, ePatches); + + if( distSq > mappingDistance[beI] ) + { + const vector disp = mapPoint - p; + + mapPoint = Foam::sqrt(mappingDistance[beI] / distSq) * disp + p; + distSq = mappingDistance[beI]; + } + + if( distSq > 1.2 * distSqApprox ) + { + mapPoint = mapPointApprox; + } + + //- move the point to the nearest corner + mapPoint.z() = points[be.start()].z(); + sMod.moveBoundaryVertexNoUpdate(bps, mapPoint); + + mapPoint.z() = points[be.end()].z(); + sMod.moveBoundaryVertexNoUpdate(bpe, mapPoint); + } + + labelLongList nodesToMap; + forAll(edgesToMap, eI) + { + const edge& be = edges[edgesToMap[eI]]; + + nodesToMap.append(bp[be.start()]); + nodesToMap.append(bp[be.end()]); + } + + sMod.updateGeometry(nodesToMap); +} + +void meshSurfaceMapper2D::mapVerticesOntoSurfacePatches() +{ + labelLongList edgesToMap; + + forAll(activeBoundaryEdges_, beI) + edgesToMap.append(activeBoundaryEdges_[beI]); + + mapVerticesOntoSurfacePatches(edgesToMap); +} + +void meshSurfaceMapper2D::mapVerticesOntoSurfacePatches +( + const labelLongList& edgesToMap +) +{ + //- map the selected edges on their patches + const edgeList& edges = surfaceEngine_.edges(); + const pointFieldPMG& points = surfaceEngine_.points(); + const VRWGraph& edgePatches = surfaceEngine_.edgePatches(); + const labelList& bp = surfaceEngine_.bp(); + + const VRWGraph* beAtProcsPtr(NULL); + if( Pstream::parRun() ) + beAtProcsPtr = &surfaceEngine_.beAtProcs(); + + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + LongList<parMapperHelper> parallelBndEdges; + labelLongList selectedCorners; + + # ifdef USE_OMP + const label size = edgesToMap.size(); + # pragma omp parallel for if( size > 1000 ) shared(parallelBndEdges) \ + schedule(dynamic, Foam::max(50, size / (3 * omp_get_max_threads()))) + # endif + forAll(edgesToMap, nI) + { + const label beI = edgesToMap[nI]; + + if( edgePatches.sizeOfRow(beI) == 2 ) + { + # ifdef USE_OMP + # pragma omp critical + # endif + selectedCorners.append(beI); + + continue; + } + + const edge& e = edges[beI]; + + const point& p = points[e.start()]; + point mapPoint; + scalar dSq; + label nt; + + meshOctree_.findNearestSurfacePointInRegion + ( + mapPoint, + dSq, + nt, + edgePatches(beI, 0), + p + ); + + mapPoint.z() = points[e.start()].z(); + surfaceModifier.moveBoundaryVertexNoUpdate(bp[e.start()], mapPoint); + + mapPoint.z() = points[e.end()].z(); + surfaceModifier.moveBoundaryVertexNoUpdate(bp[e.end()], mapPoint); + + if( beAtProcsPtr && beAtProcsPtr->sizeOfRow(beI) ) + { + # ifdef USE_OMP + # pragma omp critical + # endif + parallelBndEdges.append + ( + parMapperHelper + ( + mapPoint, + dSq, + beI, + -1 + ) + ); + } + + # ifdef DEBUGMapping + Info << "Mapped edge " << edges[beI] << endl; + # endif + } + + mapToSmallestDistance(parallelBndEdges); + + mapCorners(selectedCorners); + + //- update geometry at moved vertices + selectedCorners.clear(); + forAll(edgesToMap, eI) + { + const edge& e = edges[edgesToMap[eI]]; + + selectedCorners.append(bp[e.start()]); + selectedCorners.append(bp[e.end()]); + } + + surfaceModifier.updateGeometry(selectedCorners); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2DPremapVertices.C b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2DPremapVertices.C new file mode 100644 index 0000000000000000000000000000000000000000..f86500c9d529e1d1cfe9d75993bd285fc150bb91 --- /dev/null +++ b/meshLibrary/utilities/surfaceTools/meshSurfaceMapper2D/meshSurfaceMapper2DPremapVertices.C @@ -0,0 +1,227 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "demandDrivenData.H" +#include "meshSurfaceEngineModifier.H" +#include "meshSurfaceMapper2D.H" +#include "polyMeshGen2DEngine.H" +#include "meshOctree.H" +#include "refLabelledPoint.H" +#include "helperFunctionsPar.H" + +# ifdef USE_OMP +#include <omp.h> +# endif + +//#define DEBUGMapping + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void meshSurfaceMapper2D::preMapVertices(const label nIterations) +{ + Info << "Smoothing mesh surface before mapping. Iteration:" << flush; + + const pointFieldPMG& points = surfaceEngine_.points(); + const labelList& bp = surfaceEngine_.bp(); + const vectorField& faceCentres = surfaceEngine_.faceCentres(); + const VRWGraph& edgeFaces = surfaceEngine_.edgeFaces(); + const edgeList& edges = surfaceEngine_.edges(); + + List<labelledPoint> preMapPositions(activeBoundaryEdges_.size()); + + for(label iterI=0;iterI<nIterations;++iterI) + { + labelLongList parBndEdges; + + //- use the shrinking laplace first + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(activeBoundaryEdges_, eI) + { + const label beI = activeBoundaryEdges_[eI]; + + labelledPoint lp(0, vector::zero); + + if( edgeFaces.sizeOfRow(beI) == 2 ) + { + forAllRow(edgeFaces, beI, efI) + { + ++lp.pointLabel(); + lp.coordinates() += faceCentres[edgeFaces(beI, efI)]; + } + + } + else if( edgeFaces.sizeOfRow(beI) == 1 ) + { + ++lp.pointLabel(); + lp.coordinates() += faceCentres[edgeFaces(beI, 0)]; + + #ifdef USE_OMP + # pragma omp critical + # endif + parBndEdges.append(eI); + } + + //- store the information + preMapPositions[eI] = lp; + } + + if( Pstream::parRun() ) + { + const VRWGraph& beAtProcs = surfaceEngine_.beAtProcs(); + const labelList& globalEdgeLabel = + surfaceEngine_.globalBoundaryEdgeLabel(); + const Map<label>& globalToLocal = + surfaceEngine_.globalToLocalBndEdgeAddressing(); + + //- collect data to be sent to other processors + std::map<label, LongList<refLabelledPoint> > exchangeData; + forAll(surfaceEngine_.beNeiProcs(), i) + exchangeData.insert + ( + std::make_pair + ( + surfaceEngine_.beNeiProcs()[i], + LongList<refLabelledPoint>() + ) + ); + + Map<label> edgeToActiveAddressing; + forAll(parBndEdges, i) + { + const label beI = activeBoundaryEdges_[parBndEdges[i]]; + edgeToActiveAddressing.insert(beI, parBndEdges[i]); + + forAllRow(beAtProcs, beI, procI) + { + const label neiProc = beAtProcs(beI, procI); + + if( neiProc == Pstream::myProcNo() ) + continue; + + exchangeData[neiProc].append + ( + refLabelledPoint + ( + globalEdgeLabel[beI], + preMapPositions[beI] + ) + ); + } + } + + //- exchange data with other processors + LongList<refLabelledPoint> receivedData; + help::exchangeMap(exchangeData, receivedData); + + //- combine collected data with the available data + forAll(receivedData, i) + { + const refLabelledPoint& rlp = receivedData[i]; + const labelledPoint& lps = rlp.lPoint(); + + const label beI = globalToLocal[rlp.objectLabel()]; + const label eI = edgeToActiveAddressing[beI]; + + labelledPoint& lp = preMapPositions[eI]; + lp.pointLabel() += lps.pointLabel(); + lp.coordinates() += lps.coordinates(); + } + } + + //- calculate coordinates of points for searching + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(activeBoundaryEdges_, eI) + { + labelledPoint& lp = preMapPositions[eI]; + + if( lp.pointLabel() == 0 ) + { + Warning << "Surface edge " << activeBoundaryEdges_[eI] + << " has no active faces" << endl; + continue; + } + + lp.coordinates() /= lp.pointLabel(); + } + + //- create the surface modifier and move the surface points + meshSurfaceEngineModifier surfaceModifier(surfaceEngine_); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 50) + # endif + forAll(activeBoundaryEdges_, eI) + { + const label beI = activeBoundaryEdges_[eI]; + const edge& e = edges[beI]; + + const point& p = points[e.start()]; + + label patch, nt; + point pMap = p; + scalar dSq; + + meshOctree_.findNearestSurfacePoint + ( + pMap, + dSq, + nt, + patch, + preMapPositions[eI].coordinates() + ); + + pMap.z() = p.z(); + point newP = 0.5 * (pMap + p); + + surfaceModifier.moveBoundaryVertexNoUpdate(bp[e.start()], newP); + newP.z() = points[e.end()].z(); + surfaceModifier.moveBoundaryVertexNoUpdate(bp[e.end()], newP); + } + + surfaceModifier.updateGeometry(); + surfaceModifier.syncVerticesAtParallelBoundaries(); + + Info << "." << flush; + } + + Info << endl; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.C b/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.C index 84292b93eea3e622b7d743e6456902a171ea9bc3..eb42e1554007b5dbb288a0bdc2563965148fdcd1 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,48 +34,48 @@ namespace Foam // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // -// Construct from meshSurfaceEngine. Holds reference! meshSurfacePartitioner::meshSurfacePartitioner ( - const meshSurfaceEngine& meshSurface + const meshSurfaceEngine& meshSurface ) : meshSurface_(meshSurface), + facePatch_(meshSurface.boundaryFacePatches()), + pointPatches_(), corners_(), - edgeNodes_(), - partitionPartitions_(), - nEdgesAtPoint_() + edgePoints_(), + patchPatches_(), + nEdgesAtPoint_(), + featureEdges_() { calculateCornersEdgesAndAddressing(); } -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // - -meshSurfacePartitioner::~meshSurfacePartitioner() +meshSurfacePartitioner::meshSurfacePartitioner +( + const meshSurfaceEngine& meshSurface, + const labelList& facePatch +) +: + meshSurface_(meshSurface), + facePatch_(facePatch), + pointPatches_(), + corners_(), + edgePoints_(), + patchPatches_(), + nEdgesAtPoint_(), + featureEdges_() { + calculateCornersEdgesAndAddressing(); } -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -const labelHashSet& meshSurfacePartitioner::corners() const -{ - return corners_; -} +// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // -const labelHashSet& meshSurfacePartitioner::edgeNodes() const -{ - return edgeNodes_; -} +meshSurfacePartitioner::~meshSurfacePartitioner() +{} -label meshSurfacePartitioner::numberOfFeatureEdgesAtPoint(const label bpI) const -{ - return label(nEdgesAtPoint_[bpI]); -} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -const List<labelHashSet>& meshSurfacePartitioner::partitionPartitions() const -{ - return partitionPartitions_; -} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.H b/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.H index 01ee110860688183241e39b890ce9d9fa76eff00..9c0aec7c36134dcabce03fe1505f81179dc6cb5b 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.H +++ b/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitioner.H @@ -1,32 +1,31 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class meshSurfacePartitioner Description - Finds corners and edge nodes at the surface of the volume mesh + Finds corners and edge points at the surface of the volume mesh SourceFiles meshSurfacePartitioner.C @@ -37,8 +36,11 @@ SourceFiles #define meshSurfacePartitioner_H #include "meshSurfaceEngine.H" +#include "VRWGraph.H" #include "HashSet.H" +#include <map> + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // namespace Foam @@ -52,22 +54,31 @@ class meshSurfacePartitioner { // Private data //- reference to mesh surface engine - const meshSurfaceEngine& meshSurface_; - - //- labels of corner nodes + const meshSurfaceEngine& meshSurface_; + + //- pointer to face patches + const labelList& facePatch_; + + //- patches at a surface point + VRWGraph pointPatches_; + + //- labels of corner points labelHashSet corners_; - - //- labels of edge nodes - labelHashSet edgeNodes_; - - //- partition-partitions addressing - List<labelHashSet> partitionPartitions_; - + + //- labels of edge points + labelHashSet edgePoints_; + + //- patch-patches addressing + List<labelHashSet> patchPatches_; + //- number of edges attached to a surface point labelList nEdgesAtPoint_; + //- labels of feature edges + labelHashSet featureEdges_; + // Private member functions - //- find corners, edge nodes and addressing + //- find corners, edge points and addressing void calculateCornersEdgesAndAddressing(); //- Disallow default bitwise copy construct @@ -77,28 +88,73 @@ class meshSurfacePartitioner void operator=(const meshSurfacePartitioner&); public: - + // Constructors - //- Construct from mesh + //- Construct from meshSurfaceEngine meshSurfacePartitioner(const meshSurfaceEngine&); + //- Construct from meshSurfaceEngine and face patches + meshSurfacePartitioner + ( + const meshSurfaceEngine& meshSurface, + const labelList& facePatch + ); + // Destructor ~meshSurfacePartitioner(); // Member Functions - //- return labels of corner nodes (from the list of boundary points) - const labelHashSet& corners() const; - - //- return labels of edge nodes (from the list of boundary points) - const labelHashSet& edgeNodes() const; + //- return const reference to meshSurfaceEngine + inline const meshSurfaceEngine& surfaceEngine() const + { + return meshSurface_; + } + + //- return const reference to a list containing boudary patch index + //- for each boundary face + inline const labelList& boundaryFacePatches() const + { + return facePatch_; + } + + //- return const reference to a graph of patches attached to a surface + //- point + inline const VRWGraph& pointPatches() const + { + return pointPatches_; + } + + //- return labels of corner points (from the list of boundary points) + inline const labelHashSet& corners() const + { + return corners_; + } + + //- return labels of edge points (from the list of boundary points) + inline const labelHashSet& edgePoints() const + { + return edgePoints_; + } //- return the number of feature edges attached to a boundary point - label numberOfFeatureEdgesAtPoint(const label bpI) const; - - //- return partition-partitions addressing - const List<labelHashSet>& partitionPartitions() const; + inline label numberOfFeatureEdgesAtPoint(const label bpI) const + { + return nEdgesAtPoint_[bpI]; + } + + //- return patch-patches addressing + inline const List<labelHashSet>& patchPatches() const + { + return patchPatches_; + } + + //- return labels of boundary edges which are feature edges + inline const labelHashSet& featureEdges() const + { + return featureEdges_; + } }; diff --git a/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitionerFunctions.C b/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitionerFunctions.C index e8fecab80131845a7fa0feaa835fc377ff230aee..d15295ebea76394ec76903b5ba450dec8035bcf8 100644 --- a/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitionerFunctions.C +++ b/meshLibrary/utilities/surfaceTools/meshSurfacePartitioner/meshSurfacePartitionerFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,83 +41,136 @@ void meshSurfacePartitioner::calculateCornersEdgesAndAddressing() const labelList& bp = meshSurface_.bp(); const edgeList& edges = meshSurface_.edges(); const VRWGraph& edgeFaces = meshSurface_.edgeFaces(); - const labelList& facePatches = meshSurface_.boundaryFacePatches(); - - label nPatches(0); - forAll(facePatches, patchI) - nPatches = Foam::max(nPatches, facePatches[patchI] + 1); - + const VRWGraph& pointFaces = meshSurface_.pointFaces(); + corners_.clear(); - edgeNodes_.clear(); - partitionPartitions_.setSize(nPatches); - + edgePoints_.clear(); + + //- count the number of patches + label nPatches(0); + # ifdef USE_OMP + # pragma omp parallel + { + label localMax(0); + + forAll(facePatch_, bfI) + localMax = Foam::max(localMax, facePatch_[bfI]); + + # pragma omp critical + nPatches = Foam::max(localMax, nPatches); + } + # else + forAll(facePatch_, bfI) + nPatches = Foam::max(nPatches, facePatch_[bfI]); + # endif + ++nPatches; + + //- set the size and starting creating addressing + patchPatches_.setSize(nPatches); + nEdgesAtPoint_.clear(); - nEdgesAtPoint_.setSize(bPoints.size(), 0); - + nEdgesAtPoint_.setSize(bPoints.size()); + nEdgesAtPoint_ = 0; + + featureEdges_.clear(); + forAll(edgeFaces, edgeI) { if( edgeFaces.sizeOfRow(edgeI) != 2 ) continue; - - const label patch0 = facePatches[edgeFaces(edgeI, 0)]; - const label patch1 = facePatches[edgeFaces(edgeI, 1)]; - + + const label patch0 = facePatch_[edgeFaces(edgeI, 0)]; + const label patch1 = facePatch_[edgeFaces(edgeI, 1)]; + if( patch0 != patch1 ) { const edge& e = edges[edgeI]; ++nEdgesAtPoint_[bp[e.start()]]; ++nEdgesAtPoint_[bp[e.end()]]; - - partitionPartitions_[patch0].insert(patch1); - partitionPartitions_[patch1].insert(patch0); + + patchPatches_[patch0].insert(patch1); + patchPatches_[patch1].insert(patch0); + + featureEdges_.insert(edgeI); } } - + if( Pstream::parRun() ) { const Map<label>& otherFaceAtProc = meshSurface_.otherEdgeFaceAtProc(); - const Map<label>& otherFacePatch = meshSurface_.otherEdgeFacePatch(); - + + //- find patches on other procs sharing surface edges + Map<label> otherFacePatch; + + const DynList<label>& beNeiProcs = meshSurface_.beNeiProcs(); + const Map<label>& globalToLocalEdges = + meshSurface_.globalToLocalBndEdgeAddressing(); + + std::map<label, labelLongList> exchangeData; + forAll(beNeiProcs, i) + exchangeData.insert(std::make_pair(beNeiProcs[i], labelLongList())); + + forAllConstIter(Map<label>, globalToLocalEdges, it) + { + const label beI = it(); + + if( edgeFaces.sizeOfRow(beI) == 1 ) + { + labelLongList& data = exchangeData[otherFaceAtProc[beI]]; + + data.append(it.key()); + data.append(facePatch_[edgeFaces(beI, 0)]); + } + } + + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + for(label i=0;i<receivedData.size();) + { + const label geI = receivedData[i++]; + const label patchI = receivedData[i++]; + + otherFacePatch.insert(globalToLocalEdges[geI], patchI); + } + //- take into account feature edges at processor boundaries forAllConstIter(Map<label>, otherFaceAtProc, it) { const label beI = it.key(); - + if( it() <= Pstream::myProcNo() ) continue; - if( otherFacePatch[beI] != facePatches[edgeFaces(beI, 0)] ) + if( otherFacePatch[beI] != facePatch_[edgeFaces(beI, 0)] ) { const edge& e = edges[beI]; ++nEdgesAtPoint_[bp[e.start()]]; ++nEdgesAtPoint_[bp[e.end()]]; } } - + //- gather data on all processors - std::map<label, labelListPMG> exchangeData; + exchangeData.clear(); const DynList<label>& bpNeiProcs = meshSurface_.bpNeiProcs(); forAll(bpNeiProcs, i) - exchangeData.insert - ( - std::make_pair(bpNeiProcs[i], labelListPMG()) - ); - + exchangeData.insert(std::make_pair(bpNeiProcs[i], labelLongList())); + const Map<label>& globalToLocal = meshSurface_.globalToLocalBndPointAddressing(); const VRWGraph& bpAtProcs = meshSurface_.bpAtProcs(); forAllConstIter(Map<label>, globalToLocal, it) { const label bpI = it(); - + forAllRow(bpAtProcs, bpI, i) { const label procI = bpAtProcs(bpI, i); - + if( procI == Pstream::myProcNo() ) continue; - - labelListPMG& dts = exchangeData[procI]; - + + labelLongList& dts = exchangeData[procI]; + //- exchange data as follows: //- 1. global point label //- 2. number of feature edges connected to the vertex @@ -126,22 +178,23 @@ void meshSurfacePartitioner::calculateCornersEdgesAndAddressing() dts.append(nEdgesAtPoint_[bpI]); } } - + //- exchange information - labelListPMG receivedData; + receivedData.clear(); help::exchangeMap(exchangeData, receivedData); - + //- add the edges from other processors to the points label counter(0); while( counter < receivedData.size() ) { const label bpI = globalToLocal[receivedData[counter++]]; const label nEdges = receivedData[counter++]; - + nEdgesAtPoint_[bpI] += nEdges; } } - + + //- mark edges and corners forAll(nEdgesAtPoint_, bpI) { if( nEdgesAtPoint_[bpI] > 2 ) @@ -150,15 +203,69 @@ void meshSurfacePartitioner::calculateCornersEdgesAndAddressing() } else if( nEdgesAtPoint_[bpI] == 2 ) { - edgeNodes_.insert(bpI); + edgePoints_.insert(bpI); + } + } + + //- find patches at a surface points + pointPatches_.setSize(pointFaces.size()); + forAll(pointFaces, bpI) + { + forAllRow(pointFaces, bpI, pfI) + pointPatches_.appendIfNotIn(bpI, facePatch_[pointFaces(bpI, pfI)]); + } + + if( Pstream::parRun() ) + { + const Map<label>& globalToLocal = + meshSurface_.globalToLocalBndPointAddressing(); + const DynList<label>& bpNeiProcs = meshSurface_.bpNeiProcs(); + const VRWGraph& bpAtProcs = meshSurface_.bpAtProcs(); + + std::map<label, labelLongList> exchangeData; + forAll(bpNeiProcs, i) + exchangeData[bpNeiProcs[i]].clear(); + + forAllConstIter(Map<label>, globalToLocal, it) + { + const label bpI = it(); + + forAllRow(bpAtProcs, bpI, i) + { + const label neiProc = bpAtProcs(bpI, i); + + if( neiProc == Pstream::myProcNo() ) + continue; + + labelLongList& data = exchangeData[neiProc]; + + data.append(it.key()); + data.append(pointPatches_.sizeOfRow(bpI)); + forAllRow(pointPatches_, bpI, i) + data.append(pointPatches_(bpI, i)); + } + } + + //- exchange data with other prcessors + labelLongList receivedData; + help::exchangeMap(exchangeData, receivedData); + + label counter(0); + while( counter < receivedData.size() ) + { + const label bpI = globalToLocal[receivedData[counter++]]; + const label size = receivedData[counter++]; + + for(label i=0;i<size;++i) + pointPatches_.appendIfNotIn(bpI, receivedData[counter++]); } } - + label counter = corners_.size(); reduce(counter, sumOp<label>()); Info << "Found " << counter << " corners at the surface of the volume mesh" << endl; - counter = edgeNodes_.size(); + counter = edgePoints_.size(); reduce(counter, sumOp<label>()); Info << "Found " << counter << " edge points at the surface of the volume mesh" << endl; diff --git a/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.C b/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.C index 1f1aa91bc030a4808edfe4da9966efafdf8d688c..d8f1bb238014b5fb0dc7f67be45a43c78071911c 100644 --- a/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.C +++ b/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -38,50 +37,75 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void renameBoundaryPatches::calculateNewBoundary() { Info << "Renaming boundary patches" << endl; - - const dictionary& dict = meshDict_.subDict("renameBoundary"); - - std::map<word, label> patchToLabel; - forAll(mesh_.boundaries(), patchI) + + const dictionary& dict = meshDict_.subDict("renameBoundary"); + + std::map<word, label> patchToLabel; + forAll(mesh_.boundaries(), patchI) { - patchToLabel.insert - ( - std::pair<word, label> - ( - mesh_.boundaries()[patchI].patchName(), - patchI - ) - ); + patchToLabel.insert + ( + std::pair<word, label> + ( + mesh_.boundaries()[patchI].patchName(), + patchI + ) + ); } - - labelList patchToNew(mesh_.boundaries().size(), -1); - + + labelList patchToNew(mesh_.boundaries().size(), -1); + wordList newPatchNames(patchToNew.size()); wordList newPatchTypes(patchToNew.size()); std::map<word, label> newNameToPos; label newPatchI(0); - + //- read new patch names and types if( dict.found("newPatchNames") ) { - PtrList<entry> patchesToRename(dict.lookup("newPatchNames")); - + PtrList<entry> patchesToRename; + + if( dict.isDict("newPatchNames") ) + { + const dictionary& newPatchNames = dict.subDict("newPatchNames"); + const wordList keys = newPatchNames.toc(); + + patchesToRename.setSize(keys.size()); + + forAll(keys, patchI) + patchesToRename.set + ( + patchI, + newPatchNames.lookupEntry + ( + keys[patchI], + false, + false + ).clone() + ); + } + else + { + PtrList<entry> copyPatchesToRename(dict.lookup("newPatchNames")); + patchesToRename.transfer(copyPatchesToRename); + } + forAll(patchesToRename, patchI) { const word patchName = patchesToRename[patchI].keyword(); - + if( patchToLabel.find(patchName) == patchToLabel.end() ) { - Info<< "Patch " << patchName << " does not exist!!" << endl; + Info << "Patch " << patchName << " does not exist!!" << endl; continue; } - + if( !patchesToRename[patchI].isDict() ) { Warning << "Cannot rename patch " << patchName << endl; @@ -89,20 +113,20 @@ void renameBoundaryPatches::calculateNewBoundary() << endl; return; } - - const dictionary& pDict = patchesToRename[patchI].dict(); - + + const dictionary pDict = patchesToRename[patchI].dict(); + word newName(patchName); if( pDict.found("newName") ) newName = word(pDict.lookup("newName")); - + if( newNameToPos.find(newName) != newNameToPos.end() ) { //- patch with the same name already exists patchToNew[patchToLabel[patchName]] = newNameToPos[newName]; continue; } - + //- add a new patch newNameToPos.insert(std::pair<word, label>(newName, newPatchI)); newPatchNames[newPatchI] = newName; @@ -113,62 +137,73 @@ void renameBoundaryPatches::calculateNewBoundary() } else { - newPatchTypes[newPatchI] = "patch"; + newPatchTypes[newPatchI] = "wall"; } - + patchToNew[patchToLabel[patchName]] = newPatchI; ++newPatchI; } } - - word defaultName(""); - if( dict.found("defaultName") ) - defaultName = word(dict.lookup("defaultName")); - word defaultType("patch"); - if( dict.found("defaultType") ) - defaultType = word(dict.lookup("defaultType")); - + + word defaultName("walls"); if( dict.found("defaultName") ) + defaultName = word(dict.lookup("defaultName")); + word defaultType("wall"); + if( dict.found("defaultType") ) + defaultType = word(dict.lookup("defaultType")); + + if( dict.found("defaultName") && (newPatchI < patchToNew.size()) ) { - newNameToPos.insert(std::pair<word, label>(defaultName, newPatchI)); - newPatchNames[newPatchI] = defaultName; - newPatchTypes[newPatchI] = defaultType; - ++newPatchI; + bool addPatch(false); + forAll(patchToNew, patchI) + if( patchToNew[patchI] == -1 ) + { + addPatch = true; + break; + } + + if( addPatch ) + { + newNameToPos.insert(std::pair<word, label>(defaultName, newPatchI)); + newPatchNames[newPatchI] = defaultName; + newPatchTypes[newPatchI] = defaultType; + ++newPatchI; + } } - else - { - forAll(patchToNew, patchI) - { - if( patchToNew[patchI] != -1 ) - continue; - - patchToNew[patchI] = newPatchI; - newPatchNames[newPatchI] = mesh_.boundaries()[patchI].patchName(); - newPatchTypes[newPatchI] = mesh_.boundaries()[patchI].patchType(); - ++newPatchI; - } - } - + else + { + forAll(patchToNew, patchI) + { + if( patchToNew[patchI] != -1 ) + continue; + + patchToNew[patchI] = newPatchI; + newPatchNames[newPatchI] = mesh_.boundaries()[patchI].patchName(); + newPatchTypes[newPatchI] = mesh_.boundaries()[patchI].patchType(); + ++newPatchI; + } + } + if( newPatchI == 0 ) return; - + newPatchNames.setSize(newPatchI); newPatchTypes.setSize(newPatchI); - + //- start creating new boundary VRWGraph newBoundaryFaces; - labelListPMG newBoundaryOwners; - labelListPMG newBoundaryPatches; - - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + labelLongList newBoundaryOwners; + labelLongList newBoundaryPatches; + + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); const faceListPMG& faces = mesh_.faces(); const labelList& owner = mesh_.owner(); forAll(boundaries, patchI) { - const writePatch& wp = boundaries[patchI]; + const boundaryPatch& wp = boundaries[patchI]; const label start = wp.patchStart(); const label end = start + wp.patchSize(); - + if( patchToNew[patchI] == -1 ) { //- this patch is moved to the default patch @@ -190,7 +225,7 @@ void renameBoundaryPatches::calculateNewBoundary() } } } - + //- execute the modifier polyMeshGenModifier meshModifier(mesh_); meshModifier.replaceBoundary @@ -203,7 +238,7 @@ void renameBoundaryPatches::calculateNewBoundary() forAll(meshModifier.boundariesAccess(), patchI) meshModifier.boundariesAccess()[patchI].patchType() = newPatchTypes[patchI]; - + Info << "Finished renaming boundary patches" << endl; } @@ -212,21 +247,20 @@ void renameBoundaryPatches::calculateNewBoundary() renameBoundaryPatches::renameBoundaryPatches ( polyMeshGen& mesh, - const IOdictionary& meshDict + const IOdictionary& meshDict ) : - mesh_(mesh), - meshDict_(meshDict) + mesh_(mesh), + meshDict_(meshDict) { - if( meshDict.found("renameBoundary") ) - calculateNewBoundary(); + if( meshDict.found("renameBoundary") ) + calculateNewBoundary(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // renameBoundaryPatches::~renameBoundaryPatches() -{ -} +{} // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.H b/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.H index 26fec8383bf79568d51eaa709484d29735fa1724..7e35da86a36f50f15d2c9e674d58f0f2dcd98860 100644 --- a/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.H +++ b/meshLibrary/utilities/surfaceTools/renameBoundaryPatches/renameBoundaryPatches.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class renameBoundaryPatches @@ -54,14 +53,14 @@ class renameBoundaryPatches { // Private data //- mesh - polyMeshGen& mesh_; - - //- dictionary containing relevant information - const IOdictionary& meshDict_; + polyMeshGen& mesh_; + + //- dictionary containing relevant information + const IOdictionary& meshDict_; // Private member functions - //- calculate new boundary and replace the existing one - void calculateNewBoundary(); + //- calculate new boundary and replace the existing one + void calculateNewBoundary(); //- Disallow default bitwise copy construct renameBoundaryPatches(const renameBoundaryPatches&); @@ -76,8 +75,8 @@ public: //- Construct from mesh and IOdictionary renameBoundaryPatches ( - polyMeshGen& mesh, - const IOdictionary& meshDict + polyMeshGen& mesh, + const IOdictionary& meshDict ); // Destructor diff --git a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.C b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.C index 53cbc326bcd327884916771c04408c2a55dbefbe..0ea511ecb3ed724ac4b9ec3642997d1870082e19 100644 --- a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.C +++ b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,6 @@ Description # ifdef DEBUGMorph #include <sstream> -#include "writeMeshEnsight.H" #include "polyMeshGenAddressing.H" # endif @@ -46,32 +44,32 @@ namespace Foam void surfaceMorpherCells::replaceMeshBoundary() { - wordList patchNames(1); - patchNames[0] = "defaultFaces"; - - polyMeshGenModifier(mesh_).replaceBoundary - ( - patchNames, - newBoundaryFaces_, - newBoundaryOwners_, - newBoundaryPatches_ - ); + wordList patchNames(1); + patchNames[0] = "defaultFaces"; + + polyMeshGenModifier(mesh_).replaceBoundary + ( + patchNames, + newBoundaryFaces_, + newBoundaryOwners_, + newBoundaryPatches_ + ); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // surfaceMorpherCells::surfaceMorpherCells ( - polyMeshGen& mesh + polyMeshGen& mesh ) : - mesh_(mesh), + mesh_(mesh), nIntFaces_(0), boundaryVertex_(mesh.points().size()), - cellFlags_(mesh.cells().size()), - newBoundaryFaces_(), - newBoundaryOwners_(), - newBoundaryPatches_() + cellFlags_(mesh.cells().size()), + newBoundaryFaces_(), + newBoundaryOwners_(), + newBoundaryPatches_() { } @@ -82,102 +80,101 @@ surfaceMorpherCells::~surfaceMorpherCells() void surfaceMorpherCells::morphMesh() { - //- perform surface morphing - bool changed; - - # ifdef DEBUGMorph - label iter(0); - # endif - + //- perform surface morphing + bool changed; + + # ifdef DEBUGMorph + label iter(0); + # endif + do { - changed = false; - # ifdef DEBUGMorph - Info << "Iteration " << ++iter << endl; - # endif - - findBoundaryVertices(); - - findBoundaryCells(); - - if( removeCellsWithAllVerticesAtTheBoundary() ) - { - changed = true; - continue; - } - + changed = false; + # ifdef DEBUGMorph + Info << "Iteration " << ++iter << endl; + # endif + + findBoundaryVertices(); + + findBoundaryCells(); + + if( removeCellsWithAllVerticesAtTheBoundary() ) + { + changed = true; + continue; + } + if( morphInternalFaces() ) - { - changed = true; - continue; - } - - if( morphBoundaryFaces() ) - { - changed = true; - continue; - } - - # ifdef DEBUGMorph - mesh_.write(); - mesh_.addressingData().checkMesh(true); - fileName name("morphedMesh"); - std::ostringstream ss; - ss << iter; - name += ss.str(); - Info << "name " << name << endl; - writeMeshEnsight(mesh_, name); - ++iter; - - const cellListPMG& cells = mesh_.cells(); - const faceListPMG& faces = mesh_.faces(); - forAll(cells, cellI) - { - const cell& c = cells[cellI]; - - const edgeList edges = c.edges(faces); - List<direction> nAppearances(edges.size(), direction(0)); - - forAll(c, fI) - { - const edgeList fEdges = faces[c[fI]].edges(); - - forAll(fEdges, eI) - forAll(edges, eJ) - if( fEdges[eI] == edges[eJ] ) - { - ++nAppearances[eJ]; - break; - } - } - - bool closed(true); - forAll(nAppearances, eI) - if( nAppearances[eI] != 2 ) - { - closed = false; - Info << "Edge " << edges[eI] << " appears " - << label(nAppearances[eI]) << " times in cell " - << cellI << endl; - } - - if( !closed ) - { - Info << "Cell " << cellI << " consists of faces " << c << endl; - forAll(c, fI) - Info << "Face " << c[fI] << " is " << faces[c[fI]] << endl; - FatalErrorIn - ( - "void surfaceMorpherCells::morphMesh()" - ) << "Cell " << cellI << " is not topologically closed" - << abort(FatalError); - } - } - # endif + { + changed = true; + continue; + } + + if( morphBoundaryFaces() ) + { + changed = true; + continue; + } + + # ifdef DEBUGMorph + mesh_.write(); + mesh_.addressingData().checkMesh(true); + fileName name("morphedMesh"); + std::ostringstream ss; + ss << iter; + name += ss.str(); + Info << "name " << name << endl; + ++iter; + + const cellListPMG& cells = mesh_.cells(); + const faceListPMG& faces = mesh_.faces(); + forAll(cells, cellI) + { + const cell& c = cells[cellI]; + + const edgeList edges = c.edges(faces); + List<direction> nAppearances(edges.size(), direction(0)); + + forAll(c, fI) + { + const edgeList fEdges = faces[c[fI]].edges(); + + forAll(fEdges, eI) + forAll(edges, eJ) + if( fEdges[eI] == edges[eJ] ) + { + ++nAppearances[eJ]; + break; + } + } + + bool closed(true); + forAll(nAppearances, eI) + if( nAppearances[eI] != 2 ) + { + closed = false; + Info << "Edge " << edges[eI] << " appears " + << label(nAppearances[eI]) << " times in cell " + << cellI << endl; + } + + if( !closed ) + { + Info << "Cell " << cellI << " consists of faces " << c << endl; + forAll(c, fI) + Info << "Face " << c[fI] << " is " << faces[c[fI]] << endl; + FatalErrorIn + ( + "void surfaceMorpherCells::morphMesh()" + ) << "Cell " << cellI << " is not topologically closed" + << abort(FatalError); + } + } + # endif } while( changed ); - polyMeshGenModifier(mesh_).removeUnusedVertices(); + polyMeshGenModifier(mesh_).removeUnusedVertices(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.H b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.H index 3f5150636df9360cbb9e7c5da0df42137446d350..5c5e04b71d8941bd5c2730fc4bf173c871d9324a 100644 --- a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.H +++ b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCells.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class surfaceMorpherCells Description Changes the boundary of the mesh template, such that each boundary cell - has only one boundary face. + has only one boundary face. SourceFiles surfaceMorpherCells.C @@ -38,7 +37,7 @@ SourceFiles #define surfaceMorpherCells_H #include "polyMeshGenModifier.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "boolList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -53,49 +52,49 @@ namespace Foam class surfaceMorpherCells { // Private data - //- mesh modifier - polyMeshGen& mesh_; + //- mesh modifier + polyMeshGen& mesh_; - //- number of internal faces + //- number of internal faces label nIntFaces_; - - //- true for vertices which are at the boundary + + //- true for vertices which are at the boundary boolList boundaryVertex_; - - //- true for cells which are at the boundary - List<direction> cellFlags_; - - //- new boundary faces and owner cells - VRWGraph newBoundaryFaces_; - labelListPMG newBoundaryOwners_; - labelListPMG newBoundaryPatches_; - - // Private enumerators - enum cellTypes - { - NONE = 0, - BOUNDARY = 1, - CHANGED = 2 - }; + + //- true for cells which are at the boundary + List<direction> cellFlags_; + + //- new boundary faces and owner cells + VRWGraph newBoundaryFaces_; + labelLongList newBoundaryOwners_; + labelLongList newBoundaryPatches_; + + // Private enumerators + enum cellTypes + { + NONE = 0, + BOUNDARY = 1, + CHANGED = 2 + }; // Private member functions //- find surface vertices void findBoundaryVertices(); - - //- find boundary cells - void findBoundaryCells(); - - //- remove cells with all vertices at the boundary - bool removeCellsWithAllVerticesAtTheBoundary(); - - //- morph boundary faces + + //- find boundary cells + void findBoundaryCells(); + + //- remove cells with all vertices at the boundary + bool removeCellsWithAllVerticesAtTheBoundary(); + + //- morph boundary faces bool morphBoundaryFaces(); - + //- morph internal faces - bool morphInternalFaces(); - - //- replace the boundary of the mesh with the newly created one - void replaceMeshBoundary(); + bool morphInternalFaces(); + + //- replace the boundary of the mesh with the newly created one + void replaceMeshBoundary(); //- Disallow default bitwise copy construct surfaceMorpherCells(const surfaceMorpherCells&); diff --git a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsCreateBoundaryFaces.C b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsCreateBoundaryFaces.C index 04aecc4b3f8f4950ac3edfa6e79aec4798b7e068..20304fdcf3cf8185d07bd2b355e8a4371bf0a716 100644 --- a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsCreateBoundaryFaces.C +++ b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsCreateBoundaryFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -46,211 +45,211 @@ namespace Foam bool surfaceMorpherCells::removeCellsWithAllVerticesAtTheBoundary() { - boolList removeCells(cellFlags_.size(), false); - - const faceListPMG& faces = mesh_.faces(); - const cellListPMG& cells = mesh_.cells(); - - bool changed(false); - - label nRemoved(0); - forAll(cellFlags_, cellI) - if( cellFlags_[cellI] & BOUNDARY ) - { - const cell& c = cells[cellI]; - //- remove cells which have all their vertices at the boundary - bool allBoundary(true); - - const labelList labels = c.labels(faces); - - forAll(labels, lI) - if( !boundaryVertex_[labels[lI]] ) - { - allBoundary = false; - break; - } - - if( allBoundary ) - { - ++nRemoved; - changed = true; - removeCells[cellI] = true; - } - - //- remove cells which are not topologically closed - DynList<edge> edges(24); - DynList<direction> nAppearances(24); - - forAll(c, fI) - { - const face& f = faces[c[fI]]; - forAll(f, eI) - { - const label pos = edges.containsAtPosition(f.faceEdge(eI)); - - if( pos == -1 ) - { - edges.append(f.faceEdge(eI)); - nAppearances.append(1); - } - else - { - ++nAppearances[pos]; - } - } - } - - forAll(nAppearances, eI) - if( nAppearances[eI] != 2 ) - { - ++nRemoved; - changed = true; - removeCells[cellI] = true; - } - - } - + boolList removeCells(cellFlags_.size(), false); + + const faceListPMG& faces = mesh_.faces(); + const cellListPMG& cells = mesh_.cells(); + + bool changed(false); + + label nRemoved(0); + forAll(cellFlags_, cellI) + if( cellFlags_[cellI] & BOUNDARY ) + { + const cell& c = cells[cellI]; + //- remove cells which have all their vertices at the boundary + bool allBoundary(true); + + const labelList labels = c.labels(faces); + + forAll(labels, lI) + if( !boundaryVertex_[labels[lI]] ) + { + allBoundary = false; + break; + } + + if( allBoundary ) + { + ++nRemoved; + changed = true; + removeCells[cellI] = true; + } + + //- remove cells which are not topologically closed + DynList<edge> edges; + DynList<direction> nAppearances; + + forAll(c, fI) + { + const face& f = faces[c[fI]]; + forAll(f, eI) + { + const label pos = edges.containsAtPosition(f.faceEdge(eI)); + + if( pos == -1 ) + { + edges.append(f.faceEdge(eI)); + nAppearances.append(1); + } + else + { + ++nAppearances[pos]; + } + } + } + + forAll(nAppearances, eI) + if( nAppearances[eI] != 2 ) + { + ++nRemoved; + changed = true; + removeCells[cellI] = true; + } + + } + if( Pstream::parRun() ) reduce(nRemoved, sumOp<label>()); - + if( nRemoved != 0 ) - { - Info << "Removing " << nRemoved - << " cells which cannot be morphed" << endl; - polyMeshGenModifier(mesh_).removeCells(removeCells); - } - + { + Info << "Removing " << nRemoved + << " cells which cannot be morphed" << endl; + polyMeshGenModifier(mesh_).removeCells(removeCells); + } + if( Pstream::parRun() ) { reduce(changed, maxOp<bool>()); } - - return changed; + + return changed; } bool surfaceMorpherCells::morphBoundaryFaces() { Info << "Morphing boundary faces" << endl; - - newBoundaryFaces_.setSize(0); - newBoundaryOwners_.setSize(0); - newBoundaryPatches_.setSize(0); - - const faceListPMG& faces = mesh_.faces(); - const cellListPMG& cells = mesh_.cells(); - - bool changed(false); - - forAll(cells, cellI) - if( cellFlags_[cellI] & BOUNDARY ) - { - const cell& c = cells[cellI]; - - DynList<label> bFaces(c.size()); - - forAll(c, fI) - if( mesh_.faceIsInPatch(c[fI]) != -1 ) - bFaces.append(c[fI]); - - # ifdef DEBUGMorph - Info << "Boundary faces in cell " << cellI - << " are " << bFaces << endl; - forAll(bFaces, bfI) - Info << "Face " << bFaces[bfI] << " is " - << faces[bFaces[bfI]] << endl; - # endif - - boolList mergedFaces(bFaces.size(), false); - - face mf = faces[bFaces[0]]; - mergedFaces[0] = true; - - bool finished; - do - { - finished = true; - for(label i=1;i<bFaces.size();++i) - { - if( mergedFaces[i] ) continue; - - const face& bf = faces[bFaces[i]]; - const edgeList bEdges = bf.edges(); - const edgeList mEdges = mf.edges(); - - direction nSharedEdges(0); - forAll(bEdges, eI) - forAll(mEdges, eJ) - if( bEdges[eI] == mEdges[eJ] ) - ++nSharedEdges; - - direction nSharedPoints(0); - forAll(bf, pI) - forAll(mf, pJ) - if( bf[pI] == mf[pJ] ) - ++nSharedPoints; - - if( - nSharedEdges && - ((nSharedEdges + 1) == nSharedPoints) - ) - { - mf = help::mergeTwoFaces(mf, bf); - mergedFaces[i] = true; - changed = true; - finished = false; - - //- set CHANGED flag - cellFlags_[cellI] |= CHANGED; - } - } - } while( !finished ); - - newBoundaryFaces_.appendList(mf); - newBoundaryOwners_.append(cellI); - newBoundaryPatches_.append(0); - - # ifdef DEBUGMorph - Info << "Adding merged face " << mf << endl; - # endif - - for(label i=1;i<bFaces.size();++i) - if( !mergedFaces[i] ) - { - newBoundaryFaces_.appendList(faces[bFaces[i]]); - newBoundaryOwners_.append(cellI); - newBoundaryPatches_.append(0); - - # ifdef DEBUGMorph - Info << "Adding untouched boundary face " - << faces[bFaces[i]] << endl; - # endif - } - } - + + newBoundaryFaces_.setSize(0); + newBoundaryOwners_.setSize(0); + newBoundaryPatches_.setSize(0); + + const faceListPMG& faces = mesh_.faces(); + const cellListPMG& cells = mesh_.cells(); + + bool changed(false); + + forAll(cells, cellI) + if( cellFlags_[cellI] & BOUNDARY ) + { + const cell& c = cells[cellI]; + + DynList<label> bFaces; + + forAll(c, fI) + if( mesh_.faceIsInPatch(c[fI]) != -1 ) + bFaces.append(c[fI]); + + # ifdef DEBUGMorph + Info << "Boundary faces in cell " << cellI + << " are " << bFaces << endl; + forAll(bFaces, bfI) + Info << "Face " << bFaces[bfI] << " is " + << faces[bFaces[bfI]] << endl; + # endif + + boolList mergedFaces(bFaces.size(), false); + + face mf = faces[bFaces[0]]; + mergedFaces[0] = true; + + bool finished; + do + { + finished = true; + for(label i=1;i<bFaces.size();++i) + { + if( mergedFaces[i] ) continue; + + const face& bf = faces[bFaces[i]]; + const edgeList bEdges = bf.edges(); + const edgeList mEdges = mf.edges(); + + direction nSharedEdges(0); + forAll(bEdges, eI) + forAll(mEdges, eJ) + if( bEdges[eI] == mEdges[eJ] ) + ++nSharedEdges; + + direction nSharedPoints(0); + forAll(bf, pI) + forAll(mf, pJ) + if( bf[pI] == mf[pJ] ) + ++nSharedPoints; + + if( + nSharedEdges && + ((nSharedEdges + 1) == nSharedPoints) + ) + { + mf = help::mergeTwoFaces(mf, bf); + mergedFaces[i] = true; + changed = true; + finished = false; + + //- set CHANGED flag + cellFlags_[cellI] |= CHANGED; + } + } + } while( !finished ); + + newBoundaryFaces_.appendList(mf); + newBoundaryOwners_.append(cellI); + newBoundaryPatches_.append(0); + + # ifdef DEBUGMorph + Info << "Adding merged face " << mf << endl; + # endif + + for(label i=1;i<bFaces.size();++i) + if( !mergedFaces[i] ) + { + newBoundaryFaces_.appendList(faces[bFaces[i]]); + newBoundaryOwners_.append(cellI); + newBoundaryPatches_.append(0); + + # ifdef DEBUGMorph + Info << "Adding untouched boundary face " + << faces[bFaces[i]] << endl; + # endif + } + } + if( Pstream::parRun() ) { reduce(changed, maxOp<bool>()); } - - if( changed ) - { - replaceMeshBoundary(); - } - - # ifdef DEBUGMorph - labelHashSet zipCells; - mesh_.addressingData().checkCellsZipUp(true, &zipCells); - if( zipCells.size() ) - { - Info << "Cells " << zipCells << " are not zipped!!" << endl; - ::exit(EXIT_FAILURE); - } - mesh_.clearAddressingData(); - # endif + + if( changed ) + { + replaceMeshBoundary(); + } + + # ifdef DEBUGMorph + labelHashSet zipCells; + mesh_.addressingData().checkCellsZipUp(true, &zipCells); + if( zipCells.size() ) + { + Info << "Cells " << zipCells << " are not zipped!!" << endl; + ::exit(EXIT_FAILURE); + } + mesh_.clearAddressingData(); + # endif Info << "Finished morphing boundary faces" << endl; - - return changed; + + return changed; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsMorphInternalFaces.C b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsMorphInternalFaces.C index 7df58c02aeafdd0a96da34b7c79688d472dbacb3..8f4c6216b2e80456d282984f95d7d6741b13537f 100644 --- a/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsMorphInternalFaces.C +++ b/meshLibrary/utilities/surfaceTools/surfaceMorpherCells/surfaceMorpherCellsMorphInternalFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,7 +34,6 @@ Description #ifdef DEBUGMorph #include "polyMeshGenAddressing.H" -#include "writeMeshEnsight.H" #endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -52,7 +50,7 @@ void surfaceMorpherCells::findBoundaryVertices() boundaryVertex_.setSize(mesh_.points().size()); boundaryVertex_ = false; - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { const label start = boundaries[patchI].patchStart(); @@ -80,7 +78,7 @@ void surfaceMorpherCells::findBoundaryVertices() if( Pstream::parRun() ) { - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); bool changed; @@ -97,7 +95,7 @@ void surfaceMorpherCells::findBoundaryVertices() //- create information about bnd nodes which must be exchanged //- with other processors labelHashSet addToSend; - labelListPMG dts; + labelLongList dts; for(label faceI=start;faceI<end;++faceI) { const face& f = faces[faceI]; @@ -166,7 +164,7 @@ void surfaceMorpherCells::findBoundaryCells() cellFlags_.setSize(mesh_.cells().size()); cellFlags_ = NONE; - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { @@ -206,7 +204,7 @@ bool surfaceMorpherCells::morphInternalFaces() const labelList& neighbour = mesh_.neighbour(); //- copy boundary faces - const PtrList<writePatch>& boundaries = mesh_.boundaries(); + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); forAll(boundaries, patchI) { @@ -230,8 +228,7 @@ bool surfaceMorpherCells::morphInternalFaces() const face& f = faces[faceI]; - boolList removeFaceVertex(f.size(), false); - DynList<edge> removeEdge(f.size()); + DynList<bool> removeFaceVertex(f.size(), false); face newF(f.size()); label i(0); @@ -245,9 +242,6 @@ bool surfaceMorpherCells::morphInternalFaces() { removeFaceVertex[pI] = true; - removeEdge.appendIfNotIn(f.faceEdge(f.rcIndex(pI))); - removeEdge.appendIfNotIn(f.faceEdge(pI)); - # ifdef DEBUGMorph Info << "Removing vertex " << f[pI] << " from face " << f << endl; @@ -275,12 +269,12 @@ bool surfaceMorpherCells::morphInternalFaces() //- create new boundary faces from the removed part label mat(1); - List<direction> nodeMaterial(f.size(), direction(0)); + DynList<direction> nodeMaterial(f.size(), direction(0)); DynList<DynList<edge>, 2> edgeMats; forAll(nodeMaterial, nI) if( !nodeMaterial[nI] && removeFaceVertex[nI] ) { - edgeMats.append(DynList<edge>(f.size())); + edgeMats.append(DynList<edge>()); DynList<label> front; front.append(nI); @@ -339,7 +333,7 @@ bool surfaceMorpherCells::morphInternalFaces() //- treat processor boundaries if( Pstream::parRun() ) { - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); forAll(procBoundaries, patchI) @@ -362,11 +356,10 @@ bool surfaceMorpherCells::morphInternalFaces() const face& f = copy; - boolList removeFaceVertex(f.size(), false); - DynList<edge> removeEdge(f.size()); + DynList<bool> removeFaceVertex(f.size(), false); face newF(f.size()); - direction i(0); + label i(0); forAll(f, pI) if( @@ -377,9 +370,6 @@ bool surfaceMorpherCells::morphInternalFaces() { removeFaceVertex[pI] = true; - removeEdge.appendIfNotIn(f.faceEdge(f.rcIndex(pI))); - removeEdge.appendIfNotIn(f.faceEdge(pI)); - # ifdef DEBUGMorph Info << "Removing vertex " << f[pI] << " from face " << f << endl; @@ -407,12 +397,12 @@ bool surfaceMorpherCells::morphInternalFaces() //- create new boundary faces from the removed part label mat(1); - List<direction> nodeMaterial(f.size(), direction(0)); - DynList< DynList<edge> > edgeMats(2); + DynList<direction> nodeMaterial(f.size(), direction(0)); + DynList< DynList<edge> > edgeMats; forAll(nodeMaterial, nI) if( !nodeMaterial[nI] && removeFaceVertex[nI] ) { - edgeMats.append(DynList<edge>(f.size())); + edgeMats.append(DynList<edge>()); DynList<label> front; front.append(nI); @@ -550,7 +540,7 @@ bool surfaceMorpherCells::morphInternalFaces() if( Pstream::parRun() ) { - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = mesh_.procBoundaries(); forAll(procBoundaries, patchI) @@ -577,10 +567,9 @@ bool surfaceMorpherCells::morphInternalFaces() labelHashSet zipCells; mesh_.addressingData().checkCellsZipUp(true, &zipCells); if( zipCells.size() ) - { + { Serr << Pstream::myProcNo() << "Open cells appeared!" << endl; //mesh_.write(); - //writeMeshEnsight(mesh_, "openMeshAfterInternalMorph"); Serr << "Cells " << zipCells << " are not zipped!!" << endl; } mesh_.clearAddressingData(); diff --git a/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.C b/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.C index 98dbda50233b07ddc985b332d9b96d7db46cb93b..3bb80379dae183397a076b900b29053b2ef89427 100644 --- a/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.C +++ b/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,50 +41,50 @@ namespace Foam void triangulateNonPlanarBoundaryFaces::findBoundaryCellsToDecompose() { - const pointFieldPMG& points = mesh_.points(); - const labelList& owner = mesh_.owner(); - const faceListPMG& faces = mesh_.faces(); - - const PtrList<writePatch>& boundaries = mesh_.boundaries(); - - label nDecompose(0); - - forAll(boundaries, patchI) - { - const label start = boundaries[patchI].patchStart(); - const label end = start + boundaries[patchI].patchSize(); - - for(label faceI=start;faceI<end;++faceI) - { - const face& f = faces[faceI]; - - forAll(f, pI) - pointPatches_[f[pI]].appendIfNotIn(patchI); - - //- do not waste time on triangles - if( f.size() < 4 ) continue; - - if( !faceDecomposition(f, points).isFacePlanar() ) - { - ++nDecompose; - decomposeCell_[owner[faceI]] = true; - } - } - } - - Info << "Found " << nDecompose << " non-planar boundary faces" << endl; + const pointFieldPMG& points = mesh_.points(); + const labelList& owner = mesh_.owner(); + const faceListPMG& faces = mesh_.faces(); + + const PtrList<boundaryPatch>& boundaries = mesh_.boundaries(); + + label nDecompose(0); + + forAll(boundaries, patchI) + { + const label start = boundaries[patchI].patchStart(); + const label end = start + boundaries[patchI].patchSize(); + + for(label faceI=start;faceI<end;++faceI) + { + const face& f = faces[faceI]; + + forAll(f, pI) + pointPatches_[f[pI]].appendIfNotIn(patchI); + + //- do not waste time on triangles + if( f.size() < 4 ) continue; + + if( !faceDecomposition(f, points).isFacePlanar() ) + { + ++nDecompose; + decomposeCell_[owner[faceI]] = true; + } + } + } + + Info << "Found " << nDecompose << " non-planar boundary faces" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // triangulateNonPlanarBoundaryFaces::triangulateNonPlanarBoundaryFaces ( - polyMeshGen& mesh + polyMeshGen& mesh ) : - mesh_(mesh), + mesh_(mesh), decomposeCell_(mesh.cells().size(), false), - pointPatches_(mesh.points().size()) + pointPatches_(mesh.points().size()) { } @@ -98,13 +97,13 @@ void triangulateNonPlanarBoundaryFaces::decomposeMesh() { FatalError << "Not implemented" << exit(FatalError); - Info << "Decomposing non-planar boundary faces" << endl; - findBoundaryCellsToDecompose(); - - decomposeCells decomposeNonPlanarCells(mesh_); - decomposeNonPlanarCells.decomposeMesh(decomposeCell_); - - Info << "Finished decomposing non-planar boundary faces" << endl; + Info << "Decomposing non-planar boundary faces" << endl; + findBoundaryCellsToDecompose(); + + decomposeCells decomposeNonPlanarCells(mesh_); + decomposeNonPlanarCells.decomposeMesh(decomposeCell_); + + Info << "Finished decomposing non-planar boundary faces" << endl; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.H b/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.H index e04d1940450f08cdb72556bab5bb768a9aa2c767..92934076745243fc91de3d055ac01dbbfb24fd4e 100644 --- a/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.H +++ b/meshLibrary/utilities/surfaceTools/triangulateNonPlanarBoundaryFaces/triangulateNonPlanarBoundaryFaces.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triangulateNonPlanarBoundaryFaces @@ -51,12 +50,12 @@ namespace Foam class triangulateNonPlanarBoundaryFaces { // Private data - //- mesh modifier - polyMeshGen& mesh_; + //- mesh modifier + polyMeshGen& mesh_; boolList decomposeCell_; - - VRWGraph pointPatches_; + + VRWGraph pointPatches_; // Private member functions //- find surface vertices diff --git a/meshLibrary/utilities/tetrahedra/delaunayTessellation.tgz b/meshLibrary/utilities/tetrahedra/delaunayTessellation.tgz index ce4b7f35e0ae31ab9dede81c4050b7cd860374ab..3fed52b68d2b4d764b35a5210d80e995fd9df0ce 100644 Binary files a/meshLibrary/utilities/tetrahedra/delaunayTessellation.tgz and b/meshLibrary/utilities/tetrahedra/delaunayTessellation.tgz differ diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.C b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.C index f4ac52afa942556bec71ad3469d222fcd969ee70..059306661826f750759299e61378835c26fa3636 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.C +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,116 +35,116 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + const meshOctreeCubeCoordinates tetCreatorOctree::edgeCoordinates_[12][4]= - { - { //- edge 0 - meshOctreeCubeCoordinates(0, 0, 1, 0), - meshOctreeCubeCoordinates(0, -1, 1, 0), - meshOctreeCubeCoordinates(0, -1, 0, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0) - }, - { //- edge 1 - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(0, -1, 0, 0), - meshOctreeCubeCoordinates(0, -1, -1, 0), - meshOctreeCubeCoordinates(0, 0, -1, 0) - }, - { //- edge 2 - meshOctreeCubeCoordinates(0, 1, 0, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(0, 0, -1, 0), - meshOctreeCubeCoordinates(0, 1, -1, 0) - }, - { //- edge 3 - meshOctreeCubeCoordinates(0, 1, 1, 0), - meshOctreeCubeCoordinates(0, 0, 1, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(0, 1, 0, 0) - }, - { //- edge 4 - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(0, 0, 1, 0), - meshOctreeCubeCoordinates(1, 0, 1, 0), - meshOctreeCubeCoordinates(1, 0, 0, 0) - }, - { //- edge 5 - meshOctreeCubeCoordinates(0, 0, -1, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(1, 0, 0, 0), - meshOctreeCubeCoordinates(1, 0, -1, 0) - }, - { //- edge 6 - meshOctreeCubeCoordinates(-1, 0, -1, 0), - meshOctreeCubeCoordinates(-1, 0, 0, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(0, 0, -1, 0) - }, - { //- edge 7 - meshOctreeCubeCoordinates(-1, 0, 0, 0), - meshOctreeCubeCoordinates(-1, 0, 1, 0), - meshOctreeCubeCoordinates(0, 0, 1, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0) - }, - { //- edge 8 - meshOctreeCubeCoordinates(-1, 0, 0, 0), - meshOctreeCubeCoordinates(-1, -1, 0, 0), - meshOctreeCubeCoordinates(0, -1, 0, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0) - }, - { //- edge 9 - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(0, -1, 0, 0), - meshOctreeCubeCoordinates(1, -1, 0, 0), - meshOctreeCubeCoordinates(1, 0, 0, 0) - }, - { //- edge 10 - meshOctreeCubeCoordinates(0, 1, 0, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(1, 0, 0, 0), - meshOctreeCubeCoordinates(1, 1, 0, 0) - }, - { //- edge 11 - meshOctreeCubeCoordinates(-1, 1, 0, 0), - meshOctreeCubeCoordinates(-1, 0, 0, 0), - meshOctreeCubeCoordinates(0, 0, 0, 0), - meshOctreeCubeCoordinates(0, 1, 0, 0) - } - }; - + { + { //- edge 0 + meshOctreeCubeCoordinates(0, 0, 1, 0), + meshOctreeCubeCoordinates(0, -1, 1, 0), + meshOctreeCubeCoordinates(0, -1, 0, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0) + }, + { //- edge 1 + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(0, -1, 0, 0), + meshOctreeCubeCoordinates(0, -1, -1, 0), + meshOctreeCubeCoordinates(0, 0, -1, 0) + }, + { //- edge 2 + meshOctreeCubeCoordinates(0, 1, 0, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(0, 0, -1, 0), + meshOctreeCubeCoordinates(0, 1, -1, 0) + }, + { //- edge 3 + meshOctreeCubeCoordinates(0, 1, 1, 0), + meshOctreeCubeCoordinates(0, 0, 1, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(0, 1, 0, 0) + }, + { //- edge 4 + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(0, 0, 1, 0), + meshOctreeCubeCoordinates(1, 0, 1, 0), + meshOctreeCubeCoordinates(1, 0, 0, 0) + }, + { //- edge 5 + meshOctreeCubeCoordinates(0, 0, -1, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(1, 0, 0, 0), + meshOctreeCubeCoordinates(1, 0, -1, 0) + }, + { //- edge 6 + meshOctreeCubeCoordinates(-1, 0, -1, 0), + meshOctreeCubeCoordinates(-1, 0, 0, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(0, 0, -1, 0) + }, + { //- edge 7 + meshOctreeCubeCoordinates(-1, 0, 0, 0), + meshOctreeCubeCoordinates(-1, 0, 1, 0), + meshOctreeCubeCoordinates(0, 0, 1, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0) + }, + { //- edge 8 + meshOctreeCubeCoordinates(-1, 0, 0, 0), + meshOctreeCubeCoordinates(-1, -1, 0, 0), + meshOctreeCubeCoordinates(0, -1, 0, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0) + }, + { //- edge 9 + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(0, -1, 0, 0), + meshOctreeCubeCoordinates(1, -1, 0, 0), + meshOctreeCubeCoordinates(1, 0, 0, 0) + }, + { //- edge 10 + meshOctreeCubeCoordinates(0, 1, 0, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(1, 0, 0, 0), + meshOctreeCubeCoordinates(1, 1, 0, 0) + }, + { //- edge 11 + meshOctreeCubeCoordinates(-1, 1, 0, 0), + meshOctreeCubeCoordinates(-1, 0, 0, 0), + meshOctreeCubeCoordinates(0, 0, 0, 0), + meshOctreeCubeCoordinates(0, 1, 0, 0) + } + }; + const label tetCreatorOctree::faceCentreHelper_[3][4] = - { - {3, 5, 2, 4}, - {5, 1, 4, 0}, - {1, 3, 0, 2} - }; + { + {3, 5, 2, 4}, + {5, 1, 4, 0}, + {1, 3, 0, 2} + }; void tetCreatorOctree::createTets() { - createPointsAndAddressing(); - - createTetsFromFacesWithCentreNode(); - - createTetsAroundSplitEdges(); - - createTetsAroundEdges(); - - createTetsFromSplitFaces(); - - clearOut(); - sortedLeaves_.setSize(0); - - created_ = true; + createPointsAndAddressing(); + + createTetsFromFacesWithCentreNode(); + + createTetsAroundSplitEdges(); + + createTetsAroundEdges(); + + createTetsFromSplitFaces(); + + clearOut(); + sortedLeaves_.setSize(0); + + created_ = true; } void tetCreatorOctree::clearOut() { - sortedLeaves_.clear(); - deleteDemandDrivenData(subNodeLabelsPtr_); - deleteDemandDrivenData(cubeLabelPtr_); - deleteDemandDrivenData(faceCentreLabelPtr_); + sortedLeaves_.clear(); + deleteDemandDrivenData(subNodeLabelsPtr_); + deleteDemandDrivenData(cubeLabelPtr_); + deleteDemandDrivenData(faceCentreLabelPtr_); } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -154,28 +153,28 @@ void tetCreatorOctree::clearOut() tetCreatorOctree::tetCreatorOctree ( const meshOctree& octree, - const IOdictionary& meshDict + const IOdictionary& meshDict ) : octreeCheck_(octree, meshDict, true), - tetPoints_(), - tets_(), - sortedLeaves_(), - subNodeLabelsPtr_(NULL), - cubeLabelPtr_(NULL), - faceCentreLabelPtr_(NULL), - created_(false) + tetPoints_(), + tets_(), + sortedLeaves_(), + subNodeLabelsPtr_(NULL), + cubeLabelPtr_(NULL), + faceCentreLabelPtr_(NULL), + created_(false) { - createTets(); - - clearOut(); + createTets(); + + clearOut(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // tetCreatorOctree::~tetCreatorOctree() { - clearOut(); + clearOut(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.H b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.H index d5c1b4f4326cf33a45ac5a9b5eb9083d2c69f812..3ffdb443aa91fa2858def1fa17283a72e0662b37 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.H +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctree.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class tetCreatorOctree @@ -41,7 +40,7 @@ SourceFiles #include "meshOctreeAddressing.H" #include "meshOctreeCubeCoordinates.H" #include "VRWGraph.H" -#include "labelListPMG.H" +#include "labelLongList.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -55,69 +54,69 @@ namespace Foam class tetCreatorOctree { // Private data - //- helper for searching coordinates of cubes around an edge - static const meshOctreeCubeCoordinates edgeCoordinates_[12][4]; - - //- helper for finding face centres of cubes sharing an edge - static const label faceCentreHelper_[3][4]; - + //- helper for searching coordinates of cubes around an edge + static const meshOctreeCubeCoordinates edgeCoordinates_[12][4]; + + //- helper for finding face centres of cubes sharing an edge + static const label faceCentreHelper_[3][4]; + //- reference to the octree meshOctreeAddressing octreeCheck_; - - //- points of the tetrahedrisation - LongList<point> tetPoints_; - - //- tetrahedra - LongList<partTet> tets_; - - //- octree leaves sorted according to their level - List<labelListPMG> sortedLeaves_; - - //- node labels of vertices created inside split-hex boxes - VRWGraph* subNodeLabelsPtr_; - - //- cube centre label - labelList* cubeLabelPtr_; - - //- cube face label - VRWGraph* faceCentreLabelPtr_; - - //- are tets created or not - bool created_; - + + //- points of the tetrahedrisation + LongList<point> tetPoints_; + + //- tetrahedra + LongList<partTet> tets_; + + //- octree leaves sorted according to their level + List<labelLongList> sortedLeaves_; + + //- node labels of vertices created inside split-hex boxes + VRWGraph* subNodeLabelsPtr_; + + //- cube centre label + labelList* cubeLabelPtr_; + + //- cube face label + VRWGraph* faceCentreLabelPtr_; + + //- are tets created or not + bool created_; + // Private member functions - //- deletes all pointer data - void clearOut(); - - //- find elements which will be used as mesh cells - void selectElements(); - - // Private member functions for creating tetrahedra - //- create tetPoints_ and necessary addressing - void createPointsAndAddressing(); - - //- create faceCentreLabelPtr_ - void createFaceCentreLabels(); - - //- create tetrahedra from faces, owner and neighbour - void createTetsAroundEdges(); - - //- create tetrahedra from split faces - void createTetsFromSplitFaces(); - - //- create tetrahedra from faces which share at least one edge - //- with a refined cube - void createTetsFromFacesWithCentreNode(); - - //- create tetrahedra from faces with split edges - void createTetsAroundSplitEdges(); - - //- helper funtion which checks validity of a created tet and appends - //- it if valid - inline void checkAndAppendTet(const partTet); - - //- function containing the workflow - void createTets(); + //- deletes all pointer data + void clearOut(); + + //- find elements which will be used as mesh cells + void selectElements(); + + // Private member functions for creating tetrahedra + //- create tetPoints_ and necessary addressing + void createPointsAndAddressing(); + + //- create faceCentreLabelPtr_ + void createFaceCentreLabels(); + + //- create tetrahedra from faces, owner and neighbour + void createTetsAroundEdges(); + + //- create tetrahedra from split faces + void createTetsFromSplitFaces(); + + //- create tetrahedra from faces which share at least one edge + //- with a refined cube + void createTetsFromFacesWithCentreNode(); + + //- create tetrahedra from faces with split edges + void createTetsAroundSplitEdges(); + + //- helper funtion which checks validity of a created tet and appends + //- it if valid + inline void checkAndAppendTet(const partTet); + + //- function containing the workflow + void createTets(); // Private copy constructor //- Disallow default bitwise copy construct @@ -134,7 +133,7 @@ public: tetCreatorOctree ( const meshOctree& octree, - const IOdictionary& meshDict + const IOdictionary& meshDict ); // Destructor @@ -143,27 +142,27 @@ public: // Member Functions - const LongList<point>& tetPoints() const - { - if( !created_ ) - FatalErrorIn - ( - "const LongList<point>& tetPoints() const" - ) << "Tets are not created!" << exit(FatalError); - - return tetPoints_; - } - - const LongList<partTet>& tets() const - { - if( !created_ ) - FatalErrorIn - ( - "const LongList<point>& tets() const" - ) << "Tets are not created!" << exit(FatalError); - - return tets_; - } + const LongList<point>& tetPoints() const + { + if( !created_ ) + FatalErrorIn + ( + "const LongList<point>& tetPoints() const" + ) << "Tets are not created!" << exit(FatalError); + + return tetPoints_; + } + + const LongList<partTet>& tets() const + { + if( !created_ ) + FatalErrorIn + ( + "const LongList<point>& tets() const" + ) << "Tets are not created!" << exit(FatalError); + + return tets_; + } }; diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeFromFacesWithCentreNode.C b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeFromFacesWithCentreNode.C index 2abf7d8c084a0e6503eb5bea004d3feb2b04cff5..603cb1a35aaf1c0d19fdf149f4ae5b5572803f68 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeFromFacesWithCentreNode.C +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeFromFacesWithCentreNode.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,43 +34,43 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void tetCreatorOctree::createTetsFromFacesWithCentreNode() { - Info << "Creating tets from faces with centre node" << endl; + Info << "Creating tets from faces with centre node" << endl; + + const labelList& cubeLabel = *cubeLabelPtr_; + const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); + const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; + const FRWGraph<label, 8>& pointLeaves = octreeCheck_.nodeLeaves(); - const labelList& cubeLabel = *cubeLabelPtr_; - const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); - const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; - const FRWGraph<label, 8>& pointLeaves = octreeCheck_.nodeLeaves(); - - if( !faceCentreLabelPtr_ ) - faceCentreLabelPtr_ = new VRWGraph(cubeLabel.size()); - VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; - - //- start creating tets - forAll(pointLeaves, pointI) - { - label pl[8]; - bool create(true); - - for(label plI=0;plI<8;++plI) - { - pl[plI] = pointLeaves(pointI, plI); - if( pl[plI] == -1 ) - { - create = false; - break; - } - } - - if( !create ) - continue; - - //- create 6 tets for each possible combination - //- there are 12 possible combinations + if( !faceCentreLabelPtr_ ) + faceCentreLabelPtr_ = new VRWGraph(cubeLabel.size()); + VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; + + //- start creating tets + forAll(pointLeaves, pointI) + { + label pl[8]; + bool create(true); + + for(label plI=0;plI<8;++plI) + { + pl[plI] = pointLeaves(pointI, plI); + if( pl[plI] == -1 ) + { + create = false; + break; + } + } + + if( !create ) + continue; + + //- create 6 tets for each possible combination + //- there are 12 possible combinations for(label fI=0;fI<6;++fI) { const label* fEdges = meshOctreeCubeCoordinates::faceEdges_[fI]; @@ -196,7 +195,7 @@ void tetCreatorOctree::createTetsFromFacesWithCentreNode() } } } - } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeI.H b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeI.H index 16c428b75b92f60e284f5bb4431a54e069a72ccc..a84c534dd077a85ccf702bad2811ecab5506a70b 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeI.H +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,23 +32,23 @@ namespace Foam inline void tetCreatorOctree::checkAndAppendTet(const partTet pt) { - bool valid(true); - for(label n=0;n<4;++n) - if( pt[n] < 0 ) - { - valid = false; - break; - } - - if( valid ) - { + bool valid(true); + for(label n=0;n<4;++n) + if( pt[n] < 0 ) + { + valid = false; + break; + } + + if( valid ) + { tets_.append(pt); # ifdef DEBUGTets Info << "Added tet " << (tets_.size()-1) << " is " << tets_[tets_.size()-1] << endl; # endif - } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreePointsAndAddressing.C b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreePointsAndAddressing.C index a3d4f31ab9174986cb9dd6dd770b646d121ba91e..080cca764fb6d786175c093639aca192c9ae0aaa 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreePointsAndAddressing.C +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreePointsAndAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,266 +36,268 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void tetCreatorOctree::selectElements() { - const List<direction>& boxType = octreeCheck_.boxType(); - const meshOctree& octree = octreeCheck_.octree(); - const boundBox& rootBox = octree.rootBox(); - - //- store nodeLabels first - const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); - tetPoints_.setSize(octreeCheck_.numberOfNodes()); - - forAll(nodeLabels, leafI) - if( nodeLabels.sizeOfRow(leafI) != 0 ) - { - const meshOctreeCubeBasic& oc = octree.returnLeaf(leafI); - FixedList<point, 8> lv; - oc.vertices(rootBox, lv); - - forAll(lv, vI) - tetPoints_[nodeLabels(leafI, vI)] = lv[vI]; - } - - //- create cubeLabel list - if( !cubeLabelPtr_ ) - cubeLabelPtr_ = new labelList(); - labelList& cubeLabel = *cubeLabelPtr_; - cubeLabel.setSize(octree.numberOfLeaves()); - cubeLabel = -1; - - forAll(boxType, leafI) - if( boxType[leafI] & meshOctreeAddressing::MESHCELL ) - { - const meshOctreeCubeBasic& oc = octree.returnLeaf(leafI); - cubeLabel[leafI] = tetPoints_.size(); - tetPoints_.append(oc.centre(rootBox)); - } + const List<direction>& boxType = octreeCheck_.boxType(); + const meshOctree& octree = octreeCheck_.octree(); + const boundBox& rootBox = octree.rootBox(); + + //- store nodeLabels first + const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); + tetPoints_.setSize(octreeCheck_.numberOfNodes()); + + forAll(nodeLabels, leafI) + if( nodeLabels.sizeOfRow(leafI) != 0 ) + { + const meshOctreeCubeBasic& oc = octree.returnLeaf(leafI); + FixedList<point, 8> lv; + oc.vertices(rootBox, lv); + + forAll(lv, vI) + tetPoints_[nodeLabels(leafI, vI)] = lv[vI]; + } + + //- create cubeLabel list + if( !cubeLabelPtr_ ) + cubeLabelPtr_ = new labelList(); + labelList& cubeLabel = *cubeLabelPtr_; + cubeLabel.setSize(octree.numberOfLeaves()); + cubeLabel = -1; + + forAll(boxType, leafI) + if( boxType[leafI] & meshOctreeAddressing::MESHCELL ) + { + const meshOctreeCubeBasic& oc = octree.returnLeaf(leafI); + cubeLabel[leafI] = tetPoints_.size(); + tetPoints_.append(oc.centre(rootBox)); + } } void tetCreatorOctree::createPointsAndAddressing() { - selectElements(); - - const meshOctree& octree = octreeCheck_.octree(); - const boundBox& rootBox = octree.rootBox(); - const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); - - if( !subNodeLabelsPtr_ ) - subNodeLabelsPtr_ = new VRWGraph(octree.numberOfLeaves()); - VRWGraph& subNodeLabels = *subNodeLabelsPtr_; - - //- store nodeLabels - direction maxLevel(0); + selectElements(); + + const meshOctree& octree = octreeCheck_.octree(); + const boundBox& rootBox = octree.rootBox(); + const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); + + if( !subNodeLabelsPtr_ ) + subNodeLabelsPtr_ = new VRWGraph(octree.numberOfLeaves()); + VRWGraph& subNodeLabels = *subNodeLabelsPtr_; + + //- store nodeLabels + direction maxLevel(0); forAll(nodeLabels, leafI) if( octree.returnLeaf(leafI).level() > maxLevel ) maxLevel = octree.returnLeaf(leafI).level(); sortedLeaves_.setSize(maxLevel+1); - forAll(sortedLeaves_, levelI) - sortedLeaves_[levelI].clear(); - + forAll(sortedLeaves_, levelI) + sortedLeaves_[levelI].clear(); + forAll(nodeLabels, leafI) { const meshOctreeCubeBasic& oc = octree.returnLeaf(leafI); sortedLeaves_[oc.level()].append(leafI); } - //- create subNodeLabels - const FRWGraph<label, 8>& pointLeaves = octreeCheck_.nodeLeaves(); - - forAll(pointLeaves, pointI) - { - bool validLeaf[8]; - direction levelI(0); - for(label i=0;i<8;++i) - { - const label pointLeafI = pointLeaves(pointI, i); - - if( pointLeafI == -1 ) - { - validLeaf[i] = false; - } - else - { - validLeaf[i] = true; - for(label j=i+1;j<8;++j) - if( pointLeafI == pointLeaves(pointI, j) ) - { - validLeaf[i] = false; - validLeaf[j] = false; - } - - const direction level = - octree.returnLeaf(pointLeafI).level(); - - if( level > levelI ) - levelI = level; - } - } - - for(label plI=0;plI<8;++plI) - if( validLeaf[plI] ) - { - const label pointLeafI = pointLeaves(pointI, plI); - - const meshOctreeCubeBasic& lc = - octree.returnLeaf(pointLeafI); - - if( lc.level() < levelI ) - { - if( subNodeLabels.sizeOfRow(pointLeafI) != 8 ) - { - subNodeLabels.setRowSize(pointLeafI, 8); - forAllRow(subNodeLabels, pointLeafI, k) - subNodeLabels(pointLeafI, k) = -1; - } - - subNodeLabels(pointLeafI, (7-plI)) = tetPoints_.size(); - FixedList<point, 8> lv; - lc.vertices(rootBox, lv); - - tetPoints_.append - ( - 0.5 * (lv[7-plI] + lc.centre(rootBox)) - ); - } - } - } - - createFaceCentreLabels(); - - # ifdef DEBUGTets - forAll(nodeLabels, leafI) - { - forAllRow(nodeLabels, leafI, nlI) - if( leafI != pointLeaves(nodeLabels(leafI, nlI), (7-nlI)) ) - FatalError << "Shit" << abort(FatalError); - } - # endif + //- create subNodeLabels + const FRWGraph<label, 8>& pointLeaves = octreeCheck_.nodeLeaves(); + + forAll(pointLeaves, pointI) + { + bool validLeaf[8]; + direction levelI(0); + for(label i=0;i<8;++i) + { + const label pointLeafI = pointLeaves(pointI, i); + + if( pointLeafI == -1 ) + { + validLeaf[i] = false; + } + else + { + validLeaf[i] = true; + for(label j=i+1;j<8;++j) + if( pointLeafI == pointLeaves(pointI, j) ) + { + validLeaf[i] = false; + validLeaf[j] = false; + } + + const direction level = + octree.returnLeaf(pointLeafI).level(); + + if( level > levelI ) + levelI = level; + } + } + + for(label plI=0;plI<8;++plI) + if( validLeaf[plI] ) + { + const label pointLeafI = pointLeaves(pointI, plI); + + const meshOctreeCubeBasic& lc = + octree.returnLeaf(pointLeafI); + + if( lc.level() < levelI ) + { + if( subNodeLabels.sizeOfRow(pointLeafI) != 8 ) + { + subNodeLabels.setRowSize(pointLeafI, 8); + forAllRow(subNodeLabels, pointLeafI, k) + subNodeLabels(pointLeafI, k) = -1; + } + + subNodeLabels(pointLeafI, (7-plI)) = tetPoints_.size(); + FixedList<point, 8> lv; + lc.vertices(rootBox, lv); + + tetPoints_.append + ( + 0.5 * (lv[7-plI] + lc.centre(rootBox)) + ); + } + } + } + + createFaceCentreLabels(); + + # ifdef DEBUGTets + forAll(nodeLabels, leafI) + { + forAllRow(nodeLabels, leafI, nlI) + if( leafI != pointLeaves(nodeLabels(leafI, nlI), (7-nlI)) ) + FatalError << "Shit" << abort(FatalError); + } + # endif } void tetCreatorOctree::createFaceCentreLabels() { - Info << "Creating face centre labels " << endl; - const labelList& cubeLabel = *cubeLabelPtr_; - const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); - const FRWGraph<label, 8>& pointLeaves = octreeCheck_.nodeLeaves(); - const meshOctree& octree = octreeCheck_.octree(); - - - # ifdef DEBUGTets - Info << "Node labels " << nodeLabels << endl; - # endif - - List<direction> nodeLevel(pointLeaves.size(), direction(0)); - forAll(nodeLabels, leafI) - { - const direction level = octree.returnLeaf(leafI).level(); - - forAllRow(nodeLabels, leafI, nlI) - { - const label nLabel = nodeLabels(leafI, nlI); - # ifdef DEBUGTets - Info << "Node label[" << leafI << "][" << nlI << "] " - << nLabel << endl; - # endif - - if( nodeLevel[nLabel] < level ) - nodeLevel[nLabel] = level; - } - } - - if( !faceCentreLabelPtr_ ) - faceCentreLabelPtr_ = new VRWGraph(cubeLabel.size()); - VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; - - forAll(cubeLabel, cubeI) - if( cubeLabel[cubeI] != -1 ) - { - const direction level = octree.returnLeaf(cubeI).level(); - - for(label i=0;i<6;++i) - { - if( - (faceCentreLabel.sizeOfRow(cubeI) != 0) && - (faceCentreLabel(cubeI, i) != -1) - ) - continue; - - const FixedList<label, 4> faceNodes = - meshOctreeCubeCoordinates::faceNodes_[i]; - - label highLevelNode(-1); - for(label j=0;j<4;++j) - if( nodeLevel[nodeLabels(cubeI, faceNodes[j])] > level ) - { - highLevelNode = j; - break; - } - - if( highLevelNode == -1 ) - continue; - - DynList<label> neighbours(4); - octree.findNeighboursInDirection(cubeI, i, neighbours); - - if( (neighbours.size() != 1) || (neighbours[0] == -1) ) - continue; - - if( faceCentreLabel.sizeOfRow(cubeI) == 0 ) - { - faceCentreLabel.setRowSize(cubeI, 6); - forAllRow(faceCentreLabel, cubeI, colI) - faceCentreLabel(cubeI, colI) = -1; - } - const label cNei = neighbours[0]; - if( faceCentreLabel.sizeOfRow(cNei) == 0 ) - { - faceCentreLabel.setRowSize(cNei, 6); - forAllRow(faceCentreLabel, cNei, colI) - faceCentreLabel(cNei, colI) = -1; - } - - faceCentreLabel(cubeI, i) = tetPoints_.size(); - switch( i ) - { - case 0: - { - faceCentreLabel(cNei, 1) = tetPoints_.size(); - } break; - case 1: - { - faceCentreLabel(cNei, 0) = tetPoints_.size(); - } break; - case 2: - { - faceCentreLabel(cNei, 3) = tetPoints_.size(); - } break; - case 3: - { - faceCentreLabel(cNei, 2) = tetPoints_.size(); - } break; - case 4: - { - faceCentreLabel(cNei, 5) = tetPoints_.size(); - } break; - case 5: - { - faceCentreLabel(cNei, 4) = tetPoints_.size(); - } break; - }; - - point p(vector::zero); - for(label j=0;j<4;++j) - p += tetPoints_[nodeLabels(cubeI, faceNodes[j])]; - p /= 4; - tetPoints_.append(p); - } - } + Info << "Creating face centre labels " << endl; + const labelList& cubeLabel = *cubeLabelPtr_; + const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); + const FRWGraph<label, 8>& pointLeaves = octreeCheck_.nodeLeaves(); + const meshOctree& octree = octreeCheck_.octree(); + + + # ifdef DEBUGTets + Info << "Node labels " << nodeLabels << endl; + # endif + + List<direction> nodeLevel(pointLeaves.size(), direction(0)); + forAll(nodeLabels, leafI) + { + const direction level = octree.returnLeaf(leafI).level(); + + forAllRow(nodeLabels, leafI, nlI) + { + const label nLabel = nodeLabels(leafI, nlI); + # ifdef DEBUGTets + Info << "Node label[" << leafI << "][" << nlI << "] " + << nLabel << endl; + # endif + + if( nodeLevel[nLabel] < level ) + nodeLevel[nLabel] = level; + } + } + + if( !faceCentreLabelPtr_ ) + faceCentreLabelPtr_ = new VRWGraph(cubeLabel.size()); + VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; + + forAll(cubeLabel, cubeI) + if( cubeLabel[cubeI] != -1 ) + { + const direction level = octree.returnLeaf(cubeI).level(); + + for(label i=0;i<6;++i) + { + if( + (faceCentreLabel.sizeOfRow(cubeI) != 0) && + (faceCentreLabel(cubeI, i) != -1) + ) + continue; + + FixedList<label, 4> faceNodes; + forAll(faceNodes, fnI) + faceNodes[fnI] = + meshOctreeCubeCoordinates::faceNodes_[i][fnI]; + + label highLevelNode(-1); + for(label j=0;j<4;++j) + if( nodeLevel[nodeLabels(cubeI, faceNodes[j])] > level ) + { + highLevelNode = j; + break; + } + + if( highLevelNode == -1 ) + continue; + + DynList<label> neighbours; + octree.findNeighboursInDirection(cubeI, i, neighbours); + + if( (neighbours.size() != 1) || (neighbours[0] == -1) ) + continue; + + if( faceCentreLabel.sizeOfRow(cubeI) == 0 ) + { + faceCentreLabel.setRowSize(cubeI, 6); + forAllRow(faceCentreLabel, cubeI, colI) + faceCentreLabel(cubeI, colI) = -1; + } + const label cNei = neighbours[0]; + if( faceCentreLabel.sizeOfRow(cNei) == 0 ) + { + faceCentreLabel.setRowSize(cNei, 6); + forAllRow(faceCentreLabel, cNei, colI) + faceCentreLabel(cNei, colI) = -1; + } + + faceCentreLabel(cubeI, i) = tetPoints_.size(); + switch( i ) + { + case 0: + { + faceCentreLabel(cNei, 1) = tetPoints_.size(); + } break; + case 1: + { + faceCentreLabel(cNei, 0) = tetPoints_.size(); + } break; + case 2: + { + faceCentreLabel(cNei, 3) = tetPoints_.size(); + } break; + case 3: + { + faceCentreLabel(cNei, 2) = tetPoints_.size(); + } break; + case 4: + { + faceCentreLabel(cNei, 5) = tetPoints_.size(); + } break; + case 5: + { + faceCentreLabel(cNei, 4) = tetPoints_.size(); + } break; + }; + + point p(vector::zero); + for(label j=0;j<4;++j) + p += tetPoints_[nodeLabels(cubeI, faceNodes[j])]; + p /= 4; + tetPoints_.append(p); + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundEdges.C b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundEdges.C index 1836b3f9ae6203187ed627fc076b4f22f98b5f1b..f1b8d1b67ae449eace02a0d137d16bea3f16f633 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundEdges.C +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,180 +35,180 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void tetCreatorOctree::createTetsAroundEdges() { - Info << "Creating tets around edges" << endl; - - const labelList& cubeLabel = *cubeLabelPtr_; - const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); + Info << "Creating tets around edges" << endl; + + const labelList& cubeLabel = *cubeLabelPtr_; + const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); const FRWGraph<label, 8>& pLeaves = octreeCheck_.nodeLeaves(); - const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; - const VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; - const meshOctree& octree = octreeCheck_.octree(); + const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; + const VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; + const meshOctree& octree = octreeCheck_.octree(); const FixedList<FixedList<meshOctreeCubeCoordinates, 8>, 8>& vlPos = octree.positionsOfLeavesAtNodes(); - + //- find maximum refinement level of octree leaves attached to each vertex - List<direction> nodeLevel(octreeCheck_.numberOfNodes()); - - forAll(pLeaves, nodeI) - { + List<direction> nodeLevel(octreeCheck_.numberOfNodes()); + + forAll(pLeaves, nodeI) + { direction level(0); - - for(label plI=0;plI<8;++plI) - { + + for(label plI=0;plI<8;++plI) + { const label leafI = pLeaves(nodeI, plI); - - if( leafI < 0 ) + + if( leafI < 0 ) continue; - - level = Foam::max(level, octree.returnLeaf(leafI).level()); - } - + + level = Foam::max(level, octree.returnLeaf(leafI).level()); + } + nodeLevel[nodeI] = level; - } - + } + //- start creating tets around edges which have both vertices at the same //- refinement level which is equal to the max refinement level of boxes //- incident to such edges - forAllReverse(sortedLeaves_, levelI) - { - const labelListPMG& curLevelLeaves = sortedLeaves_[levelI]; - - forAll(curLevelLeaves, leafI) - { - const label curLeaf = curLevelLeaves[leafI]; - - if( cubeLabel[curLeaf] == -1 ) - continue; - + forAllReverse(sortedLeaves_, levelI) + { + const labelLongList& curLevelLeaves = sortedLeaves_[levelI]; + + forAll(curLevelLeaves, leafI) + { + const label curLeaf = curLevelLeaves[leafI]; + + if( cubeLabel[curLeaf] == -1 ) + continue; + const meshOctreeCubeCoordinates& cc = octree.returnLeaf(curLeaf).coordinates(); - - # ifdef DEBUGTets - Info << "Search cube " << curLeaf << " has coordinates " - << octree.returnLeaf(curLeaf).coordinates() << endl; - Info << "Node labels for cube are " << nodeLabels[curLeaf] << endl; - # endif + + # ifdef DEBUGTets + Info << "Search cube " << curLeaf << " has coordinates " + << octree.returnLeaf(curLeaf).coordinates() << endl; + Info << "Node labels for cube are " << nodeLabels[curLeaf] << endl; + # endif //- start checking edges - for(label eI=0;eI<12;++eI) - { + for(label eI=0;eI<12;++eI) + { const label startNode = meshOctreeCubeCoordinates::edgeNodes_[eI][0]; - - const label start = nodeLabels(curLeaf, startNode); - const label end = - nodeLabels - ( - curLeaf, - meshOctreeCubeCoordinates::edgeNodes_[eI][1] - ); - - # ifdef DEBUGTets - Info << "Creating tets around edge " << eI << endl; - Info << "Edge nodes are " << start << " and " << end << endl; + + const label start = nodeLabels(curLeaf, startNode); + const label end = + nodeLabels + ( + curLeaf, + meshOctreeCubeCoordinates::edgeNodes_[eI][1] + ); + + # ifdef DEBUGTets + Info << "Creating tets around edge " << eI << endl; + Info << "Edge nodes are " << start << " and " << end << endl; Info << "Coordinates start " << tetPoints_[start] << " end " << tetPoints_[end] << endl; - # endif - - bool create(true); - - if( - (nodeLevel[start] == levelI) && - (nodeLevel[end] == levelI) + # endif + + bool create(true); + + if( + (nodeLevel[start] == direction(levelI)) && + (nodeLevel[end] == direction(levelI)) ) - { + { //- edge has both vertices at the same refinement level //- as the current leaf - FixedList<label, 4> edgeCubes; + FixedList<label, 4> edgeCubes; const label fI = 2*(eI/4)+1; - + const label* fNodes = meshOctreeCubeCoordinates::faceNodes_[fI]; - + //- store octree leaves at this edge //- they are all adjacent to the start point for(label i=0;i<4;++i) edgeCubes[i] = pLeaves(start, fNodes[i]); - + # ifdef DEBUGTets forAll(edgeCubes, i) { Info << "Cube " << i << " is " << edgeCubes[i] << endl; - + if( edgeCubes[i] < 0 ) continue; - + Info << "Cubes has node labels " << nodeLabels[edgeCubes[i]] << endl; } # endif - + DynList<label> centreNodes; - - forAll(edgeCubes, i) - { - const label cLabel = edgeCubes[i]; - - if( (cLabel == -1) || (cubeLabel[cLabel] == -1) ) - { - centreNodes.append(-1); - continue; - } - - const meshOctreeCubeCoordinates& oc = - octree.returnLeaf(cLabel).coordinates(); - - # ifdef DEBUGTets - Info << "Edge cube " << i << " is " << oc << endl; - Info << "Node labels "; - forAllRow(nodeLabels, cLabel, k) - Info << nodeLabels(cLabel, k) << " "; - Info << endl; - # endif - - if( oc.level() == levelI ) - { - if( cLabel < curLeaf ) - { - create = false; - break; - } - - # ifdef DEBUGTets - Info << "Adding centre label " << cubeLabel[cLabel] - << endl; - # endif - - centreNodes.append(cubeLabel[cLabel]); - + + forAll(edgeCubes, i) + { + const label cLabel = edgeCubes[i]; + + if( (cLabel == -1) || (cubeLabel[cLabel] == -1) ) + { + centreNodes.append(-1); + continue; + } + + const meshOctreeCubeCoordinates& oc = + octree.returnLeaf(cLabel).coordinates(); + + # ifdef DEBUGTets + Info << "Edge cube " << i << " is " << oc << endl; + Info << "Node labels "; + forAllRow(nodeLabels, cLabel, k) + Info << nodeLabels(cLabel, k) << " "; + Info << endl; + # endif + + if( oc.level() == direction(levelI) ) + { + if( cLabel < curLeaf ) + { + create = false; + break; + } + + # ifdef DEBUGTets + Info << "Adding centre label " << cubeLabel[cLabel] + << endl; + # endif + + centreNodes.append(cubeLabel[cLabel]); + //- adding face centre labels - if( faceCentreLabel.sizeOfRow(cLabel) != 0 ) - { + if( faceCentreLabel.sizeOfRow(cLabel) != 0 ) + { const label helpFace = eI/4; - + const label fcl = faceCentreLabel ( cLabel, faceCentreHelper_[helpFace][i] ); - + if( fcl != -1 ) centreNodes.append(fcl); - } - - # ifdef DEBUGTets - Info << "Centre nodes after cube " << i - << " are " << centreNodes << endl; - # endif - } - else if( oc.level() < levelI ) - { + } + + # ifdef DEBUGTets + Info << "Centre nodes after cube " << i + << " are " << centreNodes << endl; + # endif + } + else if( oc.level() < direction(levelI) ) + { # ifdef DEBUGTets Info << "Edge cube " << cLabel << endl; Info << "cc " << cc << endl; @@ -217,18 +216,18 @@ void tetCreatorOctree::createTetsAroundEdges() Info << "Adding pos " << vlPos[startNode][fNodes[i]] << endl; # endif - + const meshOctreeCubeCoordinates sc ( cc + vlPos[startNode][fNodes[i]] ); - + # ifdef DEBUGTets Info << "sc " << sc << endl; # endif - - label pos(-1); - + + label pos(-1); + for(label j=0;j<8;j++) { if( sc == oc.refineForPosition(j) ) @@ -237,7 +236,7 @@ void tetCreatorOctree::createTetsAroundEdges() break; } } - + if( pos == -1 ) FatalErrorIn ( @@ -245,35 +244,35 @@ void tetCreatorOctree::createTetsAroundEdges() "createTetsAroundEdges()" ) << "Cannot find cube position" << abort(FatalError); - - # ifdef DEBUGTets - Info << "Pos " << pos << endl; - # endif - + + # ifdef DEBUGTets + Info << "Pos " << pos << endl; + # endif + centreNodes.append(subNodeLabels(cLabel, pos)); - - # ifdef DEBUGTets - Info << "Centre node " << i << " is " - << subNodeLabels(cLabel, pos) + + # ifdef DEBUGTets + Info << "Centre node " << i << " is " + << subNodeLabels(cLabel, pos) << " coordinates " << tetPoints_[subNodeLabels(cLabel, pos)] << endl; - # endif - } - } - - //- create tets around this edge - if( create ) - { - const label nCentres = centreNodes.size(); - - forAll(centreNodes, i) - { - if( centreNodes[i] == -1 ) - continue; - if( centreNodes[(i+1)%nCentres] == -1 ) - continue; - + # endif + } + } + + //- create tets around this edge + if( create ) + { + const label nCentres = centreNodes.size(); + + forAll(centreNodes, i) + { + if( centreNodes[i] == -1 ) + continue; + if( centreNodes[(i+1)%nCentres] == -1 ) + continue; + partTet tet ( centreNodes[i], @@ -281,20 +280,20 @@ void tetCreatorOctree::createTetsAroundEdges() start, end ); - - tets_.append(tet); - - # ifdef DEBUGTets - Info << "Last added tet " - << tets_.size()-1 <<" is " - << tets_[tets_.size()-1] << endl; - # endif - } - } - } - } - } - } + + tets_.append(tet); + + # ifdef DEBUGTets + Info << "Last added tet " + << tets_.size()-1 <<" is " + << tets_[tets_.size()-1] << endl; + # endif + } + } + } + } + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundSplitEdges.C b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundSplitEdges.C index 74f7363aa6052a1938b6bc364143e8e85b983e48..9fa29d392b257d7c4be4bf41480c8d01678b5d81 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundSplitEdges.C +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsAroundSplitEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,354 +35,356 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void tetCreatorOctree::createTetsAroundSplitEdges() { - Info << "Creating tets around split edges " << endl; - - const labelList& cubeLabel = *cubeLabelPtr_; - const meshOctree& octree = octreeCheck_.octree(); - const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); + Info << "Creating tets around split edges " << endl; + + const labelList& cubeLabel = *cubeLabelPtr_; + const meshOctree& octree = octreeCheck_.octree(); + const VRWGraph& nodeLabels = octreeCheck_.nodeLabels(); const FRWGraph<label, 8>& pLeaves = octreeCheck_.nodeLeaves(); - const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; - const VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; - - # ifdef DEBUGTets - Info << "Number of octree nodes " << octreeCheck_.numberOfNodes() << endl; - # endif - + const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; + const VRWGraph& faceCentreLabel = *faceCentreLabelPtr_; + + # ifdef DEBUGTets + Info << "Number of octree nodes " << octreeCheck_.numberOfNodes() << endl; + # endif + //- find maximum refinement level of octree leaves attached to each vertex - List<direction> nodeLevel(octreeCheck_.numberOfNodes()); - - forAll(pLeaves, nodeI) - { + List<direction> nodeLevel(octreeCheck_.numberOfNodes()); + + forAll(pLeaves, nodeI) + { direction level(0); - - for(label plI=0;plI<8;++plI) - { + + for(label plI=0;plI<8;++plI) + { const label leafI = pLeaves(nodeI, plI); - - if( leafI < 0 ) + + if( leafI < 0 ) continue; - - level = Foam::max(level, octree.returnLeaf(leafI).level()); - } - + + level = Foam::max(level, octree.returnLeaf(leafI).level()); + } + nodeLevel[nodeI] = level; - } - - //- start creating tets around split edges - label helpNodes[2][8]; - label faceCentres[4]; - - forAllReverse(sortedLeaves_, levelI) - { - const labelListPMG& curLevelLeaves = sortedLeaves_[levelI]; - - forAll(curLevelLeaves, leafI) - { - const label curLabel = curLevelLeaves[leafI]; - - if( cubeLabel[curLabel] == -1 ) - continue; - + } + + //- start creating tets around split edges + label helpNodes[2][8]; + label faceCentres[4]; + + forAllReverse(sortedLeaves_, levelI) + { + const labelLongList& curLevelLeaves = sortedLeaves_[levelI]; + + const direction level = direction(levelI); + + forAll(curLevelLeaves, leafI) + { + const label curLabel = curLevelLeaves[leafI]; + + if( cubeLabel[curLabel] == -1 ) + continue; + //- start checking edges - for(label eI=0;eI<12;++eI) - { - const label start = - nodeLabels - ( - curLabel, - meshOctreeCubeCoordinates::edgeNodes_[eI][0] - ); - const label end = - nodeLabels - ( - curLabel, - meshOctreeCubeCoordinates::edgeNodes_[eI][1] - ); - - if( (nodeLevel[start] == levelI) && (nodeLevel[end] == levelI) ) - continue; - + for(label eI=0;eI<12;++eI) + { + const label start = + nodeLabels + ( + curLabel, + meshOctreeCubeCoordinates::edgeNodes_[eI][0] + ); + const label end = + nodeLabels + ( + curLabel, + meshOctreeCubeCoordinates::edgeNodes_[eI][1] + ); + + if( (nodeLevel[start] == level) && (nodeLevel[end] == level) ) + continue; + //- the edge has at least one vertex at different ref level - bool create(true); - - FixedList<label, 4> edgeCubes; + bool create(true); + + FixedList<label, 4> edgeCubes; const label fI = 2*(eI/4)+1; - + const label* fNodes = meshOctreeCubeCoordinates::faceNodes_[fI]; - + //- store octree leaves at this edge //- they are all adjacent to the start point for(label i=0;i<4;++i) edgeCubes[i] = pLeaves(start, fNodes[i]); - - # ifdef DEBUGTets - Info << "Cube " << curLabel << " has nodes "; - forAllRow(nodeLabels, curLabel, i) - Info << nodeLabels(curLabel, i) << " "; - Info << endl; - Info << "Creating tets around edge " << eI << endl; - Info << "Edge nodes are " << start << " and " << end << endl; - Info << "Edge cubes " << edgeCubes << endl; - # endif - - forAll(edgeCubes, i) - { - const label cLabel = edgeCubes[i]; - - if( - (cLabel == -1) || - (cLabel < curLabel) || - (octree.returnLeaf(cLabel).level() != levelI) - ) - { - create = false; - break; - } - - # ifdef DEBUGTets - Info << "Edge cube " << i << " is " << cLabel << endl; - # endif - - for(label j=0;j<8;++j) - { - if( nodeLabels(cLabel,j) == start ) - { - if( subNodeLabels.sizeOfRow(cLabel) != 0 ) - { - helpNodes[0][i] = subNodeLabels(cLabel,j); - } - else - { - helpNodes[0][i] = -1; - } - - helpNodes[0][i+4] = cubeLabel[cLabel]; - } - - if( nodeLabels(cLabel, j) == end ) - { - if( subNodeLabels.sizeOfRow(cLabel) != 0 ) - { - helpNodes[1][i+4] = subNodeLabels(cLabel,j); - } - else - { - helpNodes[1][i+4] = -1; - } - - helpNodes[1][i] = cubeLabel[cLabel]; - } - } - - if( faceCentreLabel.sizeOfRow(cLabel) != 0 ) - { + + # ifdef DEBUGTets + Info << "Cube " << curLabel << " has nodes "; + forAllRow(nodeLabels, curLabel, i) + Info << nodeLabels(curLabel, i) << " "; + Info << endl; + Info << "Creating tets around edge " << eI << endl; + Info << "Edge nodes are " << start << " and " << end << endl; + Info << "Edge cubes " << edgeCubes << endl; + # endif + + forAll(edgeCubes, i) + { + const label cLabel = edgeCubes[i]; + + if( + (cLabel == -1) || + (cLabel < curLabel) || + (octree.returnLeaf(cLabel).level() != level) + ) + { + create = false; + break; + } + + # ifdef DEBUGTets + Info << "Edge cube " << i << " is " << cLabel << endl; + # endif + + for(label j=0;j<8;++j) + { + if( nodeLabels(cLabel,j) == start ) + { + if( subNodeLabels.sizeOfRow(cLabel) != 0 ) + { + helpNodes[0][i] = subNodeLabels(cLabel,j); + } + else + { + helpNodes[0][i] = -1; + } + + helpNodes[0][i+4] = cubeLabel[cLabel]; + } + + if( nodeLabels(cLabel, j) == end ) + { + if( subNodeLabels.sizeOfRow(cLabel) != 0 ) + { + helpNodes[1][i+4] = subNodeLabels(cLabel,j); + } + else + { + helpNodes[1][i+4] = -1; + } + + helpNodes[1][i] = cubeLabel[cLabel]; + } + } + + if( faceCentreLabel.sizeOfRow(cLabel) != 0 ) + { const label helpFace = eI/4; - + faceCentres[i] = faceCentreLabel ( cLabel, faceCentreHelper_[helpFace][i] ); - } - else - { - faceCentres[i] = -1; - } - } - - if( !create ) - continue; - - # ifdef DEBUGTets - for(label n=0;n<4;++n) - { - Info << "Face centre " << n << " " - << faceCentres[n] << endl; - Info << "Hex 0 " << helpNodes[0][n] << " and " - << helpNodes[0][n+4] << endl; - Info << "Hex 1 " << helpNodes[1][n] << " and " - << helpNodes[1][n+4] << endl; - } - # endif - - if( nodeLevel[start] > levelI ) - { - for(label k=0;k<4;++k) - { - //- add 4 tets - checkAndAppendTet - ( - partTet - ( - start, - helpNodes[0][k], - helpNodes[0][(k+1)%4], - tetPoints_.size() - ) - ); - - //- 2. tet - checkAndAppendTet - ( - partTet - ( - tetPoints_.size(), - helpNodes[0][k], - helpNodes[0][(k+1)%4], - faceCentres[k] - ) - ); - - //- 3. tet - checkAndAppendTet - ( - partTet - ( - faceCentres[k], - helpNodes[0][k], - helpNodes[0][k+4], - tetPoints_.size() - ) - ); - - //- 4. tet - checkAndAppendTet - ( - partTet - ( - faceCentres[(k+3)%4], - helpNodes[0][k+4], - helpNodes[0][k], - tetPoints_.size() - ) - ); - } - } - else - { - for(label k=0;k<4;++k) - { - checkAndAppendTet - ( - partTet - ( - faceCentres[(k+3)%4], - helpNodes[0][k+4], - start, - tetPoints_.size() - ) - ); - - checkAndAppendTet - ( - partTet - ( - faceCentres[k], - start, - helpNodes[0][k+4], - tetPoints_.size() - ) - ); - } - } - - if( nodeLevel[end] > levelI ) - { - for(label k=0;k<4;++k) - { - //- add 4 tets - checkAndAppendTet - ( - partTet - ( - tetPoints_.size(), - helpNodes[1][k+4], - helpNodes[1][((k+1)%4)+4], - end - ) - ); - - // 2. tet - checkAndAppendTet - ( - partTet - ( - faceCentres[k], - helpNodes[1][k+4], - helpNodes[1][((k+1)%4)+4], - tetPoints_.size() - ) - ); - - //- 3. tet - checkAndAppendTet - ( - partTet - ( - tetPoints_.size(), - helpNodes[1][k], - faceCentres[k], - helpNodes[1][k+4] - ) - ); - - //- 4. tet - checkAndAppendTet - ( - partTet - ( - faceCentres[(k+3)%4], - helpNodes[1][k], - tetPoints_.size(), - helpNodes[1][k+4] - ) - ); - } - } - else - { - for(label k=0;k<4;++k) - { - checkAndAppendTet - ( - partTet - ( - faceCentres[(k+3)%4], - helpNodes[1][k], - tetPoints_.size(), - end - ) - ); - - checkAndAppendTet - ( - partTet - ( - helpNodes[1][k], - faceCentres[k], - tetPoints_.size(), - end - ) - ); - } - } - + } + else + { + faceCentres[i] = -1; + } + } + + if( !create ) + continue; + + # ifdef DEBUGTets + for(label n=0;n<4;++n) + { + Info << "Face centre " << n << " " + << faceCentres[n] << endl; + Info << "Hex 0 " << helpNodes[0][n] << " and " + << helpNodes[0][n+4] << endl; + Info << "Hex 1 " << helpNodes[1][n] << " and " + << helpNodes[1][n+4] << endl; + } + # endif + + if( nodeLevel[start] > level ) + { + for(label k=0;k<4;++k) + { + //- add 4 tets + checkAndAppendTet + ( + partTet + ( + start, + helpNodes[0][k], + helpNodes[0][(k+1)%4], + tetPoints_.size() + ) + ); + + //- 2. tet + checkAndAppendTet + ( + partTet + ( + tetPoints_.size(), + helpNodes[0][k], + helpNodes[0][(k+1)%4], + faceCentres[k] + ) + ); + + //- 3. tet + checkAndAppendTet + ( + partTet + ( + faceCentres[k], + helpNodes[0][k], + helpNodes[0][k+4], + tetPoints_.size() + ) + ); + + //- 4. tet + checkAndAppendTet + ( + partTet + ( + faceCentres[(k+3)%4], + helpNodes[0][k+4], + helpNodes[0][k], + tetPoints_.size() + ) + ); + } + } + else + { + for(label k=0;k<4;++k) + { + checkAndAppendTet + ( + partTet + ( + faceCentres[(k+3)%4], + helpNodes[0][k+4], + start, + tetPoints_.size() + ) + ); + + checkAndAppendTet + ( + partTet + ( + faceCentres[k], + start, + helpNodes[0][k+4], + tetPoints_.size() + ) + ); + } + } + + if( nodeLevel[end] > level ) + { + for(label k=0;k<4;++k) + { + //- add 4 tets + checkAndAppendTet + ( + partTet + ( + tetPoints_.size(), + helpNodes[1][k+4], + helpNodes[1][((k+1)%4)+4], + end + ) + ); + + // 2. tet + checkAndAppendTet + ( + partTet + ( + faceCentres[k], + helpNodes[1][k+4], + helpNodes[1][((k+1)%4)+4], + tetPoints_.size() + ) + ); + + //- 3. tet + checkAndAppendTet + ( + partTet + ( + tetPoints_.size(), + helpNodes[1][k], + faceCentres[k], + helpNodes[1][k+4] + ) + ); + + //- 4. tet + checkAndAppendTet + ( + partTet + ( + faceCentres[(k+3)%4], + helpNodes[1][k], + tetPoints_.size(), + helpNodes[1][k+4] + ) + ); + } + } + else + { + for(label k=0;k<4;++k) + { + checkAndAppendTet + ( + partTet + ( + faceCentres[(k+3)%4], + helpNodes[1][k], + tetPoints_.size(), + end + ) + ); + + checkAndAppendTet + ( + partTet + ( + helpNodes[1][k], + faceCentres[k], + tetPoints_.size(), + end + ) + ); + } + } + //- add the edge centre - tetPoints_.append(0.5 * (tetPoints_[start] + tetPoints_[end])); - } - } - } - - # ifdef DEBUGTets - Info << "Created tets " << tets_ << endl; - # endif + tetPoints_.append(0.5 * (tetPoints_[start] + tetPoints_[end])); + } + } + } + + # ifdef DEBUGTets + Info << "Created tets " << tets_ << endl; + # endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsFromSplitFaces.C b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsFromSplitFaces.C index 65d41d8391b172c7ef6f6f5a691f3f0be70f0e62..3b7285b8d6dd82240db9d6d537b3d27595b5efa2 100644 --- a/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsFromSplitFaces.C +++ b/meshLibrary/utilities/tetrahedra/tetCreatorOctree/tetCreatorOctreeTetsFromSplitFaces.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,54 +34,54 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void tetCreatorOctree::createTetsFromSplitFaces() { - Info << "Creating tets from split faces" << endl; + Info << "Creating tets from split faces" << endl; + + const labelList& cubeLabel = *cubeLabelPtr_; + const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; + const FRWGraph<label, 8>& pLeaves = octreeCheck_.nodeLeaves(); - const labelList& cubeLabel = *cubeLabelPtr_; - const VRWGraph& subNodeLabels = *subNodeLabelsPtr_; - const FRWGraph<label, 8>& pLeaves = octreeCheck_.nodeLeaves(); - - forAll(pLeaves, pointI) - { - for(label i=0;i<6;++i) - { + forAll(pLeaves, pointI) + { + for(label i=0;i<6;++i) + { const label* fNodes = meshOctreeCubeCoordinates::faceNodes_[i]; - const label cLabel = pLeaves(pointI, fNodes[0]); + const label cLabel = pLeaves(pointI, fNodes[0]); if( cLabel < 0 ) continue; if( cubeLabel[cLabel] < 0 ) continue; - if( - (cLabel == pLeaves(pointI, fNodes[1])) && - (cLabel == pLeaves(pointI, fNodes[2])) && - (cLabel == pLeaves(pointI, fNodes[3])) - ) - { - //- create 4 tets - for(label j=0;j<4;++j) + if( + (cLabel == pLeaves(pointI, fNodes[1])) && + (cLabel == pLeaves(pointI, fNodes[2])) && + (cLabel == pLeaves(pointI, fNodes[3])) + ) + { + //- create 4 tets + for(label j=0;j<4;++j) { - checkAndAppendTet - ( - partTet - ( - pointI, - subNodeLabels(cLabel, 7-fNodes[j]), - subNodeLabels(cLabel, 7-fNodes[(j+1)%4]), - cubeLabel[cLabel] - ) - ); + checkAndAppendTet + ( + partTet + ( + pointI, + subNodeLabels(cLabel, 7-fNodes[j]), + subNodeLabels(cLabel, 7-fNodes[(j+1)%4]), + cubeLabel[cLabel] + ) + ); } - } - } - } + } + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.C b/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.C index 33f870409b5e00bf86c922e9d852811a272ad6d4..9bb822ee739dfbadf387897fecbac6c4a20dc296 100644 --- a/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.C +++ b/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -40,14 +39,14 @@ namespace Foam // Construct from octree and mesh data tetPointsCreator::tetPointsCreator ( - tetTessellation& tessellation, + tetTessellation& tessellation, const meshOctree& octree ) : - tessellation_(tessellation), + tessellation_(tessellation), octree_(octree) { - createPoints(); + createPoints(); } // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.H b/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.H index 8029e38849aa74527bd07e28cef95aa7d1e62ee2..e503ef867898e558c9af84ba9c7b352470c42e9f 100644 --- a/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.H +++ b/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreator.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class tetPointsCreator @@ -56,25 +55,25 @@ class tetTessellation; class tetPointsCreator { // Private data - //- reference to the Delaunay tessellation - tetTessellation& tessellation_; - + //- reference to the Delaunay tessellation + tetTessellation& tessellation_; + //- reference to the octree const meshOctree& octree_; // Private member functions //- create vertices and pointLeaves addressing void createPoints(); - - // Helper functions - //- checks if the point is inside the surface - bool isPointInsideSurface(const point&) const; - - //- find out if this element has been changed already - bool isElementChanged(const label elmtI, const label nElements) const; - - //- return cell size at the given location - scalar cellSizeAtLocation(const point&) const; + + // Helper functions + //- checks if the point is inside the surface + bool isPointInsideSurface(const point&) const; + + //- find out if this element has been changed already + bool isElementChanged(const label elmtI, const label nElements) const; + + //- return cell size at the given location + scalar cellSizeAtLocation(const point&) const; // Private copy constructor //- Disallow default bitwise copy construct @@ -90,7 +89,7 @@ public: //- Construct from octree and mesh data tetPointsCreator ( - tetTessellation& tessellation, + tetTessellation& tessellation, const meshOctree& octree ); diff --git a/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreatorAddPoints.C b/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreatorAddPoints.C index 3cb78a81d844674e201e92a17eb7ef2c85c8ec69..64c84d1b5f7a5b08e3ee7ee3552294776b50f7bf 100644 --- a/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreatorAddPoints.C +++ b/meshLibrary/utilities/tetrahedra/tetPointsCreator/tetPointsCreatorAddPoints.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,88 +36,88 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void tetPointsCreator::createPoints() { - //- create initial bunch of points from centroids of the existing tets - //- repeat this until the first internal point is found - const LongList<point>& tetPoints = tessellation_.points(); - const LongList<tessellationElement>& elmts = tessellation_.elmts(); - LongList<bool> internalPoint(tetPoints.size(), false); - - bool found; - label nIter(0); - do - { - Info << "Tessellation has " << tetPoints.size() << " points" << endl; - Info << "Number of tets " << elmts.size() << endl; - found = false; - const label nPoints = tetPoints.size(); - const label nElements = elmts.size(); - for(label elmtI=0;elmtI<nElements;++elmtI) - //forAll(elmts, elmtI) - { - if( isElementChanged(elmtI, nPoints) ) - continue; - - const tessellationElement& elmt = elmts[elmtI]; - const point p = elmt.centroid(tetPoints); - - if( isPointInsideSurface(p) ) - { - tessellation_.addCentroid(elmtI); - found = true; - } - } - } while( found && (++nIter < 7) ); - - tessellation_.checkTessellation(); + //- create initial bunch of points from centroids of the existing tets + //- repeat this until the first internal point is found + const LongList<point>& tetPoints = tessellation_.points(); + const LongList<tessellationElement>& elmts = tessellation_.elmts(); + LongList<bool> internalPoint(tetPoints.size(), false); + + bool found; + label nIter(0); + do + { + Info << "Tessellation has " << tetPoints.size() << " points" << endl; + Info << "Number of tets " << elmts.size() << endl; + found = false; + const label nPoints = tetPoints.size(); + const label nElements = elmts.size(); + for(label elmtI=0;elmtI<nElements;++elmtI) + //forAll(elmts, elmtI) + { + if( isElementChanged(elmtI, nPoints) ) + continue; + + const tessellationElement& elmt = elmts[elmtI]; + const point p = elmt.centroid(tetPoints); + + if( isPointInsideSurface(p) ) + { + tessellation_.addCentroid(elmtI); + found = true; + } + } + } while( found && (++nIter < 7) ); + + tessellation_.checkTessellation(); } bool tetPointsCreator::isPointInsideSurface(const point& p) const { - const label cLabel = octree_.findLeafContainingVertex(p); - - if( cLabel == -1 ) - return false; - - if( - (octree_.returnLeaf(cLabel).cubeType() & meshOctreeCubeBasic::INSIDE) || - (octree_.returnLeaf(cLabel).cubeType() & meshOctreeCubeBasic::DATA) - ) - return true; - - return false; + const label cLabel = octree_.findLeafContainingVertex(p); + + if( cLabel == -1 ) + return false; + + if( + (octree_.returnLeaf(cLabel).cubeType() & meshOctreeCubeBasic::INSIDE) || + (octree_.returnLeaf(cLabel).cubeType() & meshOctreeCubeBasic::DATA) + ) + return true; + + return false; } bool tetPointsCreator::isElementChanged ( - const label elmtI, - const label nElements + const label elmtI, + const label nElements ) const { - if( elmtI >= nElements ) - return true; - - const tessellationElement& elmt = tessellation_.elmts()[elmtI]; - - for(direction i=0;i<DIM;++i) - if( elmt[i] >= nElements ) - return true; - - return false; + if( elmtI >= nElements ) + return true; + + const tessellationElement& elmt = tessellation_.elmts()[elmtI]; + + for(direction i=0;i<DIM;++i) + if( elmt[i] >= nElements ) + return true; + + return false; } scalar tetPointsCreator::cellSizeAtLocation(const point& p) const { - const label cLabel = octree_.findLeafContainingVertex(p); - - if( cLabel == -1 ) - return VGREAT; - - return octree_.returnLeaf(cLabel).size(octree_.rootBox()); + const label cLabel = octree_.findLeafContainingVertex(p); + + if( cLabel == -1 ) + return VGREAT; + + return octree_.returnLeaf(cLabel).size(octree_.rootBox()); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.C b/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.C index 34f6fcedb95588f9b6e2a957d2a666c83318854b..a5f777be0c5c38ce71349a8b281539dda54c04bb 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.H b/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.H index 8395bf7e2c000e6679c5f8aa399230aa5a963e95..5f85e16b3b55c1790500519e71930bc397e77c8f 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.H +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellation.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class delaunayTesselation @@ -53,13 +52,13 @@ public: // Constructors //- Construct from list of points - delaunayTessellation(const LongList<point>&); + delaunayTessellation(const LongList<point>&); - //- Construct from triangulated surface - delaunayTessellation(const triSurface& surf); + //- Construct from triangulated surface + delaunayTessellation(const triSurface& surf); - //- Construct from boundBox - delaunayTessellation(const boundBox& bb); + //- Construct from boundBox + delaunayTessellation(const boundBox& bb); // Destructor @@ -67,22 +66,22 @@ public: // Member functions - //- add point which is already in the list of points - bool addPoint(const label pI); + //- add point which is already in the list of points + bool addPoint(const label pI); - //- create a new point from the centroid of the given element - //- and add it into the tessellation - void addCentroid(const label elmtI); + //- create a new point from the centroid of the given element + //- and add it into the tessellation + void addCentroid(const label elmtI); - //- create a new point from the circumcentre of the given element - //- and add it into the tessellation - void addCircumCentre(const label elmtI); - - //- create a new point at the centre of the given edge of the element - //- and add it into the tessellation - void addEdgeCentre(const label elmtI, const direction eI); + //- create a new point from the circumcentre of the given element + //- and add it into the tessellation + void addCircumCentre(const label elmtI); + + //- create a new point at the centre of the given edge of the element + //- and add it into the tessellation + void addEdgeCentre(const label elmtI, const direction eI); - //- check if the tesselation obeys Delaunay properties + //- check if the tesselation obeys Delaunay properties void checkTessellation() const; }; diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellationFunctions.C b/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellationFunctions.C index 081734e8922690b980a76df5fe760c169b413484..f644cc5569cea2569f6e6e97fc9b1157cfa779cf 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellationFunctions.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/delaunayTessellation/delaunayTessellationFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,17 +38,17 @@ namespace Foam bool delaunayTessellation::addPoint(const label pI) { - # ifdef DEBUGTessalation - Info << "Adding point " << pI - << " with coordinates " << points_[pI] << endl; - # endif - - const point& p = points_[pI]; - + # ifdef DEBUGTessalation + Info << "Adding point " << pI + << " with coordinates " << points_[pI] << endl; + # endif + + const point& p = points_[pI]; + pointOk_ = true; nElmts_ = 0; - + const label el = findInitialElement(p); treeSearch @@ -66,121 +65,121 @@ bool delaunayTessellation::addPoint(const label pI) } makeNewElements(el, pI); - - resetInfluences(el); + + resetInfluences(el); return true; } void delaunayTessellation::addCentroid(const label elmtI) { - const label pI = points_.size(); - points_.append(elmts_[elmtI].centroid(points_)); - const point& p = points_[pI]; - - do - { - pointOk_ = true; - - nElmts_ = 0; - - treeSearch(elmtI, p); - - //- skip the point if it produces invalid tessellation - if( !pointOk_ ) - { - resetInfluences(elmtI); - continue; - } - - makeNewElements(elmtI, pI); - - resetInfluences(elmtI); - } - while( !pointOk_ ); + const label pI = points_.size(); + points_.append(elmts_[elmtI].centroid(points_)); + const point& p = points_[pI]; + + do + { + pointOk_ = true; + + nElmts_ = 0; + + treeSearch(elmtI, p); + + //- skip the point if it produces invalid tessellation + if( !pointOk_ ) + { + resetInfluences(elmtI); + continue; + } + + makeNewElements(elmtI, pI); + + resetInfluences(elmtI); + } + while( !pointOk_ ); } void delaunayTessellation::addCircumCentre(const label elmtI) { - const label pI = points_.size(); - points_.append(elmts_[elmtI].crcmCentre(points_)); - const point& p = points_[pI]; - + const label pI = points_.size(); + points_.append(elmts_[elmtI].crcmCentre(points_)); + const point& p = points_[pI]; + do - { - pointOk_ = true; - - nElmts_ = 0; - - treeSearch(elmtI, p); - - //- skip the point if it produces invalid tessellation - if( !pointOk_ ) - { - resetInfluences(elmtI); - continue; - } - - makeNewElements(elmtI, pI); - - resetInfluences(elmtI); - } - while( !pointOk_ ); + { + pointOk_ = true; + + nElmts_ = 0; + + treeSearch(elmtI, p); + + //- skip the point if it produces invalid tessellation + if( !pointOk_ ) + { + resetInfluences(elmtI); + continue; + } + + makeNewElements(elmtI, pI); + + resetInfluences(elmtI); + } + while( !pointOk_ ); } void delaunayTessellation::addEdgeCentre(const label elmtI, const direction eI) { - const label pI = points_.size(); - const edge e = elmts_[elmtI].edges()[eI]; - points_.append(0.5*(points_[e[0]]+points_[e[1]])); - const point& p = points_[pI]; - + const label pI = points_.size(); + const edge e = elmts_[elmtI].edges()[eI]; + points_.append(0.5*(points_[e[0]]+points_[e[1]])); + const point& p = points_[pI]; + do - { - Info << "Adding point " << pI << endl; - pointOk_ = true; - - nElmts_ = 0; - - treeSearch(elmtI, p); - - //- skip the point if it produces invalid tessellation - if( !pointOk_ ) - { - Warning << "Adding point " << pI << " failed" << endl; - resetInfluences(elmtI); - continue; - } - - makeNewElements(elmtI, pI); - - resetInfluences(elmtI); - } - while( !pointOk_ ); + { + Info << "Adding point " << pI << endl; + pointOk_ = true; + + nElmts_ = 0; + + treeSearch(elmtI, p); + + //- skip the point if it produces invalid tessellation + if( !pointOk_ ) + { + Warning << "Adding point " << pI << " failed" << endl; + resetInfluences(elmtI); + continue; + } + + makeNewElements(elmtI, pI); + + resetInfluences(elmtI); + } + while( !pointOk_ ); } void delaunayTessellation::checkTessellation() const { forAll(elmts_, elI) { - const tessellationElement& elmt = elmts_[elI]; - - for(direction i=0;i<DIM1;++i) - if( elmt.neighbour(i) > elI ) - { - const tessellationElement& nei = elmts_[elmt.neighbour(i)]; + const tessellationElement& elmt = elmts_[elI]; + + for(direction i=0;i<DIM1;++i) + if( elmt.neighbour(i) > elI ) + { + const tessellationElement& nei = elmts_[elmt.neighbour(i)]; if( nei.influencedBy(points_, points_[elmt[i]]) > VSM ) { - Info << "Influence " - << nei.influencedBy(points_, points_[elmt[i]]) << endl; - FatalErrorIn - ( - "delaunayTessellation::checkTessalation()" - ) << "This is not a Delaunay hierarchy!!" - << abort(FatalError); + Info << "Influence " + << nei.influencedBy(points_, points_[elmt[i]]) << endl; + FatalErrorIn + ( + "delaunayTessellation::checkTessalation()" + ) << "This is not a Delaunay hierarchy!!" + << abort(FatalError); } } - } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.C b/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.C index 3e240386e4b3ff32ea763bf9be30efb6ea9a3fa8..e5edd24b60c2afb2465fa20f25e8c3684a24f7f8 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.H b/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.H index c7a7b4dbee7b102d7041da81d931107d2ac24f7e..75b9a6df7db901ac81fbdf9a555634473b91ea4c 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.H +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellation.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class delaunayTesselation @@ -49,53 +48,53 @@ class subdivisionTessellation : public tetTessellation { // Private member functions - //- mark all tetrahedra sharing edge e (used in addEdgeCentre) + //- mark all tetrahedra sharing edge e (used in addEdgeCentre) void treeSearch(const label elmtI, const edge& e); - - //- mark tetrahedron (used in addCentroid); - void treeSearch(const label elmtI); - - //- (used in addEdgeCentre); - void makeNewElementsBisect - ( - const label elmtI, - const edge& e, - const label pI - ); - + + //- mark tetrahedron (used in addCentroid); + void treeSearch(const label elmtI); + + //- (used in addEdgeCentre); + void makeNewElementsBisect + ( + const label elmtI, + const edge& e, + const label pI + ); + public: // Constructors //- Construct from list of points - subdivisionTessellation(const LongList<point>&); + subdivisionTessellation(const LongList<point>&); - //- Construct from triangulated surface - subdivisionTessellation(const triSurface& surf); + //- Construct from triangulated surface + subdivisionTessellation(const triSurface& surf); - //- Construct from boundBox - subdivisionTessellation(const boundBox& bb); + //- Construct from boundBox + subdivisionTessellation(const boundBox& bb); // Destructor ~subdivisionTessellation(); // Member functions - //- this function is not implemented - bool addPoint(const label); + //- this function is not implemented + bool addPoint(const label); - //- create a new point from the centroid of the given element - //- and add it into the tessellation - void addCentroid(const label elmtI); + //- create a new point from the centroid of the given element + //- and add it into the tessellation + void addCentroid(const label elmtI); - //- this is not implemented - void addCircumCentre(const label); - - //- create a new point at the centre of the given edge of the element - //- and add it into the tessellation - void addEdgeCentre(const label elmtI, const direction eI); + //- this is not implemented + void addCircumCentre(const label); + + //- create a new point at the centre of the given edge of the element + //- and add it into the tessellation + void addEdgeCentre(const label elmtI, const direction eI); - //- check if all elements have positive volume + //- check if all elements have positive volume void checkTessellation() const; }; diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellationFunctions.C b/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellationFunctions.C index de7b8c0ae74b7b54d374695ed4cbee9d395628f5..8fed45a4a08dcce72f666c0be23111f1c5d20f8d 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellationFunctions.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/subdivisionTessellation/subdivisionTessellationFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -42,84 +41,84 @@ namespace Foam bool subdivisionTessellation::addPoint(const label pI) { - FatalErrorIn - ( - "bool subdivisionTessellation::addPoint(const label)" - ) << "Not implemented!" << exit(FatalError); - - return false; + FatalErrorIn + ( + "bool subdivisionTessellation::addPoint(const label)" + ) << "Not implemented!" << exit(FatalError); + + return false; } void subdivisionTessellation::addCentroid(const label elmtI) { - const label pI = points_.size(); - points_.append(elmts_[elmtI].centroid(points_)); - - # ifdef DEBUGTessalation - Info << "subdivisionTessellation:: Adding centroid " << pI << endl; - # endif - - nElmts_ = 0; - - treeSearch(elmtI); - - makeNewElements(elmtI, pI); - - resetInfluences(elmtI); + const label pI = points_.size(); + points_.append(elmts_[elmtI].centroid(points_)); + + # ifdef DEBUGTessalation + Info << "subdivisionTessellation:: Adding centroid " << pI << endl; + # endif + + nElmts_ = 0; + + treeSearch(elmtI); + + makeNewElements(elmtI, pI); + + resetInfluences(elmtI); } void subdivisionTessellation::addCircumCentre(const label elmtI) { - FatalErrorIn - ( - "bool subdivisionTessellation::addPoint(const label)" - ) << "Not implemented!" << exit(FatalError); + FatalErrorIn + ( + "bool subdivisionTessellation::addPoint(const label)" + ) << "Not implemented!" << exit(FatalError); } void subdivisionTessellation::addEdgeCentre ( - const label elmtI, - const direction eI + const label elmtI, + const direction eI ) { - const label pI = points_.size(); - const edge e = elmts_[elmtI].edges()[eI]; - points_.append(0.5*(points_[e[0]]+points_[e[1]])); - - # ifdef DEBUGTessalation - Info << "subdivisionTessellation:: Adding edge centre " - << points_[pI] << endl; - # endif - - nElmts_ = 0; - - treeSearch(elmtI, e); - - makeNewElementsBisect(elmtI, e, pI); - - resetInfluences(elmtI); + const label pI = points_.size(); + const edge e = elmts_[elmtI].edges()[eI]; + points_.append(0.5*(points_[e[0]]+points_[e[1]])); + + # ifdef DEBUGTessalation + Info << "subdivisionTessellation:: Adding edge centre " + << points_[pI] << endl; + # endif + + nElmts_ = 0; + + treeSearch(elmtI, e); + + makeNewElementsBisect(elmtI, e, pI); + + resetInfluences(elmtI); } - + void subdivisionTessellation::treeSearch(const label elmtI) { - tessellationElement& elmt = elmts_[elmtI]; - - //- stop searching it the tessellationElement is marked already + tessellationElement& elmt = elmts_[elmtI]; + + //- stop searching it the tessellationElement is marked already if( elmt.influence_ & tessellationElement::GOOD ) return; - - # ifdef DEBUGTessalation - Info << "Setting GOOD at element " << elmtI << endl; - # endif - - elmt.influence_ |= tessellationElement::GOOD; - delElmts_[nElmts_++] = elmtI; - - for(direction ineigh=0;ineigh<DIM1;++ineigh) - { - const label el = elmt.neighbour(ineigh); - + + # ifdef DEBUGTessalation + Info << "Setting GOOD at element " << elmtI << endl; + # endif + + elmt.influence_ |= tessellationElement::GOOD; + delElmts_[nElmts_++] = elmtI; + + for(direction ineigh=0;ineigh<DIM1;++ineigh) + { + const label el = elmt.neighbour(ineigh); + if( el != -1 ) - elmts_[el].influence_ |= tessellationElement::BOUND; - } + elmts_[el].influence_ |= tessellationElement::BOUND; + } } void subdivisionTessellation::treeSearch @@ -128,32 +127,32 @@ void subdivisionTessellation::treeSearch const edge& e ) { - tessellationElement& elmt = elmts_[elmtI]; - + tessellationElement& elmt = elmts_[elmtI]; + //- stop searching if there exist an element with unknown influence if( !pointOk_ ) return; //- stop searching it the tessellationElement is marked already if( elmt.influence_ & tessellationElement::GOOD ) return; - - if( (elmt.whichPosition(e[0]) != -1) && (elmt.whichPosition(e[1]) != -1) ) - { - elmt.influence_ |= tessellationElement::GOOD; - delElmts_[nElmts_++] = elmtI; - # ifdef DEBUGTessalation - Info << "Selecting element " << elmtI << "with nodes " << elmt << endl; - # endif - } - else - { - elmt.influence_ |= tessellationElement::BOUND; - return; - } + + if( (elmt.whichPosition(e[0]) != -1) && (elmt.whichPosition(e[1]) != -1) ) + { + elmt.influence_ |= tessellationElement::GOOD; + delElmts_[nElmts_++] = elmtI; + # ifdef DEBUGTessalation + Info << "Selecting element " << elmtI << "with nodes " << elmt << endl; + # endif + } + else + { + elmt.influence_ |= tessellationElement::BOUND; + return; + } for(direction i=0;i<DIM1;++i) { const label el = elmt.neighbour(i); - + if( el != -1 ) { //- search other tessellationElements @@ -168,177 +167,177 @@ void subdivisionTessellation::treeSearch void subdivisionTessellation::makeNewElementsBisect ( - const label elmtI, - const edge& e, - const label pI + const label elmtI, + const edge& e, + const label pI ) { - # ifdef DEBUGTessalation - for(label i=0;i<nElmts_;++i) - Info << "Element to delete is " << elmts_[delElmts_[i]] << endl; - # endif - - //- create new elements - DynList<tessellationElement>* newElementsPtr = - new DynList<tessellationElement>(4*nElmts_); - for(label i=0;i<nElmts_;++i) - { - const tessellationElement& elmt = elmts_[delElmts_[i]]; - - for(direction j=0;j<DIM1;++j) - { - const label nei = elmt.neighbour(j); - if( - (nei == -1) || - (elmts_[nei].influence_ & tessellationElement::BOUND) - ) - { - triFace f = elmt.face(j); - direction nFound(0); - forAll(f, pJ) - if( e.otherVertex(f[pJ]) != -1 ) - ++nFound; - if( nFound != 2 ) - { - tessellationElement nelmt(f[0], f[1], f[2], pI); - nelmt.setNeighbour(3, nei); - nelmt.influence_ = elmt.influence_; - newElementsPtr->append(nelmt); - } - } - } - } - - //- create labels of new elements and store them - labelList newLabels(newElementsPtr->size()); - forAll(newLabels, lI) - if( lI < nElmts_ ) - { - elmts_[delElmts_[lI]] = (*newElementsPtr)[lI]; - newLabels[lI] = delElmts_[lI]; - } - else - { - newLabels[lI] = elmts_.size(); - elmts_.append((*newElementsPtr)[lI]); - } - - deleteDemandDrivenData(newElementsPtr); - # ifdef DEBUGTessalation - Info << "Labels of new elements " << newLabels << endl; - # endif - //- update neighbouring information for BOUND elements - Map<label> newPointLabel; - forAll(newLabels, lI) - { - const tessellationElement& elmt = elmts_[newLabels[lI]]; - for(direction i=0;i<DIM;++i) - if( !newPointLabel.found(elmt[i]) ) - { - const label n = newPointLabel.size(); - newPointLabel.insert(elmt[i], n); - } - - const label nei = elmt.neighbour(3); - if( nei != -1 ) - { - tessellationElement& nelmt = elmts_[nei]; - for(direction i=0;i<DIM1;++i) - if( elmt.whichPosition(nelmt[i]) == -1 ) - { - nelmt.setNeighbour(i, newLabels[lI]); - break; - } - } - } - - //- create neighbours of newly created elements - List< DynList<label> > nodeElements - ( - newPointLabel.size(), - DynList<label>(6) - ); - - forAll(newLabels, lI) - { - const tessellationElement& elmt = elmts_[newLabels[lI]]; - for(direction i=0;i<DIM;++i) - nodeElements[newPointLabel[elmt[i]]].append(newLabels[lI]); - } - - # ifdef DEBUGTessalation - Info << "Node elements " << nodeElements << endl; - Info <<"New point label " << newPointLabel << endl; - # endif - - forAll(newLabels, lI) - { - tessellationElement& elmt = elmts_[newLabels[lI]]; - for(direction i=0;i<DIM;++i) - { - const label s = newPointLabel[elmt[(i+1)%3]]; - const label e = elmt[(i+2)%3]; - const DynList<label>& nel = nodeElements[s]; - forAll(nel, elI) - if( (elmts_[nel[elI]].whichPosition(e) != -1) && - (nel[elI] != newLabels[lI]) - ) - { - elmt.setNeighbour(i, nel[elI]); - break; - } - } - } - - # ifdef DEBUGTessalation - forAll(newLabels, lI) - { - const tessellationElement& elmt = elmts_[newLabels[lI]]; - Info << "New element " << newLabels[lI] << " is " << elmt << endl; - for(direction i=0;i<DIM1;++i) - { - Info << "Neighbour over face " << elmt.face(i) << " is " - << elmt.neighbour(i) << endl; - - triFace f = elmt.face(i); - if( elmt.neighbour(i) != -1 ) - { - const label nei = elmt.neighbour(i); - bool found(false); - for(direction j=0;j<DIM1;++j) - { - triFace fnei = elmts_[nei].face(j); - if( fnei == f ) - { - found = true; - if( elmts_[nei].neighbour(j) != newLabels[lI] ) - FatalError << "Wrong neighbour addressing" - << abort(FatalError); - } - } - - if( !found ) - FatalError << "Cannot find neighbour!" << abort(FatalError); - } - } - } - # endif + # ifdef DEBUGTessalation + for(label i=0;i<nElmts_;++i) + Info << "Element to delete is " << elmts_[delElmts_[i]] << endl; + # endif + + //- create new elements + DynList<tessellationElement>* newElementsPtr = + new DynList<tessellationElement>(4*nElmts_); + for(label i=0;i<nElmts_;++i) + { + const tessellationElement& elmt = elmts_[delElmts_[i]]; + + for(direction j=0;j<DIM1;++j) + { + const label nei = elmt.neighbour(j); + if( + (nei == -1) || + (elmts_[nei].influence_ & tessellationElement::BOUND) + ) + { + triFace f = elmt.face(j); + direction nFound(0); + forAll(f, pJ) + if( e.otherVertex(f[pJ]) != -1 ) + ++nFound; + if( nFound != 2 ) + { + tessellationElement nelmt(f[0], f[1], f[2], pI); + nelmt.setNeighbour(3, nei); + nelmt.influence_ = elmt.influence_; + newElementsPtr->append(nelmt); + } + } + } + } + + //- create labels of new elements and store them + labelList newLabels(newElementsPtr->size()); + forAll(newLabels, lI) + if( lI < nElmts_ ) + { + elmts_[delElmts_[lI]] = (*newElementsPtr)[lI]; + newLabels[lI] = delElmts_[lI]; + } + else + { + newLabels[lI] = elmts_.size(); + elmts_.append((*newElementsPtr)[lI]); + } + + deleteDemandDrivenData(newElementsPtr); + # ifdef DEBUGTessalation + Info << "Labels of new elements " << newLabels << endl; + # endif + //- update neighbouring information for BOUND elements + Map<label> newPointLabel; + forAll(newLabels, lI) + { + const tessellationElement& elmt = elmts_[newLabels[lI]]; + for(direction i=0;i<DIM;++i) + if( !newPointLabel.found(elmt[i]) ) + { + const label n = newPointLabel.size(); + newPointLabel.insert(elmt[i], n); + } + + const label nei = elmt.neighbour(3); + if( nei != -1 ) + { + tessellationElement& nelmt = elmts_[nei]; + for(direction i=0;i<DIM1;++i) + if( elmt.whichPosition(nelmt[i]) == -1 ) + { + nelmt.setNeighbour(i, newLabels[lI]); + break; + } + } + } + + //- create neighbours of newly created elements + List< DynList<label> > nodeElements + ( + newPointLabel.size(), + DynList<label>() + ); + + forAll(newLabels, lI) + { + const tessellationElement& elmt = elmts_[newLabels[lI]]; + for(direction i=0;i<DIM;++i) + nodeElements[newPointLabel[elmt[i]]].append(newLabels[lI]); + } + + # ifdef DEBUGTessalation + Info << "Node elements " << nodeElements << endl; + Info <<"New point label " << newPointLabel << endl; + # endif + + forAll(newLabels, lI) + { + tessellationElement& elmt = elmts_[newLabels[lI]]; + for(direction i=0;i<DIM;++i) + { + const label s = newPointLabel[elmt[(i+1)%3]]; + const label e = elmt[(i+2)%3]; + const DynList<label>& nel = nodeElements[s]; + forAll(nel, elI) + if( (elmts_[nel[elI]].whichPosition(e) != -1) && + (nel[elI] != newLabels[lI]) + ) + { + elmt.setNeighbour(i, nel[elI]); + break; + } + } + } + + # ifdef DEBUGTessalation + forAll(newLabels, lI) + { + const tessellationElement& elmt = elmts_[newLabels[lI]]; + Info << "New element " << newLabels[lI] << " is " << elmt << endl; + for(direction i=0;i<DIM1;++i) + { + Info << "Neighbour over face " << elmt.face(i) << " is " + << elmt.neighbour(i) << endl; + + triFace f = elmt.face(i); + if( elmt.neighbour(i) != -1 ) + { + const label nei = elmt.neighbour(i); + bool found(false); + for(direction j=0;j<DIM1;++j) + { + triFace fnei = elmts_[nei].face(j); + if( fnei == f ) + { + found = true; + if( elmts_[nei].neighbour(j) != newLabels[lI] ) + FatalError << "Wrong neighbour addressing" + << abort(FatalError); + } + } + + if( !found ) + FatalError << "Cannot find neighbour!" << abort(FatalError); + } + } + } + # endif } void subdivisionTessellation::checkTessellation() const { forAll(elmts_, elI) { - const tessellationElement& elmt = elmts_[elI]; - - if( elmt.mag(points_) < 0.0 ) - { - FatalErrorIn - ( - "subdivisionTessellation::checkTessalation()" - ) << "Element " << elI << " is inverted!" << abort(FatalError); - } - } + const tessellationElement& elmt = elmts_[elI]; + + if( elmt.mag(points_) < 0.0 ) + { + FatalErrorIn + ( + "subdivisionTessellation::checkTessalation()" + ) << "Element " << elI << " is inverted!" << abort(FatalError); + } + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.C b/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.C index cb385c16ed65277d3f2720d77ef42c0350796494..a59cafffaefa75614ffcdee7f004de36cff31ec3 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -37,20 +36,20 @@ namespace Foam tessellationElement::tessellationElement() : - partTet(), - influence_(NONE) + partTet(), + influence_(NONE) { } tessellationElement::tessellationElement ( const label a, - const label b, - const label c, - const label d + const label b, + const label c, + const label d ) : - partTet(a, b, c, d), + partTet(a, b, c, d), influence_(NONE) { for(label dir=0;dir<4;++dir) @@ -67,12 +66,12 @@ tessellationElement::~tessellationElement() scalar tessellationElement::influencedBy ( - const LongList<point>& points, - const point& r + const LongList<point>& points, + const point& r ) const { - const point crcm = crcmCentre(points); - + const point crcm = crcmCentre(points); + const scalar d = (magSqr(crcm - points[a()]) - magSqr(crcm - r)); # ifdef DEBUGtessalation @@ -89,16 +88,16 @@ scalar tessellationElement::influencedBy Ostream& operator<<(Ostream& os, const tessellationElement& elmt) { - partTet t(elmt); + partTet t(elmt); os << t; - os << " neighbours are "; + os << " neighbours are "; for(label ineigh=0;ineigh<4;++ineigh) { os << " " << elmt.neighbours_[ineigh]; } - os << endl; - + os << endl; + return os; } diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.H b/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.H index e9c6575a233cebcead8540e7c80e9be270ce4f46..850e013031963a2009a9fcd2bbc9c9c8139532bb 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.H +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElement.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class delaunayElement @@ -53,33 +52,33 @@ class tessellationElement : public partTet { // Private data - - //- neighbours of the given element - label neighbours_[4]; - + + //- neighbours of the given element + label neighbours_[4]; + public: // Constructors //- Construct null - tessellationElement(); + tessellationElement(); - //- Construct from nodes + //- Construct from nodes tessellationElement - ( - const label a, - const label b, - const label c, - const label d - ); + ( + const label a, + const label b, + const label c, + const label d + ); // Destructor ~tessellationElement(); - // Enumerations and public members + // Enumerations and public members - //- types of influence a node can have on an tessellationElement + //- types of influence a node can have on an tessellationElement enum typesOfInfluence { NONE = 0, @@ -92,17 +91,17 @@ public: direction influence_; // Member functions - //- swap node with another one - inline void setNode(const direction, const label); + //- swap node with another one + inline void setNode(const direction, const label); - //- Return index of a neighbour in the given direction + //- Return index of a neighbour in the given direction inline label neighbour(const direction) const; - - //- set neighbour in a given direction - inline void setNeighbour(const direction, const label); - - //- return face in the given direction - inline triFace face(const direction) const; + + //- set neighbour in a given direction + inline void setNeighbour(const direction, const label); + + //- return face in the given direction + inline triFace face(const direction) const; //- Return the influence the point r has on this tessellationElement. // Result is the difference between the sqr of the radius of @@ -110,15 +109,15 @@ public: // centre of the circumcircle. The result is positive if the point // is inside the circle (i.e. influences it). scalar influencedBy - ( - const LongList<point>& points, - const point& r - ) const; + ( + const LongList<point>& points, + const point& r + ) const; - // Ostream Operator + // Ostream Operator friend Ostream& operator<<(Ostream&, const tessellationElement&); - - inline void operator=(const tessellationElement&); + + inline void operator=(const tessellationElement&); }; diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElementI.H b/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElementI.H index f21e277cb8d7e5e64f35cd3e21dbc5befbde5e36..6f55af2f22d2025be773459cd771f111a80ef627 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElementI.H +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/tessellationElementI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,7 @@ namespace Foam inline void tessellationElement::setNode(const direction i, const label nodeI) { - data_[i] = nodeI; + data_[i] = nodeI; } inline label tessellationElement::neighbour(const direction i) const @@ -43,49 +42,49 @@ inline label tessellationElement::neighbour(const direction i) const inline void tessellationElement::setNeighbour ( - const direction i, - const label neiI + const direction i, + const label neiI ) { - neighbours_[i] = neiI; + neighbours_[i] = neiI; } inline triFace tessellationElement::face(const direction i) const { - switch( i ) - { - case 0: - { - return triFace(data_[1], data_[3], data_[2]); - } break; - case 1: - { - return triFace(data_[0], data_[2], data_[3]); - } break; - case 2: - { - return triFace(data_[0], data_[3], data_[1]); - } break; - case 3: - { - return triFace(data_[0], data_[1], data_[2]); - } break; - }; - - return triFace(); + switch( i ) + { + case 0: + { + return triFace(data_[1], data_[3], data_[2]); + } break; + case 1: + { + return triFace(data_[0], data_[2], data_[3]); + } break; + case 2: + { + return triFace(data_[0], data_[3], data_[1]); + } break; + case 3: + { + return triFace(data_[0], data_[1], data_[2]); + } break; + }; + + return triFace(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // inline void tessellationElement::operator=(const tessellationElement& elmt) { - for(label i=0;i<4;++i) - { - data_[i] = elmt[i]; - neighbours_[i] = elmt.neighbour(i); - } - - influence_ = elmt.influence_; + for(label i=0;i<4;++i) + { + data_[i] = elmt[i]; + neighbours_[i] = elmt.neighbour(i); + } + + influence_ = elmt.influence_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.C b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.C index 093d3f07af44ad08cd7c342c336556eecc22f8ca..fe7b9a3aa7894fab9af7e21ae9b88a0cc476d2ce 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,94 +34,94 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - + void tetTessellation::createInitialTets() { - boundaryPoints_[0] = points_.size(); - points_.append(min_); - boundaryPoints_[1] = points_.size(); - points_.append(point(max_.x(), min_.y(), min_.z())); - boundaryPoints_[2] = points_.size(); - points_.append(point(max_.x(), max_.y(), min_.z())); - boundaryPoints_[3] = points_.size(); - points_.append(point(min_.x(), max_.y(), min_.z())); - boundaryPoints_[4] = points_.size(); - points_.append(point(min_.x(), min_.y(), max_.z())); - boundaryPoints_[5] = points_.size(); - points_.append(point(max_.x(), min_.y(), max_.z())); - boundaryPoints_[6] = points_.size(); - points_.append(max_); - boundaryPoints_[7] = points_.size(); - points_.append(point(min_.x(), max_.y(), max_.z())); - - DynList<label> tetLabels(5); - tetLabels.append(elmts_.size()); - elmts_.append - ( - tessellationElement - ( - boundaryPoints_[0], - boundaryPoints_[4], - boundaryPoints_[1], - boundaryPoints_[3] - ) - ); - tetLabels.append(elmts_.size()); - elmts_.append - ( - tessellationElement - ( - boundaryPoints_[5], - boundaryPoints_[1], - boundaryPoints_[4], - boundaryPoints_[6] - ) - ); - tetLabels.append(elmts_.size()); - elmts_.append - ( - tessellationElement - ( - boundaryPoints_[7], - boundaryPoints_[4], - boundaryPoints_[3], - boundaryPoints_[6] - ) - ); - tetLabels.append(elmts_.size()); - elmts_.append - ( - tessellationElement - ( - boundaryPoints_[2], - boundaryPoints_[3], - boundaryPoints_[1], - boundaryPoints_[6] - ) - ); - tetLabels.append(elmts_.size()); - elmts_.append - ( - tessellationElement - ( - boundaryPoints_[3], - boundaryPoints_[4], - boundaryPoints_[1], - boundaryPoints_[6] - ) - ); - - elmts_[tetLabels[0]].setNeighbour(0, tetLabels[4]); - elmts_[tetLabels[1]].setNeighbour(0, tetLabels[4]); - elmts_[tetLabels[2]].setNeighbour(0, tetLabels[4]); - elmts_[tetLabels[3]].setNeighbour(0, tetLabels[4]); - - elmts_[tetLabels[4]].setNeighbour(0, tetLabels[1]); - elmts_[tetLabels[4]].setNeighbour(1, tetLabels[3]); - elmts_[tetLabels[4]].setNeighbour(2, tetLabels[2]); - elmts_[tetLabels[4]].setNeighbour(3, tetLabels[0]); + boundaryPoints_[0] = points_.size(); + points_.append(min_); + boundaryPoints_[1] = points_.size(); + points_.append(point(max_.x(), min_.y(), min_.z())); + boundaryPoints_[2] = points_.size(); + points_.append(point(max_.x(), max_.y(), min_.z())); + boundaryPoints_[3] = points_.size(); + points_.append(point(min_.x(), max_.y(), min_.z())); + boundaryPoints_[4] = points_.size(); + points_.append(point(min_.x(), min_.y(), max_.z())); + boundaryPoints_[5] = points_.size(); + points_.append(point(max_.x(), min_.y(), max_.z())); + boundaryPoints_[6] = points_.size(); + points_.append(max_); + boundaryPoints_[7] = points_.size(); + points_.append(point(min_.x(), max_.y(), max_.z())); + + DynList<label> tetLabels; + tetLabels.append(elmts_.size()); + elmts_.append + ( + tessellationElement + ( + boundaryPoints_[0], + boundaryPoints_[4], + boundaryPoints_[1], + boundaryPoints_[3] + ) + ); + tetLabels.append(elmts_.size()); + elmts_.append + ( + tessellationElement + ( + boundaryPoints_[5], + boundaryPoints_[1], + boundaryPoints_[4], + boundaryPoints_[6] + ) + ); + tetLabels.append(elmts_.size()); + elmts_.append + ( + tessellationElement + ( + boundaryPoints_[7], + boundaryPoints_[4], + boundaryPoints_[3], + boundaryPoints_[6] + ) + ); + tetLabels.append(elmts_.size()); + elmts_.append + ( + tessellationElement + ( + boundaryPoints_[2], + boundaryPoints_[3], + boundaryPoints_[1], + boundaryPoints_[6] + ) + ); + tetLabels.append(elmts_.size()); + elmts_.append + ( + tessellationElement + ( + boundaryPoints_[3], + boundaryPoints_[4], + boundaryPoints_[1], + boundaryPoints_[6] + ) + ); + + elmts_[tetLabels[0]].setNeighbour(0, tetLabels[4]); + elmts_[tetLabels[1]].setNeighbour(0, tetLabels[4]); + elmts_[tetLabels[2]].setNeighbour(0, tetLabels[4]); + elmts_[tetLabels[3]].setNeighbour(0, tetLabels[4]); + + elmts_[tetLabels[4]].setNeighbour(0, tetLabels[1]); + elmts_[tetLabels[4]].setNeighbour(1, tetLabels[3]); + elmts_[tetLabels[4]].setNeighbour(2, tetLabels[2]); + elmts_[tetLabels[4]].setNeighbour(3, tetLabels[0]); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -169,10 +168,10 @@ tetTessellation::tetTessellation # ifdef DEBUGTessalation Info << "Elements " << elmts_ << endl; - forAll(elmts_, eI) - Info << "Volume of element " << eI - << " is " << elmts_[eI].mag(points_) << endl; - Info << "Number of points is " << points_.size() << endl; + forAll(elmts_, eI) + Info << "Volume of element " << eI + << " is " << elmts_[eI].mag(points_) << endl; + Info << "Number of points is " << points_.size() << endl; Info << "Number of tetrahedra is " << elmts_.size() << endl; # endif } @@ -187,16 +186,16 @@ tetTessellation::tetTessellation elmts_(), pointOk_(true), nElmts_(), - max_(Foam::max(surf.localPoints())), - min_(Foam::min(surf.localPoints())) + max_(Foam::max(surf.points())), + min_(Foam::min(surf.points())) { createInitialTets(); # ifdef DEBUGTessalation Info << "Elements " << elmts_ << endl; - forAll(elmts_, eI) - Info << "Volume of element " << eI - << " is " << elmts_[eI].mag(points_) << endl; + forAll(elmts_, eI) + Info << "Volume of element " << eI + << " is " << elmts_[eI].mag(points_) << endl; # endif } @@ -214,9 +213,9 @@ tetTessellation::tetTessellation(const boundBox& bb) # ifdef DEBUGTessalation Info << "Elements " << elmts_ << endl; - forAll(elmts_, eI) - Info << "Volume of element " << eI - << " is " << elmts_[eI].mag(points_) << endl; + forAll(elmts_, eI) + Info << "Volume of element " << eI + << " is " << elmts_[eI].mag(points_) << endl; # endif } diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.H b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.H index 43b0ef69f60b6906b96ad1897db4f91664aa3286..4b1a079c1b9331657d76736e2b26ba6903f42daa 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.H +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellation.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class tetTessellation @@ -44,7 +43,7 @@ SourceFiles namespace Foam { - + class triSurface; /*---------------------------------------------------------------------------*\ @@ -54,16 +53,16 @@ class triSurface; class tetTessellation { protected: - + // Protected data //- The points LongList<point> points_; - - //- labels of boundary tet points - //- boundary tet encompasses the whole structure and all elements of - //- interest are contained inside it. The labels of these points are - //- stored such that they can be removed from the final mesh - label boundaryPoints_[8]; + + //- labels of boundary tet points + //- boundary tet encompasses the whole structure and all elements of + //- interest are contained inside it. The labels of these points are + //- stored such that they can be removed from the final mesh + label boundaryPoints_[8]; //- The tessellationElements LongList<tessellationElement> elmts_; @@ -78,28 +77,28 @@ protected: point min_; // Protected member functions - label findInitialElement(const point&); + label findInitialElement(const point&); void treeSearch(const label elmtI, const point&); void resetInfluences(const label elmtI); void makeNewElements(const label elmtI, const label pI); - - void createInitialTets(); - + + void createInitialTets(); + public: // Constructors //- Construct from list of points - tetTessellation(const LongList<point>&); + tetTessellation(const LongList<point>&); - //- Construct from triangulated surface - tetTessellation(const triSurface& surf); + //- Construct from triangulated surface + tetTessellation(const triSurface& surf); - //- Construct from boundBox - tetTessellation(const boundBox& bb); + //- Construct from boundBox + tetTessellation(const boundBox& bb); // Destructor @@ -107,30 +106,30 @@ public: // Member functions - //- add point which is already in the list of points - virtual bool addPoint(const label pI) = 0; + //- add point which is already in the list of points + virtual bool addPoint(const label pI) = 0; - //- create a new point from the centroid of the given element - //- and add it into the tessellation - virtual void addCentroid(const label elmtI) = 0; + //- create a new point from the centroid of the given element + //- and add it into the tessellation + virtual void addCentroid(const label elmtI) = 0; - //- create a new point from the circumcentre of the given element - //- and add it into the tessellation - virtual void addCircumCentre(const label elmtI) = 0; - - //- create a new point at the centre of the given edge of the element - //- and add it into the tessellation - virtual void addEdgeCentre(const label elmtI, const direction eI) = 0; + //- create a new point from the circumcentre of the given element + //- and add it into the tessellation + virtual void addCircumCentre(const label elmtI) = 0; + + //- create a new point at the centre of the given edge of the element + //- and add it into the tessellation + virtual void addEdgeCentre(const label elmtI, const direction eI) = 0; const LongList<point>& points() const { return points_; }; - - const LongList<tessellationElement>& elmts() const - { - return elmts_; - } + + const LongList<tessellationElement>& elmts() const + { + return elmts_; + } const point& max() const { diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationFunctions.C b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationFunctions.C index 878437fcef73077a44ce5d53d199a757a5d9cfb1..0411dcaed0604d289e9f0bbbdf31404d57bf97e4 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationFunctions.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -43,11 +42,11 @@ label tetTessellation::findInitialElement(const point& p) label el = elmts_.size() - 1; //- find an tessellationElement which is influenced by the point - //- this brutal force search is not to be used for big tessellations + //- this brutal force search is not to be used for big tessellations const label nEl = elmts_.size(); - for(label tI=0;tI<nEl;++tI) - if( elmts_[tI].influencedBy(points_, p) > VSM ) - return tI; + for(label tI=0;tI<nEl;++tI) + if( elmts_[tI].influencedBy(points_, p) > VSM ) + return tI; return el; } @@ -58,15 +57,15 @@ void tetTessellation::treeSearch const point& p ) { - tessellationElement& elmt = elmts_[elmtI]; - + tessellationElement& elmt = elmts_[elmtI]; + //- stop searching if there exist an element with unknown influence if( !pointOk_ ) return; //- stop searching it the tessellationElement is marked already if( elmt.influence_ & tessellationElement::GOOD ) return; - - const scalar infl = elmt.influencedBy(points_, p); + + const scalar infl = elmt.influencedBy(points_, p); if( infl > VSM ) { @@ -89,8 +88,8 @@ void tetTessellation::treeSearch { point& r = const_cast<point&>(p); Random rnd(0); - - const point crcm = elmt.crcmCentre(points_); + + const point crcm = elmt.crcmCentre(points_); point add = p - 1e-7 * @@ -127,8 +126,8 @@ void tetTessellation::treeSearch void tetTessellation::resetInfluences(const label elmtI) { - tessellationElement& elmt = elmts_[elmtI]; - + tessellationElement& elmt = elmts_[elmtI]; + if( !elmt.influence_ ) return; elmt.influence_ = tessellationElement::NONE; diff --git a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationNewElmts.C b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationNewElmts.C index 9e2739d5bb1b5bca92642fd7040c1c46b3ee9a9c..906f15d2ffc3791e3a8edc420ca6ee7b9d9266d7 100644 --- a/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationNewElmts.C +++ b/meshLibrary/utilities/tetrahedra/tetTessellation/tetTessellationNewElmts.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -41,146 +40,146 @@ namespace Foam void tetTessellation::makeNewElements(const label elmtI, const label pI) { - # ifdef DEBUGTessalation - for(label i=0;i<nElmts_;++i) - Info << "Element to delete is " << elmts_[delElmts_[i]] << endl; - # endif - - //- create new elements - DynList<tessellationElement>* newElementsPtr = - new DynList<tessellationElement>(4*nElmts_); - for(label i=0;i<nElmts_;++i) - { - const tessellationElement& elmt = elmts_[delElmts_[i]]; - - for(direction j=0;j<DIM1;++j) - { - const label nei = elmt.neighbour(j); - if( - (nei == -1) || - (elmts_[nei].influence_ & tessellationElement::BOUND) - ) - { - triFace f = elmt.face(j); - tessellationElement nelmt(f[0], f[1], f[2], pI); - nelmt.setNeighbour(3, nei); - nelmt.influence_ = elmt.influence_; - newElementsPtr->append(nelmt); - } - } - } - - //- create labels of new elements and store them - labelList newLabels(newElementsPtr->size()); - forAll(newLabels, lI) - if( lI < nElmts_ ) - { - elmts_[delElmts_[lI]] = (*newElementsPtr)[lI]; - newLabels[lI] = delElmts_[lI]; - } - else - { - newLabels[lI] = elmts_.size(); - elmts_.append((*newElementsPtr)[lI]); - } - - deleteDemandDrivenData(newElementsPtr); - # ifdef DEBUGTessalation - Info << "Labels of new elements " << newLabels << endl; - # endif - //- update neighbouring information for BOUND elements - Map<label> newPointLabel; - forAll(newLabels, lI) - { - const tessellationElement& elmt = elmts_[newLabels[lI]]; - for(direction i=0;i<DIM;++i) - if( !newPointLabel.found(elmt[i]) ) - { - const label n = newPointLabel.size(); - newPointLabel.insert(elmt[i], n); - } - - const label nei = elmt.neighbour(3); - if( nei != -1 ) - { - tessellationElement& nelmt = elmts_[nei]; - for(direction i=0;i<DIM1;++i) - if( elmt.whichPosition(nelmt[i]) == -1 ) - { - nelmt.setNeighbour(i, newLabels[lI]); - break; - } - } - } - - //- create neighbours of newly created elements - List< DynList<label> > nodeElements - ( - newPointLabel.size(), - DynList<label>(6) - ); - - forAll(newLabels, lI) - { - const tessellationElement& elmt = elmts_[newLabels[lI]]; - for(direction i=0;i<DIM;++i) - nodeElements[newPointLabel[elmt[i]]].append(newLabels[lI]); - } - - # ifdef DEBUGTessalation - Info << "Node elements " << nodeElements << endl; - Info <<"New point label " << newPointLabel << endl; - # endif - - forAll(newLabels, lI) - { - tessellationElement& elmt = elmts_[newLabels[lI]]; - for(direction i=0;i<DIM;++i) - { - const label s = newPointLabel[elmt[(i+1)%3]]; - const label e = elmt[(i+2)%3]; - const DynList<label>& nel = nodeElements[s]; - forAll(nel, elI) - if( (elmts_[nel[elI]].whichPosition(e) != -1) && - (nel[elI] != newLabels[lI]) - ) - elmt.setNeighbour(i, nel[elI]); - } - } - - # ifdef DEBUGTessalation - forAll(newLabels, lI) - { - const tessellationElement& elmt = elmts_[newLabels[lI]]; - Info << "New element " << newLabels[lI] << " is " << elmt << endl; - for(direction i=0;i<DIM1;++i) - { - Info << "Neighbour over face " << elmt.face(i) << " is " - << elmt.neighbour(i) << endl; - - triFace f = elmt.face(i); - if( elmt.neighbour(i) != -1 ) - { - const label nei = elmt.neighbour(i); - bool found(false); - for(direction j=0;j<DIM1;++j) - { - triFace fnei = elmts_[nei].face(j); - if( fnei == f ) - { - found = true; - if( elmts_[nei].neighbour(j) != newLabels[lI] ) - FatalError << "Wrong neighbour addressing" - << abort(FatalError); - } - } - - if( !found ) - FatalError << "Cannot find neighbour!" << abort(FatalError); - } - } - } - # endif + # ifdef DEBUGTessalation + for(label i=0;i<nElmts_;++i) + Info << "Element to delete is " << elmts_[delElmts_[i]] << endl; + # endif + + //- create new elements + DynList<tessellationElement>* newElementsPtr = + new DynList<tessellationElement>(4*nElmts_); + for(label i=0;i<nElmts_;++i) + { + const tessellationElement& elmt = elmts_[delElmts_[i]]; + + for(direction j=0;j<DIM1;++j) + { + const label nei = elmt.neighbour(j); + if( + (nei == -1) || + (elmts_[nei].influence_ & tessellationElement::BOUND) + ) + { + triFace f = elmt.face(j); + tessellationElement nelmt(f[0], f[1], f[2], pI); + nelmt.setNeighbour(3, nei); + nelmt.influence_ = elmt.influence_; + newElementsPtr->append(nelmt); + } + } + } + + //- create labels of new elements and store them + labelList newLabels(newElementsPtr->size()); + forAll(newLabels, lI) + if( lI < nElmts_ ) + { + elmts_[delElmts_[lI]] = (*newElementsPtr)[lI]; + newLabels[lI] = delElmts_[lI]; + } + else + { + newLabels[lI] = elmts_.size(); + elmts_.append((*newElementsPtr)[lI]); + } + + deleteDemandDrivenData(newElementsPtr); + # ifdef DEBUGTessalation + Info << "Labels of new elements " << newLabels << endl; + # endif + //- update neighbouring information for BOUND elements + Map<label> newPointLabel; + forAll(newLabels, lI) + { + const tessellationElement& elmt = elmts_[newLabels[lI]]; + for(direction i=0;i<DIM;++i) + if( !newPointLabel.found(elmt[i]) ) + { + const label n = newPointLabel.size(); + newPointLabel.insert(elmt[i], n); + } + + const label nei = elmt.neighbour(3); + if( nei != -1 ) + { + tessellationElement& nelmt = elmts_[nei]; + for(direction i=0;i<DIM1;++i) + if( elmt.whichPosition(nelmt[i]) == -1 ) + { + nelmt.setNeighbour(i, newLabels[lI]); + break; + } + } + } + + //- create neighbours of newly created elements + List< DynList<label> > nodeElements + ( + newPointLabel.size(), + DynList<label>() + ); + + forAll(newLabels, lI) + { + const tessellationElement& elmt = elmts_[newLabels[lI]]; + for(direction i=0;i<DIM;++i) + nodeElements[newPointLabel[elmt[i]]].append(newLabels[lI]); + } + + # ifdef DEBUGTessalation + Info << "Node elements " << nodeElements << endl; + Info <<"New point label " << newPointLabel << endl; + # endif + + forAll(newLabels, lI) + { + tessellationElement& elmt = elmts_[newLabels[lI]]; + for(direction i=0;i<DIM;++i) + { + const label s = newPointLabel[elmt[(i+1)%3]]; + const label e = elmt[(i+2)%3]; + const DynList<label>& nel = nodeElements[s]; + forAll(nel, elI) + if( (elmts_[nel[elI]].whichPosition(e) != -1) && + (nel[elI] != newLabels[lI]) + ) + elmt.setNeighbour(i, nel[elI]); + } + } + + # ifdef DEBUGTessalation + forAll(newLabels, lI) + { + const tessellationElement& elmt = elmts_[newLabels[lI]]; + Info << "New element " << newLabels[lI] << " is " << elmt << endl; + for(direction i=0;i<DIM1;++i) + { + Info << "Neighbour over face " << elmt.face(i) << " is " + << elmt.neighbour(i) << endl; + + triFace f = elmt.face(i); + if( elmt.neighbour(i) != -1 ) + { + const label nei = elmt.neighbour(i); + bool found(false); + for(direction j=0;j<DIM1;++j) + { + triFace fnei = elmts_[nei].face(j); + if( fnei == f ) + { + found = true; + if( elmts_[nei].neighbour(j) != newLabels[lI] ) + FatalError << "Wrong neighbour addressing" + << abort(FatalError); + } + } + + if( !found ) + FatalError << "Cannot find neighbour!" << abort(FatalError); + } + } + } + # endif } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdges.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdges.C new file mode 100644 index 0000000000000000000000000000000000000000..d3f846ff2381692396f5c598251280498b3289e9 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdges.C @@ -0,0 +1,67 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfaceClassifyEdges.H" +#include "helperFunctions.H" +#include "demandDrivenData.H" +#include "triSurfModifier.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfaceClassifyEdges::triSurfaceClassifyEdges +( + const meshOctree& octree +) +: + octree_(octree), + edgeTypes_(), + facetOrientation_() +{ + checkOrientation(); + + classifyEdgesTypes(); +} + +triSurfaceClassifyEdges::~triSurfaceClassifyEdges() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +const List<direction>& triSurfaceClassifyEdges::edgeTypes() const +{ + return edgeTypes_; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdges.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdges.H new file mode 100644 index 0000000000000000000000000000000000000000..43cc2a082fb5011a5b9afb155d22f3c239a05094 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdges.H @@ -0,0 +1,124 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfaceClassifyEdges + +Description + Divides the surface mesh into regions bounded by feature edges + +SourceFiles + triSurfaceClassifyEdges.C + triSurfaceClassifyEdgesFunctions.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfaceClassifyEdges_H +#define triSurfaceClassifyEdges_H + +#include "triSurf.H" +#include "VRWGraph.H" +#include "boolList.H" +#include "direction.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +//- Forward declarations +class meshOctree; + +/*---------------------------------------------------------------------------*\ + Class triSurfaceClassifyEdges Declaration +\*---------------------------------------------------------------------------*/ + +class triSurfaceClassifyEdges +{ + // Private data + //- reference to meshOctree + const meshOctree& octree_; + + //- flags for surface edges + List<direction> edgeTypes_; + + //- orientation of facet's normal (0 - unknown, 1- outward, 2- inward) + List<direction> facetOrientation_; + + // Private member functions + //- check the orientation of the patches in the triangulated surface + void checkOrientation(); + + //- classify edges based on the orientation of the surface facets + void classifyEdgesTypes(); + + //- Disallow default bitwise copy construct + triSurfaceClassifyEdges(const triSurfaceClassifyEdges&); + + //- Disallow default bitwise assignment + void operator=(const triSurfaceClassifyEdges&); + +public: + + // Enumerators + + enum edgeType_ + { + NONE = 0, + CONVEXEDGE = 1, + CONCAVEEDGE = 2, + FLATSURFACEEDGE = 4, + FEATUREEDGE = 8 + }; + + // Constructors + + //- Construct from octree + triSurfaceClassifyEdges(const meshOctree& octree); + + // Destructor + + ~triSurfaceClassifyEdges(); + + + // Member Functions + + //- return the edge type according to the above enumerator + inline direction edgeType(const label edgeI) const + { + return edgeTypes_[edgeI]; + } + + //- return the list of edge classification + const List<direction>& edgeTypes() const; +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdgesFunctions.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdgesFunctions.C new file mode 100644 index 0000000000000000000000000000000000000000..670fc2c75f68689549837c1e5f80570247b9c04a --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceClassifyEdges/triSurfaceClassifyEdgesFunctions.C @@ -0,0 +1,402 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfaceClassifyEdges.H" +#include "demandDrivenData.H" +#include "helperFunctions.H" +#include "triSurf.H" +#include "meshOctree.H" +#include "labelPair.H" + +#ifdef USE_OMP +#include <omp.h> +#endif + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfaceClassifyEdges::checkOrientation() +{ + const triSurf& surf = octree_.surface(); + const boundBox& rootBox = octree_.rootBox(); + const pointField& points = surf.points(); + const VRWGraph& facetEdges = surf.facetEdges(); + const VRWGraph& edgeFacets = surf.edgeFacets(); + + facetOrientation_.setSize(surf.size()); + + //- sort all surface facets into groups consisting of facets with consistent + //- orientation. Do not cross non-manifold edges + labelLongList orientationGroup(surf.size(), -1); + label nGroups(0); + + forAll(surf, triI) + { + if( orientationGroup[triI] != -1 ) + continue; + + orientationGroup[triI] = nGroups; + labelLongList front; + front.append(triI); + + while( front.size() != 0 ) + { + const label tLabel = front.removeLastElement(); + + const labelledTri& facet = surf[tLabel]; + + forAll(facet, eI) + { + const label edgeI = facetEdges(tLabel, eI); + + if( edgeFacets.sizeOfRow(edgeI) != 2 ) + continue; + + forAllRow(edgeFacets, edgeI, efI) + { + const label neiFacetI = edgeFacets(edgeI, efI); + + if( orientationGroup[neiFacetI] != -1 ) + continue; + if( neiFacetI == tLabel ) + continue; + + const labelledTri& neiFacet = surf[neiFacetI]; + + //- check the orientation of triangles at this edge + //- check the sign of the angle + //- if the orientation is not consistent + DynList<labelPair, 2> sharedIndices; + forAll(facet, i) + { + forAll(neiFacet, j) + { + if( facet[i] == neiFacet[j] ) + sharedIndices.append(labelPair(i, j)); + } + } + + if( sharedIndices.size() == 2 ) + { + const labelPair& pair0 = sharedIndices[0]; + const labelPair& pair1 = sharedIndices[1]; + if( ((pair0.first() + 1) % 3) == pair1.first() ) + { + if( (pair1.second() + 1) % 3 == pair0.second() ) + { + orientationGroup[neiFacetI] = nGroups; + front.append(neiFacetI); + } + } + else + { + if( (pair0.second() + 1) % 3 == pair1.second() ) + { + orientationGroup[neiFacetI] = nGroups; + front.append(neiFacetI); + } + } + } + } + } + } + + ++nGroups; + } + + Info << "Found " << nGroups + << " groups of triangles with consistent orientation" << endl; + + //- find the octree leaves containing each triangle + VRWGraph triangleInLeaves(surf.size()); + labelLongList ntl(surf.size(), 0); + + DynList<label> helper; + for(label leafI=0;leafI<octree_.numberOfLeaves();++leafI) + { + helper.clear(); + octree_.containedTriangles(leafI, helper); + + forAll(helper, i) + ++ntl[helper[i]]; + } + + forAll(ntl, triI) + triangleInLeaves.setRowSize(triI, ntl[triI]); + + ntl = 0; + for(label leafI=0;leafI<octree_.numberOfLeaves();++leafI) + { + helper.clear(); + octree_.containedTriangles(leafI, helper); + + forAll(helper, i) + { + const label triI = helper[i]; + + triangleInLeaves(triI, ntl[triI]++) = leafI; + } + } + + //- check the orientation of all facets in a group and collect their votes + DynList<labelPair> groupVotes; + groupVotes.setSize(nGroups); + groupVotes = labelPair(0, 0); + + # ifdef USE_OMP + # pragma omp parallel if( surf.size() > 1000 ) private(helper) + # endif + { + DynList<labelPair> localVotes; + localVotes.setSize(nGroups); + localVotes = labelPair(0, 0); + + # ifdef USE_OMP + # pragma omp for schedule(dynamic, 40) + # endif + forAll(orientationGroup, triI) + { + const labelledTri& tri = surf[triI]; + const point c = tri.centre(points); + vector n = tri.normal(points); + const scalar magN = mag(n); + + if( magN < VSMALL ) + continue; + + n /= magN; + + //- find the OUTSIDE octree cubes in the vicinity of the triangle + //- and check the orientation of the triangle + forAllRow(triangleInLeaves, triI, tlI) + { + const label leafI = triangleInLeaves(triI, tlI); + + octree_.findAllLeafNeighbours(leafI, helper); + + forAll(helper, i) + { + const label leafJ = helper[i]; + + const meshOctreeCubeBasic& oc = octree_.returnLeaf(leafJ); + + if( oc.cubeType() & meshOctreeCubeBasic::OUTSIDE ) + { + const scalar length = 3.0 * oc.size(rootBox); + + point pMin, pMax; + oc.cubeBox(rootBox, pMin, pMax); + + const boundBox bb(pMin, pMax); + + //- check whether the ray casted from + //- the centre of the triangle intersects the cube + const point endPos = c + length * n; + const point endNeg = c - length * n; + + if( help::boundBoxLineIntersection(c, endPos, bb) ) + { + //- found an intersection in the positive direction + ++localVotes[orientationGroup[triI]].first(); + } + else if( help::boundBoxLineIntersection(c, endNeg, bb) ) + { + //- found an intersection in the negative direction + ++localVotes[orientationGroup[triI]].second(); + } + } + } + } + } + + # ifdef USE_OMP + # pragma omp critical(grouping) + # endif + { + forAll(localVotes, groupI) + { + groupVotes[groupI].first() += localVotes[groupI].first(); + groupVotes[groupI].second() += localVotes[groupI].second(); + } + } + } + + Info << "Before determining of orientation" << endl; + + //- determine whether a group is oriented outward or inward + List<direction> outwardGroup(nGroups, direction(0)); + + forAll(groupVotes, groupI) + { + if( groupVotes[groupI].first() > groupVotes[groupI].second() ) + { + outwardGroup[groupI] = 1; + } + else if( groupVotes[groupI].first() < groupVotes[groupI].second() ) + { + outwardGroup[groupI] = 2; + } + } + + Info << "Here setting orientation" << endl; + //- Finally, set the orientation of the normal + facetOrientation_.setSize(surf.size()); + forAll(facetOrientation_, triI) + facetOrientation_[triI] = outwardGroup[orientationGroup[triI]]; +} + +void triSurfaceClassifyEdges::classifyEdgesTypes() +{ + const triSurf& surf = octree_.surface(); + const pointField& points = surf.points(); + const VRWGraph& edgeFacets = surf.edgeFacets(); + const edgeLongList& edges = surf.edges(); + const VRWGraph& pointEdges = surf.pointEdges(); + const edgeLongList& featureEdges = surf.featureEdges(); + + edgeTypes_.setSize(edgeFacets.size()); + edgeTypes_ = NONE; + + //- set feature edge types + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 20) + # endif + forAll(featureEdges, feI) + { + const edge& e = featureEdges[feI]; + + forAllRow(pointEdges, e.start(), peI) + { + if( edges[pointEdges(e.start(), peI)] == e ) + edgeTypes_[pointEdges(e.start(), peI)] |= FEATUREEDGE; + } + } + + //- Finally, check the edges and assign flags + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif + forAll(edgeFacets, edgeI) + { + if( edgeFacets.sizeOfRow(edgeI) != 2 ) + { + //- this is not a manifold edge + edgeTypes_[edgeI] = NONE; + continue; + } + + //- surface is a manifold at this edge + const label f0 = edgeFacets(edgeI, 0); + const label f1 = edgeFacets(edgeI, 1); + + const labelledTri& tri0 = surf[f0]; + const labelledTri& tri1 = surf[f1]; + + if( tri0.region() != tri1.region() ) + edgeTypes_[edgeI] |= FEATUREEDGE; + + label apexNode(-1); + forAll(tri1, pI) + { + bool found(false); + forAll(tri0, pJ) + { + if( tri0[pJ] == tri1[pI] ) + { + found = true; + break; + } + + if( found ) + break; + } + + if( !found ) + { + apexNode = tri1[pI]; + break; + } + } + + const tetrahedron<point, point> tet + ( + points[tri0[0]], + points[tri0[1]], + points[tri0[2]], + points[apexNode] + ); + + const scalar vol = tet.mag(); + + if( facetOrientation_[f0] == 1 ) + { + //- facet is outward oriented + if( vol < -VSMALL ) + { + //- this is a convex edge + edgeTypes_[edgeI] |= CONVEXEDGE; + } + else if( vol > VSMALL ) + { + //- this is a concave edge + edgeTypes_[edgeI] |= CONCAVEEDGE; + } + else + { + edgeTypes_[edgeI] |= FLATSURFACEEDGE; + } + } + else if( facetOrientation_[f0] == 2 ) + { + //- facet is inward oriented + if( vol > VSMALL ) + { + //- this is a convex edge + edgeTypes_[edgeI] |= CONVEXEDGE; + } + else if( vol < -VSMALL ) + { + //- this is a concave edge + edgeTypes_[edgeI] |= CONCAVEEDGE; + } + else + { + edgeTypes_[edgeI] |= FLATSURFACEEDGE; + } + } + } +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.C index ecd46dbbd4b4c8eab6b18a664a4500b08efff692..6e9738238582cdf8506e87688b580977f0d0b9ef 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -44,7 +43,7 @@ triSurfaceCleanupDuplicates::triSurfaceCleanupDuplicates ) : tolerance_(tol), - surf_(octree.surface()), + surf_(const_cast<triSurf&>(octree.surface())), octree_(octree), newTriangleLabel_(), done_(false) diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.H index 748d1e8ee556ca0a0ae643e5e70346e4114665ac..c89c455adb5a6b188080273d7a1da9651c1d3daa 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.H +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicates.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triSurfaceCleanupDuplicates Description Provides information regarding surface partitions on the surface - triangulation, and connectivity between various surface partitions. + triangulation, and connectivity between various surface partitions. SourceFiles triSurfaceCleanupDuplicatesDuplicates.C @@ -59,13 +58,13 @@ class triSurfaceCleanupDuplicates const scalar tolerance_; //- reference to triSurf - const triSurf& surf_; + triSurf& surf_; //- reference to octree const meshOctree& octree_; //- new triangle labels in case some of them is removed - labelListPMG newTriangleLabel_; + labelLongList newTriangleLabel_; //- check if the operation has already been performed bool done_; @@ -78,7 +77,7 @@ class triSurfaceCleanupDuplicates bool mergeDuplicatePoints(); //- update triangle mapping - void updateTriangleLabels(const labelListPMG&); + void updateTriangleLabels(const labelLongList&); //- Disallow default bitwise copy construct triSurfaceCleanupDuplicates(const triSurfaceCleanupDuplicates&); diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicatesFunctions.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicatesFunctions.C index 28f76d7a3676943ba0be559640dff5a9d81c5e16..9664b3c7c66f05824f65508267bb516abc02e571 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicatesFunctions.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCleanupDuplicates/triSurfaceCleanupDuplicatesFunctions.C @@ -1,36 +1,38 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description \*---------------------------------------------------------------------------*/ #include "triSurfaceCleanupDuplicates.H" +#include "triSurfModifier.H" #include "meshOctree.H" #include "demandDrivenData.H" +# ifdef USE_OMP #include <omp.h> +# endif #include <set> // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -42,9 +44,9 @@ namespace Foam bool triSurfaceCleanupDuplicates::checkDuplicateTriangles() { - labelListPMG newTriangleLabel(surf_.size(), -1); + labelLongList newTriangleLabel(surf_.size(), -1); - const labelListList& pointTriangles = surf_.pointFaces(); + const VRWGraph& pointTriangles = surf_.pointFacets(); //- check if there exist duplicate triangles label counter(0); @@ -61,7 +63,7 @@ bool triSurfaceCleanupDuplicates::checkDuplicateTriangles() forAll(pointTriangles[tri[0]], ptI) { - const label triJ = pointTriangles[tri[0]][ptI]; + const label triJ = pointTriangles(tri[0], ptI); if( triJ <= triI ) continue; @@ -84,7 +86,7 @@ bool triSurfaceCleanupDuplicates::checkDuplicateTriangles() Info << "New number of triangles " << counter << endl; //- create new list of triangles and store it in the surface mesh - List<labelledTri> newTriangles(counter); + LongList<labelledTri> newTriangles(counter); forAll(newTriangleLabel, triI) { @@ -93,14 +95,8 @@ bool triSurfaceCleanupDuplicates::checkDuplicateTriangles() updateTriangleLabels(newTriangleLabel); - triSurface newSurf - ( - newTriangles, - surf_.patches(), - surf_.points() - ); - - const_cast<triSurface&>(static_cast<const triSurface&>(surf_)) = newSurf; + triSurfModifier(surf_).facetsAccess().transfer(newTriangles); + surf_.updateFacetsSubsets(newTriangleLabel); return true; } @@ -108,20 +104,27 @@ bool triSurfaceCleanupDuplicates::checkDuplicateTriangles() bool triSurfaceCleanupDuplicates::mergeDuplicatePoints() { pointField& pts = const_cast<pointField&>(surf_.points()); - labelListPMG newPointLabel(surf_.localPoints().size()); + labelLongList newPointLabel(surf_.nPoints()); bool foundDuplicates(false); + # ifdef USE_OMP # pragma omp parallel + # endif { + # ifdef USE_OMP # pragma omp for + # endif forAll(newPointLabel, pI) newPointLabel[pI] = pI; + # ifdef USE_OMP # pragma omp barrier - + # endif //- check if there exist any vertices closer //- than the prescribed tolerance + # ifdef USE_OMP # pragma omp for schedule(dynamic, 20) + # endif for(label leafI=0;leafI<octree_.numberOfLeaves();++leafI) { DynList<label> ct; @@ -159,7 +162,9 @@ bool triSurfaceCleanupDuplicates::mergeDuplicatePoints() if( magSqr(pts[pointI] - pts[*nIt]) < sqr(tolerance_) ) { foundDuplicates = true; + # ifdef USE_OMP # pragma omp critical + # endif newPointLabel[*nIt] = pointI; } } @@ -170,9 +175,6 @@ bool triSurfaceCleanupDuplicates::mergeDuplicatePoints() if( !foundDuplicates ) return false; - List<labelledTri>& triangles = - const_cast<List<labelledTri>&>(surf_.localFaces()); - //- remove vertices and update node labels label counter(0); forAll(pts, pI) @@ -194,7 +196,8 @@ bool triSurfaceCleanupDuplicates::mergeDuplicatePoints() pts.setSize(counter); //- remove triangles containing duplicate points - labelListPMG newTriangleLabel(surf_.size(), -1); + LongList<labelledTri> newTriangles(surf_.facets()); + labelLongList newTriangleLabel(surf_.size(), -1); counter = 0; forAll(surf_, triI) @@ -219,31 +222,24 @@ bool triSurfaceCleanupDuplicates::mergeDuplicatePoints() if( store ) { - triangles[counter] = newTri; + newTriangles[counter] = newTri; newTriangleLabel[triI] = counter; ++counter; } } - triangles.setSize(counter); - - updateTriangleLabels(newTriangleLabel); - - triSurface newSurf - ( - triangles, - surf_.patches(), - pts - ); + newTriangles.setSize(counter); - const_cast<triSurface&>(static_cast<const triSurface&>(surf_)) = newSurf; + //- update the surface + triSurfModifier(surf_).facetsAccess().transfer(newTriangles); + surf_.updateFacetsSubsets(newTriangleLabel); return true; } void triSurfaceCleanupDuplicates::updateTriangleLabels ( - const labelListPMG& newTriangleLabel + const labelLongList& newTriangleLabel ) { //- update addressing between the original triangles and the cleaned mesh diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCopyParts/triSurfaceCopyParts.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceCopyParts/triSurfaceCopyParts.C new file mode 100644 index 0000000000000000000000000000000000000000..bb9b8d67619294c5ef67f59b899659b50d7f17b5 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCopyParts/triSurfaceCopyParts.C @@ -0,0 +1,200 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfaceCopyParts.H" +#include "triSurfModifier.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfaceCopyParts::markFacetsForCopying +( + const wordList& parts, + boolList& copyFacets +) const +{ + copyFacets.setSize(surf_.size()); + copyFacets = false; + + const geometricSurfacePatchList& patches = surf_.patches(); + + //- mark patches which will be removed + boolList removePatch(patches.size(), false); + + forAll(patches, patchI) + { + const word name = patches[patchI].name(); + + forAll(parts, partI) + { + if( parts[partI] == name ) + { + removePatch[patchI] = true; + break; + } + } + } + + //- select facets affected by the deletion of a patch + forAll(surf_, triI) + { + if( removePatch[surf_[triI].region()] ) + copyFacets[triI] = true; + } + + //- mark facets contained in selected subsets + DynList<label> facetSubsetsIDs; + surf_.facetSubsetIndices(facetSubsetsIDs); + + forAll(facetSubsetsIDs, i) + { + const word fsName = surf_.facetSubsetName(facetSubsetsIDs[i]); + + forAll(parts, partI) + { + if( parts[partI] == fsName ) + { + labelLongList containedFacets; + surf_.facetsInSubset(facetSubsetsIDs[i], containedFacets); + + forAll(containedFacets, cfI) + copyFacets[containedFacets[cfI]] = true; + + break; + } + } + } +} + +void triSurfaceCopyParts::copySurfaceMesh +( + const boolList& copyFacets, + triSurf& s +) const +{ + Info << "Starting copying surface parts" << endl; + + const pointField& pts = surf_.points(); + + labelLongList newPointLabel(pts.size(), -1); + + label nPoints(0); + + //- create the modifier and delete data if there is any + triSurfModifier sm(s); + LongList<labelledTri>& newTriangles = sm.facetsAccess(); + newTriangles.clear(); + sm.featureEdgesAccess().clear(); + sm.patchesAccess().setSize(1); + sm.patchesAccess()[0] = geometricSurfacePatch("patch0", "patch", 0); + + //- copy selected patches + forAll(copyFacets, triI) + { + if( !copyFacets[triI] ) + continue; + + const labelledTri& tri = surf_[triI]; + + labelledTri newTri; + newTri.region() = 0; + + forAll(tri, pI) + { + if( newPointLabel[tri[pI]] == -1 ) + { + newPointLabel[tri[pI]] = nPoints; + ++nPoints; + } + + newTri[pI] = newPointLabel[tri[pI]]; + } + + newTriangles.append(newTri); + } + + Info << "Copied triangles " << newTriangles.size() << endl; + Info << "Number of vertices " << nPoints << endl; + + //- copy vertices + pointField& newPts = sm.pointsAccess(); + newPts.setSize(nPoints); + + forAll(newPointLabel, i) + { + if( newPointLabel[i] < 0 ) + continue; + + newPts[newPointLabel[i]] = pts[i]; + } + + Info << "Finished copying surface parts" << endl; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfaceCopyParts::triSurfaceCopyParts(const triSurf& surface) +: + surf_(surface) +{} + +triSurfaceCopyParts::~triSurfaceCopyParts() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfaceCopyParts::copySurface(const wordList& patches, triSurf& s) const +{ + boolList copyFacets(surf_.size(), false); + + markFacetsForCopying(patches, copyFacets); + + copySurfaceMesh(copyFacets, s); +} + +triSurf* triSurfaceCopyParts::copySurface(const wordList& patches) const +{ + boolList copyFacets(surf_.size(), false); + + markFacetsForCopying(patches, copyFacets); + + triSurf* sPtr = new triSurf(); + + copySurfaceMesh(copyFacets, *sPtr); + + return sPtr; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCopyParts/triSurfaceCopyParts.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceCopyParts/triSurfaceCopyParts.H new file mode 100644 index 0000000000000000000000000000000000000000..56f9773674aa1e8ad48284e61ca2d5beaa5cfad3 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCopyParts/triSurfaceCopyParts.H @@ -0,0 +1,98 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfaceCopyParts + +Description + Copies user-selected surface parts into a new surface mesh + +SourceFiles + triSurfaceCopyParts.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfaceCopyParts_H +#define triSurfaceCopyParts_H + +#include "triSurf.H" +#include "boolList.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +/*---------------------------------------------------------------------------*\ + Class triSurfaceCopyParts Declaration +\*---------------------------------------------------------------------------*/ + +class triSurfaceCopyParts +{ + // Private data + //- reference to triSurf + const triSurf& surf_; + + // Private member functions + //- mark facets which shall be copied + void markFacetsForCopying(const wordList&, boolList&) const; + + //- copies data to a new surface mesh + void copySurfaceMesh(const boolList&, triSurf&) const; + + //- Disallow default bitwise copy construct + triSurfaceCopyParts(const triSurfaceCopyParts&); + + //- Disallow default bitwise assignment + void operator=(const triSurfaceCopyParts&); + +public: + + // Constructors + + //- Construct from octree + triSurfaceCopyParts(const triSurf& surface); + + // Destructor + + ~triSurfaceCopyParts(); + + + // Member Functions + + //- copies selected patches/subsets to an already created mesh + void copySurface(const wordList&, triSurf&) const; + + //- creates a new surface mesh and copies selected patches/subsets + triSurf* copySurface(const wordList&) const; +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.C index ff5b8c694b623e57410c89b382851cbb0d8de1b7..450e803870aaa845000a7e2ac8c079b3fe272dd5 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -33,7 +32,6 @@ Description # ifdef DEBUGMorph #include <sstream> -#include "writeMeshEnsight.H" # endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -45,7 +43,7 @@ namespace Foam triSurfaceCurvatureEstimator::triSurfaceCurvatureEstimator ( - const triSurface& surface + const triSurf& surface ) : surface_(surface), diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.H index df51895d05d5302a80c7b81bf8c7c517e79ea6b8..63c4651a701da531d98e679a27c71d2c27839948 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.H +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimator.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triSurfaceCurvatureCalculator Description Provides information regarding surface partitions on the surface - triangulation, and connectivity between various surface partitions. + triangulation, and connectivity between various surface partitions. SourceFiles triSurfaceCurvatureEstimator.C @@ -37,7 +36,7 @@ SourceFiles #ifndef triSurfaceCurvatureEstimator_H #define triSurfaceCurvatureEstimator_H -#include "triSurface.H" +#include "triSurf.H" #include "FRWGraph.H" #include "DynList.H" @@ -54,7 +53,7 @@ class triSurfaceCurvatureEstimator { // Private data //- reference to triSurface - const triSurface& surface_; + const triSurf& surface_; //- curvature of points at feature edges scalarField edgePointCurvature_; @@ -95,7 +94,7 @@ public: // Constructors //- Construct from triSurface - triSurfaceCurvatureEstimator(const triSurface& surface); + triSurfaceCurvatureEstimator(const triSurf& surface); // Destructor diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimatorCalculate.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimatorCalculate.C index 1d98ae56ff0f65e59689eb991efd4722f6f1a224..824db3c72fee40e5ff5a2530f26e45f7a9f53556 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimatorCalculate.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceCurvatureEstimator/triSurfaceCurvatureEstimatorCalculate.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,12 +29,17 @@ Description #include "matrix3D.H" #include "quadricFitting.H" #include "HashSet.H" - +#include "boolList.H" +#include "Map.H" #include "DynList.H" #include "OFstream.H" +#include <map> + +# ifdef USE_OMP #include <omp.h> +# endif //#define DEBUGCurvatureEstimator @@ -49,7 +53,7 @@ namespace Foam void writeSurfaceToVTK ( OFstream& file, - const triSurface& surf + const triSurf& surf ) { //- write the header @@ -59,7 +63,7 @@ void writeSurfaceToVTK file << "DATASET POLYDATA\n"; //- write points - const pointField& points = surf.localPoints(); + const pointField& points = surf.points(); file << "POINTS " << points.size() << " float\n"; forAll(points, pI) { @@ -84,7 +88,7 @@ void writeSurfaceToVTK void writeSurfaceToVTK ( const word& name, - const triSurface& surf, + const triSurf& surf, const List<DynList<scalar, 1> >& data ) { @@ -93,7 +97,7 @@ void writeSurfaceToVTK writeSurfaceToVTK(file, surf); //- write curvature fields - const pointField& points = surf.localPoints(); + const pointField& points = surf.points(); file << "\n"; file << "\nPOINT_DATA " << points.size() << "\n"; @@ -111,7 +115,7 @@ void writeSurfaceToVTK void writeSurfaceToVTK ( const word& name, - const triSurface& surf, + const triSurf& surf, const List<DynList<vector, 1> >& data ) { @@ -120,7 +124,7 @@ void writeSurfaceToVTK writeSurfaceToVTK(file, surf); //- write curvature fields - const pointField& points = surf.localPoints(); + const pointField& points = surf.points(); file << "\n"; file << "\nPOINT_DATA " << points.size() << "\n"; @@ -139,32 +143,40 @@ void writeSurfaceToVTK void triSurfaceCurvatureEstimator::calculateEdgeCurvature() { - const pointField& points = surface_.localPoints(); - const edgeList& edges = surface_.edges(); - const labelListList& pointEdges = surface_.pointEdges(); - const labelListList& edgeFaces = surface_.edgeFaces(); + const pointField& points = surface_.points(); + const edgeLongList& edges = surface_.edges(); + const VRWGraph& pointEdges = surface_.pointEdges(); + const VRWGraph& edgeFaces = surface_.edgeFacets(); edgePointCurvature_.setSize(points.size()); boolList featureEdge(edges.size()); + # ifdef USE_OMP # pragma omp parallel + # endif { + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(edgePointCurvature_, i) edgePointCurvature_[i] = 0.0; //- mark feature edges + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(edgeFaces, eI) { - const labelList& eFaces = edgeFaces[eI]; - if( eFaces.size() != 2 ) + if( edgeFaces.sizeOfRow(eI) != 2 ) { featureEdge[eI] = false; continue; } - if( surface_[eFaces[0]].region() == surface_[eFaces[1]].region() ) + if( + surface_[edgeFaces(eI, 0)].region() == + surface_[edgeFaces(eI, 1)].region() + ) { featureEdge[eI] = false; } @@ -174,20 +186,23 @@ void triSurfaceCurvatureEstimator::calculateEdgeCurvature() } } + # ifdef USE_OMP # pragma omp barrier + # endif //- loop through the points and calculate the curvature for points //- attached to two feature edges + # ifdef USE_OMP # pragma omp for schedule(dynamic, 20) + # endif forAll(pointEdges, pI) { - const labelList& pEdges = pointEdges[pI]; - DynList<label> features; - forAll(pEdges, peI) + forAllRow(pointEdges, pI, peI) { - if( featureEdge[pEdges[peI]] ) - features.append(pEdges[peI]); + const label edgeI = pointEdges(pI, peI); + if( featureEdge[edgeI] ) + features.append(edgeI); } if( features.size() == 2 ) @@ -215,10 +230,11 @@ void triSurfaceCurvatureEstimator::calculateEdgeCurvature() void triSurfaceCurvatureEstimator::calculateSurfaceCurvatures() { - const labelListList& pointTriangles = surface_.pointFaces(); - const pointField& points = surface_.localPoints(); - const labelListList& pointEdges = surface_.pointEdges(); - const edgeList& edges = surface_.edges(); + const VRWGraph& pointTriangles = surface_.pointFacets(); + + const pointField& points = surface_.points(); + const VRWGraph& pointEdges = surface_.pointEdges(); + const edgeLongList& edges = surface_.edges(); patchPositions_.setSize(surface_.size()); gaussianCurvature_.setSize(points.size()); @@ -230,24 +246,31 @@ void triSurfaceCurvatureEstimator::calculateSurfaceCurvatures() List<DynList<label, 4> > pointPatches(points.size()); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(pointTriangles, pointI) { - const labelList& pTriangles = pointTriangles[pointI]; - - Map<DynList<label> > regionTriangles; + std::map<label, DynList<label> > regionTriangles; Map<labelHashSet> otherLabels; Map<vector> normals; - forAll(pTriangles, ptI) + forAllRow(pointTriangles, pointI, ptI) { - const label triI = pTriangles[ptI]; + const label triI = pointTriangles(pointI, ptI); const label regionI = surface_[triI].region(); if( !normals.found(regionI) ) normals.insert(regionI, vector::zero); - if( !regionTriangles.found(regionI) ) - regionTriangles.insert(regionI, DynList<label>()); + if( regionTriangles.find(regionI) != regionTriangles.end() ) + regionTriangles.insert + ( + std::make_pair + ( + regionI, + DynList<label>() + ) + ); if( !otherLabels.found(regionI) ) otherLabels.insert(regionI, labelHashSet()); @@ -273,7 +296,7 @@ void triSurfaceCurvatureEstimator::calculateSurfaceCurvatures() forAllConstIter(labelHashSet, currLabels, lit) { const label neiPointI = lit.key(); - const labelList& pEdges = pointEdges[neiPointI]; + const constRow pEdges = pointEdges[neiPointI]; forAll(pEdges, peI) { @@ -317,6 +340,7 @@ void triSurfaceCurvatureEstimator::calculateSurfaceCurvatures() forAll(rTriangles, i) { const label tI = rTriangles[i]; + label pos(-1); forAll(surface_[tI], j) if( surface_[tI][j] == pointI ) @@ -357,14 +381,18 @@ void triSurfaceCurvatureEstimator::calculateSurfaceCurvatures() List<DynList<scalar, 1> > smoothMinCurv(points.size()); List<DynList<scalar, 1> > smoothMaxCurv(points.size()); + # ifdef USE_OMP # pragma omp parallel + # endif { for(label iteration=0;iteration<2;++iteration) { + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(pointEdges, pointI) { - const labelList& pEdges = pointEdges[pointI]; + const constRow pEdges = pointEdges[pointI]; //- find neighbouring points for each patch Map<DynList<label> > patchNeiPoints; @@ -434,9 +462,11 @@ void triSurfaceCurvatureEstimator::calculateSurfaceCurvatures() } } + # ifdef USE_OMP # pragma omp barrier # pragma omp for schedule(static, 1) + # endif forAll(minCurvature_, pointI) { forAll(minCurvature_[pointI], i) @@ -447,10 +477,14 @@ void triSurfaceCurvatureEstimator::calculateSurfaceCurvatures() } } + # ifdef USE_OMP # pragma omp barrier + # endif //- update Gaussian and mean curvatures + # ifdef USE_OMP # pragma omp for schedule(static, 1) + # endif forAll(minCurvature_, pointI) { const DynList<scalar, 1>& minCurv = minCurvature_[pointI]; @@ -493,7 +527,7 @@ void triSurfaceCurvatureEstimator::calculateGaussianCurvature() } } - const pointField& points = surface_.localPoints(); + const pointField& points = surface_.points(); const labelListList& pointTriangles = surface_.pointFaces(); forAll(surface_, triI) @@ -597,7 +631,7 @@ void triSurfaceCurvatureEstimator::calculateGaussianCurvature() void triSurfaceCurvatureEstimator::calculateMeanCurvature() { - const pointField& points = surface_.localPoints(); + const pointField& points = surface_.points(); meanCurvature_.setSize(surface_.patches().size()); diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.C index bc836271294bae9ab5872e2e2ca970407fdafb0c..05a53196880c7490e6becce589d8c59c35b0c5f4 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,6 +28,7 @@ Description #include "triSurfaceDetectFeatureEdges.H" #include "helperFunctions.H" #include "demandDrivenData.H" +#include "triSurfModifier.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -39,29 +39,23 @@ namespace Foam triSurfaceDetectFeatureEdges::triSurfaceDetectFeatureEdges ( - const triSurf& surface, + triSurf& surface, const scalar angleDeviation ) : surf_(surface), featureEdges_(surf_.edges().size(), direction(0)), - angleTolerance_(angleDeviation), - facetInPatch_(), - nPatches_(), - newPatchNames_(), - newPatchTypes_() + angleTolerance_(angleDeviation) { if( Pstream::parRun() ) - FatalError << "Material detection does not run in parallel" + FatalError << "Feature edges detection does not run in parallel" << exit(FatalError); detectFeatureEdgesAngleCriterion(); detectFeatureEdgesPointAngleCriterion(); - detectOuterBoundariesOfPlanarRegions(); - - createPatches(); + //detectOuterBoundariesOfPlanarRegions(); } triSurfaceDetectFeatureEdges::~triSurfaceDetectFeatureEdges() @@ -69,113 +63,18 @@ triSurfaceDetectFeatureEdges::~triSurfaceDetectFeatureEdges() // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void triSurfaceDetectFeatureEdges::detectedSurfaceRegions -( - VRWGraph& graph -) const -{ - graph.setSize(nPatches_); - - labelListPMG nFacetsInPatch(nPatches_, 0); - - forAll(facetInPatch_, triI) - ++nFacetsInPatch[facetInPatch_[triI]]; - - graph.setSizeAndRowSize(nFacetsInPatch); - - nFacetsInPatch = 0; - forAll(facetInPatch_, triI) - { - const label patchI = facetInPatch_[triI]; - - graph(patchI, nFacetsInPatch[patchI]) = triI; - ++nFacetsInPatch[patchI]; - } -} - -const triSurf* triSurfaceDetectFeatureEdges::surfaceWithPatches -( - const word prefix, - const bool forceOverwrite -) const +void triSurfaceDetectFeatureEdges::detectFeatureEdges() { - //- collect patch information - VRWGraph facetsInPatch; - detectedSurfaceRegions(facetsInPatch); + const edgeLongList& edges = surf_.edges(); + triSurfModifier surfMod(surf_); + edgeLongList& featureEdges = surfMod.featureEdgesAccess(); + featureEdges.clear(); - //- create new list of boundary patches - List<labelledTri> newTriangles(facetInPatch_.size()); - label counter(0); - geometricSurfacePatchList newPatches(nPatches_); - - if( forceOverwrite ) - { - forAll(newPatches, patchI) - { - newPatches[patchI].name() = prefix+help::scalarToText(patchI); - newPatches[patchI].geometricType() = "patch"; - newPatches[patchI].index() = patchI; - } - } - else + forAll(featureEdges_, eI) { - forAll(facetsInPatch, patchI) - { - forAllRow(facetsInPatch, patchI, fpI) - { - const label origPatchI = - surf_[facetsInPatch(patchI, fpI)].region(); - newPatches[patchI].name() = - surf_.patches()[origPatchI].name() + - help::scalarToText(patchI); - newPatches[patchI].geometricType() = - surf_.patches()[origPatchI].geometricType(); - newPatches[patchI].index() = patchI; - } - } + if( featureEdges_[eI] ) + featureEdges.append(edges[eI]); } - - //- create triangles for the new surface - labelListPMG newFacetLabel(newTriangles.size(), -1); - - forAll(facetsInPatch, patchI) - forAllRow(facetsInPatch, patchI, tI) - { - newFacetLabel[facetsInPatch(patchI, tI)] = counter; - labelledTri tria = surf_[facetsInPatch(patchI, tI)]; - tria.region() = patchI; - newTriangles[counter++] = tria; - } - - //- update subsets - std::map<word, labelListPMG> newSubsets; - - DynList<word> existingSubsets; - surf_.existingFaceSubsets(existingSubsets); - - forAll(existingSubsets, subsetI) - { - const labelListPMG& subsetFacets = - surf_.facesInSubset(existingSubsets[subsetI]); - - labelListPMG& newSubset = newSubsets[existingSubsets[subsetI]]; - newSubset.setSize(subsetFacets.size()); - - forAll(subsetFacets, tI) - newSubset[tI] = newFacetLabel[subsetFacets[tI]]; - } - - //- create and return thr new surface mesh - triSurf* newSurfPtr = - new triSurf - ( - newTriangles, - newPatches, - surf_.points(), - newSubsets - ); - - return newSurfPtr; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.H index 3a58bcb0d8a6d91a5fdeed68154ca98195364f6d..061426a9f23ae3400299a34b613177be6be58345 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.H +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdges.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triSurfaceDetectFeatureEdges @@ -53,7 +52,7 @@ class triSurfaceDetectFeatureEdges { // Private data //- reference to triSurf - const triSurf& surf_; + triSurf& surf_; //- detected feature edges List<direction> featureEdges_; @@ -61,18 +60,6 @@ class triSurfaceDetectFeatureEdges //- angle tolerance scalar angleTolerance_; - //- surface patches - labelList facetInPatch_; - - //- number of patches - label nPatches_; - - //- patch names - wordList newPatchNames_; - - //- patch types - wordList newPatchTypes_; - // Private member functions //- detect feature edges by check angle between the normals //- of the two neighbouring facets @@ -85,9 +72,6 @@ class triSurfaceDetectFeatureEdges //- detect feature edges at the boundaries of planar regions void detectOuterBoundariesOfPlanarRegions(); - //- create patches bounded by a set of feature edges - void createPatches(); - //- Disallow default bitwise copy construct triSurfaceDetectFeatureEdges(const triSurfaceDetectFeatureEdges&); @@ -101,7 +85,7 @@ public: //- Construct from triSurface and tolerance triSurfaceDetectFeatureEdges ( - const triSurf& surface, + triSurf& surface, const scalar angleDeviation = 45.0 ); @@ -113,14 +97,7 @@ public: // Member Functions //- store regions in a graph - void detectedSurfaceRegions(VRWGraph&) const; - - //- store regions into subsets with a given prefix - const triSurf* surfaceWithPatches - ( - const word prefix = "patch_", - const bool forceOverwrite = false - ) const; + void detectFeatureEdges(); }; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdgesFunctions.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdgesFunctions.C index ac18e87975fc5de2eaf6e6f50c06d3f5d438961e..ee2accbf9d03ab1c27db42a5f7e6827a0ff648d5 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdgesFunctions.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectFeatureEdges/triSurfaceDetectFeatureEdgesFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -30,8 +29,11 @@ Description #include "helperFunctions.H" #include "triSurfaceDetectPlanarRegions.H" #include "demandDrivenData.H" +#include "labelPair.H" +# ifdef USE_OMP #include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -44,25 +46,57 @@ void triSurfaceDetectFeatureEdges::detectFeatureEdgesAngleCriterion() { const scalar tol = Foam::cos(angleTolerance_*M_PI/180.0); - const vectorField& normals = surf_.faceNormals(); + const vectorField& normals = surf_.facetNormals(); - const labelListList& edgeFaces = surf_.edgeFaces(); + const VRWGraph& edgeFaces = surf_.edgeFacets(); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(edgeFaces, edgeI) { - const labelList& eFaces = edgeFaces[edgeI]; + const constRow eFaces = edgeFaces[edgeI]; - if( eFaces.size() != 2 ) + if( edgeFaces.sizeOfRow(edgeI) != 2 ) { featureEdges_[edgeI] |= 8; continue; } - const scalar cosAngle = + scalar cosAngle = (normals[eFaces[0]] & normals[eFaces[1]]) / (mag(normals[eFaces[0]]) * mag(normals[eFaces[1]]) + VSMALL); + //- check the orientation of triangles at this edge + //- check the sign of the angle if the orientation is not consistent + const labelledTri& tri0 = surf_[edgeFaces(edgeI, 0)]; + const labelledTri& tri1 = surf_[edgeFaces(edgeI, 1)]; + DynList<labelPair> sharedIndices; + forAll(tri0, i) + { + forAll(tri1, j) + { + if( tri0[i] == tri1[j] ) + sharedIndices.append(labelPair(i, j)); + } + } + + if( sharedIndices.size() == 2 ) + { + const labelPair& pair0 = sharedIndices[0]; + const labelPair& pair1 = sharedIndices[1]; + if( ((pair0.first() + 1) % 3) == pair1.first() ) + { + if( (pair0.second() + 1) % 3 == pair1.second() ) + cosAngle *= -1.0; + } + else + { + if( (pair1.second() + 1) % 3 == pair0.second() ) + cosAngle *= -1.0; + } + } + if( cosAngle < tol ) featureEdges_[edgeI] |= 1; } @@ -80,18 +114,20 @@ void triSurfaceDetectFeatureEdges::detectOuterBoundariesOfPlanarRegions() VRWGraph planarRegions; dpr.detectedRegions(planarRegions); - labelListPMG facetInPlanarRegion(surf_.size(), -1); + labelLongList facetInPlanarRegion(surf_.size(), -1); forAll(planarRegions, regionI) forAllRow(planarRegions, regionI, rfI) facetInPlanarRegion[planarRegions(regionI, rfI)] = regionI; - const labelListList& edgeFaces = surf_.edgeFaces(); + const VRWGraph& edgeFaces = surf_.edgeFacets(); + # ifdef USE_OMP # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(edgeFaces, edgeI) { - const labelList& eFaces = edgeFaces[edgeI]; + const constRow eFaces = edgeFaces[edgeI]; if( eFaces.size() != 2 ) continue; @@ -101,65 +137,6 @@ void triSurfaceDetectFeatureEdges::detectOuterBoundariesOfPlanarRegions() } } -void triSurfaceDetectFeatureEdges::createPatches() -{ - nPatches_ = 0; - facetInPatch_.setSize(surf_.size()); - facetInPatch_ = -1; - - const labelListList& faceEdges = surf_.faceEdges(); - const labelListList& edgeFaces = surf_.edgeFaces(); - - forAll(facetInPatch_, triI) - { - if( facetInPatch_[triI] != -1 ) - continue; - - labelListPMG front; - front.append(triI); - facetInPatch_[triI] = nPatches_; - - while( front.size() ) - { - const label fLabel = front.removeLastElement(); - - const labelList& fEdges = faceEdges[fLabel]; - - forAll(fEdges, feI) - { - const label edgeI = fEdges[feI]; - - //- check if th edges is marked as a feature edge - if( featureEdges_[edgeI] ) - continue; - - const labelList& eFaces = edgeFaces[edgeI]; - - //- stop at non-manifold edges - if( eFaces.size() != 2 ) - continue; - - label neiTri = eFaces[0]; - if( neiTri == fLabel ) - neiTri = eFaces[1]; - - //- do not overwrite existing patch information - if( surf_[fLabel].region() != surf_[neiTri].region() ) - continue; - if( facetInPatch_[neiTri] != -1 ) - continue; - - facetInPatch_[neiTri] = nPatches_; - front.append(neiTri); - } - } - - ++nPatches_; - } - - Info << "Created " << nPatches_ << " surface patches" << endl; -} - // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // } // End namespace Foam diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.C index 63612957a02fa0d80547e4cd5c24049f20701eba..e772aaf486a1c22a692e80388083740923721c1a 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -39,7 +38,7 @@ namespace Foam triSurfaceDetectMaterials::triSurfaceDetectMaterials(const triSurf& surface) : - surf_(surface), + surf_(surface), octreePtr_(NULL), facePartition_(), nPartitions_(), @@ -117,7 +116,7 @@ void triSurfaceDetectMaterials::writeMaterials(const fileName& fName) const Info << "Partition " << partI << " is an enclosed baffle" << endl; } } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // } // End namespace Foam diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.H index dc1e3a37864b76bdf18137acb3c231ab0edf040e..59fbac84de750ca3e38004ec74611baf86b7ed77 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.H +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterials.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triSurfaceDetectMaterials Description Provides information regarding surface partitions on the surface - triangulation, and connectivity between various surface partitions. + triangulation, and connectivity between various surface partitions. SourceFiles triSurfaceDetectMaterials.C @@ -55,7 +54,7 @@ class meshOctree; class triSurfaceDetectMaterials { // Private data - //- reference to triSurf + //- reference to triSurf const triSurf& surf_; //- pointer to the octree @@ -78,9 +77,9 @@ class triSurfaceDetectMaterials List<direction> partitionType_; // Private member functions - //- create partitioning + //- create partitioning void createPartitions(); - + //- create the octree void createOctree(); @@ -118,7 +117,7 @@ public: // Member Functions - + //- detect surface parts belonging to different materials void detectMaterialsAndInternalWalls(); diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsFunctions.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsFunctions.C index 5479084e03459cfad3c6512a830cddc0d7d1c898..b98c1c577f05aca68bc6c4367a911c8a214ea13a 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsFunctions.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsFunctions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,7 +34,6 @@ Description //#define DEBUGMaterials # ifdef DEBUGMaterials -#include "writeOctreeEnsight.H" #include "helperFunctions.H" # endif @@ -52,8 +50,8 @@ void triSurfaceDetectMaterials::createPartitions() facePartition_ = -1; nPartitions_ = 0; - const labelListList& faceEdges = surf_.faceEdges(); - const labelListList& edgeFaces = surf_.edgeFaces(); + const VRWGraph& faceEdges = surf_.facetEdges(); + const VRWGraph& edgeFaces = surf_.edgeFacets(); forAll(surf_, triI) { @@ -61,24 +59,23 @@ void triSurfaceDetectMaterials::createPartitions() continue; facePartition_[triI] = nPartitions_; - labelListPMG front; + labelLongList front; front.append(triI); while( front.size() ) { const label fLabel = front.removeLastElement(); - const labelList& fEdges = faceEdges[fLabel]; - forAll(fEdges, feI) + forAllRow(faceEdges, fLabel, feI) { - const label edgeI = fEdges[feI]; + const label edgeI = faceEdges(fLabel, feI); - if( edgeFaces[edgeI].size() != 2 ) + if( edgeFaces.sizeOfRow(edgeI) != 2 ) continue; - label nei = edgeFaces[edgeI][0]; + label nei = edgeFaces(edgeI, 0); if( nei == fLabel ) - nei = edgeFaces[edgeI][1]; + nei = edgeFaces(edgeI, 1); if( facePartition_[nei] == -1 ) { @@ -115,12 +112,12 @@ void triSurfaceDetectMaterials::createOctree() if( !octreePtr_ ) octreePtr_ = new meshOctree(surf_); - const edgeList& edges = surf_.edges(); + const edgeLongList& edges = surf_.edges(); if( edges.size() == 0 ) FatalError << "Surface mesh has no edges!!" << exit(FatalError); - const pointField& points = surf_.localPoints(); + const pointField& points = surf_.points(); scalar averageLength(0.0), minLength(VGREAT); forAll(edges, eI) @@ -181,7 +178,7 @@ void triSurfaceDetectMaterials::createOctree() //- refine coarse boxes. This is performed by refinining octree boxes //- containing more than one partition in its vicinity const boundBox& rootBox = octreePtr_->rootBox(); - const labelListList& pointTriangles = surf_.pointFaces(); + const VRWGraph& pointTriangles = surf_.pointFacets(); DynList<const meshOctreeCube*, 256> neis; do @@ -230,7 +227,7 @@ void triSurfaceDetectMaterials::createOctree() //- check if there exist any corners or edges in the boundBox forAllConstIter(labelHashSet, containedPts, pIter) { - const labelList& pTriangles = pointTriangles[pIter.key()]; + const constRow pTriangles = pointTriangles[pIter.key()]; labelHashSet partitions; forAll(pTriangles, i) @@ -297,10 +294,6 @@ void triSurfaceDetectMaterials::createOctree() Info << "Number of INSIDE leaves " << nInside << endl; Info << "Number of OUTSIDE leaves " << nOutside << endl; Info << "Number of UNKNOWN leaves " << nUnknown << endl; - - # ifdef DEBUGMaterials - writeOctreeEnsight(*octreePtr_, "refinedOctree", meshOctreeCubeBasic::DATA); - # endif } void triSurfaceDetectMaterials::refineOctree() @@ -351,7 +344,7 @@ void triSurfaceDetectMaterials::findOctreeGroups() octreeGroupForBox_ = -1; nOctreeGroups_ = 0; - DynList<label> neighs(24); + DynList<label> neighs; for(label leafI=0;leafI<nLeaves;++leafI) { if( octreeGroupForBox_[leafI] != -1 ) @@ -361,7 +354,7 @@ void triSurfaceDetectMaterials::findOctreeGroups() if( octreePtr_->hasContainedTriangles(leafI) ) continue; - labelListPMG front; + labelLongList front; octreeGroupForBox_[leafI] = nOctreeGroups_; front.append(leafI); @@ -407,7 +400,7 @@ void triSurfaceDetectMaterials::findMaterialsAndWalls() partitionType_ = 0; const label nLeaves = octreePtr_->numberOfLeaves(); - DynList<label> containedTriangles(64), neighbours(24); + DynList<label> containedTriangles, neighbours; for(label leafI=0;leafI<nLeaves;++leafI) { //const meshOctreeCubeBasic& oc = octreePtr_->returnLeaf(leafI); @@ -567,7 +560,7 @@ void triSurfaceDetectMaterials::findMaterialsAndWalls() //- renumber partitionMaterials_ according to newGroupLabels forAll(partitionMaterials_, partitionI) { - DynList<label> partitions(partitionMaterials_.sizeOfRow(partitionI)); + DynList<label> partitions; forAllRow(partitionMaterials_, partitionI, i) partitions.appendIfNotIn ( diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsI.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsI.H index afc93ab944eff47a362b60a74ef6a9d748b956b4..593eeda9dbbf1ecfabdbecdeb43d3b29deb1f384 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsI.H +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectMaterials/triSurfaceDetectMaterialsI.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.C index 7a8e7874a0e44bf412958b02f4c40b48ce795e9a..e286b0f778c5bfd8a4206b32b39c28600e29dd82 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -46,9 +45,9 @@ void triSurfaceDetectPlanarRegions::checkPlanarRegions() const scalar cosTol = Foam::cos(tol_); - const vectorField& normals = surf_.faceNormals(); - const labelListList& faceEdges = surf_.faceEdges(); - const labelListList& edgeFaces = surf_.edgeFaces(); + const vectorField& normals = surf_.facetNormals(); + const VRWGraph& faceEdges = surf_.facetEdges(); + const VRWGraph& edgeFaces = surf_.edgeFacets(); forAll(planarRegion_, triI) { @@ -60,7 +59,7 @@ void triSurfaceDetectPlanarRegions::checkPlanarRegions() n /= mag(n); planarRegion_[triI] = nRegions_; - labelListPMG front; + labelLongList front; front.append(triI); label nFacetsInRegion(1); @@ -68,19 +67,16 @@ void triSurfaceDetectPlanarRegions::checkPlanarRegions() { const label fLabel = front.removeLastElement(); - const labelList& fEdges = faceEdges[fLabel]; - forAll(fEdges, feI) + forAllRow(faceEdges, fLabel, feI) { - const label edgeI = fEdges[feI]; + const label edgeI = faceEdges(fLabel, feI); - const labelList& eFaces = edgeFaces[edgeI]; - - if( eFaces.size() != 2 ) + if( edgeFaces.sizeOfRow(edgeI) != 2 ) continue; - forAll(eFaces, efI) + forAllRow(edgeFaces, edgeI, efI) { - const label fNei = eFaces[efI]; + const label fNei = edgeFaces(edgeI, efI); if( planarRegion_[fNei] != -1 ) continue; @@ -168,7 +164,7 @@ void triSurfaceDetectPlanarRegions::detectedRegions(VRWGraph& graph) const void triSurfaceDetectPlanarRegions::detectedRegions(const word prefix) const { - List<labelListPMG> facetsInRegion(nRegions_); + List<labelLongList> facetsInRegion(nRegions_); forAll(planarRegion_, triI) { if( planarRegion_[triI] == -1 ) @@ -180,11 +176,11 @@ void triSurfaceDetectPlanarRegions::detectedRegions(const word prefix) const for(label regionI=0;regionI<nRegions_;++regionI) { const word subsetName = prefix+help::scalarToText(regionI); - const_cast<triSurf&>(surf_).addFacetsToSubset - ( - subsetName, - facetsInRegion[regionI] - ); + + triSurf& surf = const_cast<triSurf&>(surf_); + const label subsetID = surf.addFacetSubset(subsetName); + forAll(facetsInRegion[regionI], fI) + surf.addFacetToSubset(subsetID, facetsInRegion[regionI][fI]); } } diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.H index 4e990a091f4e0210c56590aa3992eaecc4635e51..3c8acbe9abbc2f770523bbd8ceb0a4428e12e4c3 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.H +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceDetectPlanarRegions/triSurfaceDetectPlanarRegions.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triSurfaceDetectPlanarRegions diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceExtrude2DEdges/triSurfaceExtrude2DEdges.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceExtrude2DEdges/triSurfaceExtrude2DEdges.C new file mode 100644 index 0000000000000000000000000000000000000000..dfac3955f31da9e711529f967fce52773037bd95 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceExtrude2DEdges/triSurfaceExtrude2DEdges.C @@ -0,0 +1,111 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfaceExtrude2DEdges.H" +#include "triSurfModifier.H" +#include "boundBox.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfaceExtrude2DEdges::triSurfaceExtrude2DEdges(const triSurf& surface) +: + surf_(surface) +{} + +triSurfaceExtrude2DEdges::~triSurfaceExtrude2DEdges() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfaceExtrude2DEdges::extrudeSurface(triSurf& newSurf) const +{ + triSurfModifier sMod(newSurf); + + //- set patches + geometricSurfacePatchList& patches = sMod.patchesAccess(); + + patches.setSize(1); + patches[0].name() = "patch0"; + patches[0].geometricType() = "patch"; + + //- check if the edges are in the x-y plane + const pointField& sPoints = surf_.points(); + const boundBox bb(sPoints); + + if( Foam::mag(bb.max().z() - bb.min().z()) > SMALL ) + FatalErrorIn + ( + "void triSurfaceExtrude2DEdges::extrudeSurface(triSurf&) const" + ) << "Cannot extrude edges which are not in the x-y plane!" + << exit(FatalError); + + //- copy points + pointField& pts = sMod.pointsAccess(); + pts.setSize(2 * sPoints.size()); + + const label nOffset = sPoints.size(); + const scalar zOffset = 0.1 * bb.mag(); + + forAll(sPoints, pI) + { + pts[pI] = pts[pI+nOffset] = sPoints[pI]; + pts[pI+sPoints.size()].z() += zOffset; + } + + //- create triangles from feature edges + LongList<labelledTri>& triangles = sMod.facetsAccess(); + const edgeLongList& edges = surf_.featureEdges(); + + triangles.setSize(2 * edges.size()); + forAll(edges, eI) + { + const edge& e = edges[eI]; + const label tI = 2 * eI; + triangles[tI] = labelledTri(e[0], e[1], e[1]+nOffset, 0); + triangles[tI + 1] = labelledTri(e[0], e[1]+nOffset, e[0]+nOffset, 0); + } +} + +const triSurf* triSurfaceExtrude2DEdges::extrudeSurface() const +{ + triSurf* sPtr = new triSurf(); + + extrudeSurface(*sPtr); + + return sPtr; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceExtrude2DEdges/triSurfaceExtrude2DEdges.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceExtrude2DEdges/triSurfaceExtrude2DEdges.H new file mode 100644 index 0000000000000000000000000000000000000000..51a34d255930aaef9e0cfaf17f1c629331319b50 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceExtrude2DEdges/triSurfaceExtrude2DEdges.H @@ -0,0 +1,92 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfaceExtrude2DEdges + +Description + Extrudes edges in x-y plane into a triangulation used for 2D meshing + +SourceFiles + triSurfaceExtrude2DEdges.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfaceExtrude2DEdges_H +#define triSurfaceExtrude2DEdges_H + +#include "triSurf.H" +#include "boolList.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +/*---------------------------------------------------------------------------*\ + Class triSurfaceExtrude2DEdges Declaration +\*---------------------------------------------------------------------------*/ + +class triSurfaceExtrude2DEdges +{ + // Private data + //- reference to triSurf + const triSurf& surf_; + + // Private member functions + + //- Disallow default bitwise copy construct + triSurfaceExtrude2DEdges(const triSurfaceExtrude2DEdges&); + + //- Disallow default bitwise assignment + void operator=(const triSurfaceExtrude2DEdges&); + +public: + + // Constructors + + //- Construct from octree + triSurfaceExtrude2DEdges(const triSurf& surface); + + // Destructor + + ~triSurfaceExtrude2DEdges(); + + + // Member Functions + + //- extrudes edges into a triangulation + void extrudeSurface(triSurf&) const; + + const triSurf* extrudeSurface() const; +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceMetaData/triSurfaceMetaData.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceMetaData/triSurfaceMetaData.C new file mode 100644 index 0000000000000000000000000000000000000000..2b7528ce475a72d4d2f678d2df0e2ea640baad8b --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceMetaData/triSurfaceMetaData.C @@ -0,0 +1,136 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfaceMetaData.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfaceMetaData::createMetaData() +{ + metaDict_.clear(); + + metaDict_.add("nPoints", surf_.points().size()); + metaDict_.add("nFacets", surf_.facets().size()); + metaDict_.add("nPatches", surf_.patches().size()); + metaDict_.add("nFeatureEdges", surf_.featureEdges().size()); + + dictionary dict; + + //- store nformation about surface patches + labelList nInPatch(surf_.patches().size(), 0); + forAll(surf_, triI) + ++nInPatch[surf_[triI].region()]; + + forAll(surf_.patches(), patchI) + { + const geometricSurfacePatch& patch = surf_.patches()[patchI]; + + dictionary pDict; + pDict.add("type", patch.geometricType()); + pDict.add("nFacets", nInPatch[patchI]); + + dict.add(patch.name(), pDict); + } + + metaDict_.add("patches", dict); + + //- store information about point subsets + DynList<label> subsetIds; + surf_.pointSubsetIndices(subsetIds); + dict.clear(); + forAll(subsetIds, i) + { + dictionary sDict; + + labelLongList inSubset; + surf_.pointsInSubset(subsetIds[i], inSubset); + sDict.add("nPoints", inSubset.size()); + + dict.add(surf_.pointSubsetName(subsetIds[i]), sDict); + } + + metaDict_.add("pointSubsets", dict); + + //- store information about facet subsets + subsetIds.clear(); + surf_.facetSubsetIndices(subsetIds); + dict.clear(); + forAll(subsetIds, i) + { + dictionary sDict; + + labelLongList inSubset; + surf_.facetsInSubset(subsetIds[i], inSubset); + sDict.add("nFacets", inSubset.size()); + + dict.add(surf_.facetSubsetName(subsetIds[i]), sDict); + } + + metaDict_.add("facetSubsets", dict); + + //- store information about feature edge subsets + subsetIds.clear(); + surf_.edgeSubsetIndices(subsetIds); + dict.clear(); + forAll(subsetIds, i) + { + dictionary sDict; + + labelLongList inSubset; + surf_.edgesInSubset(subsetIds[i], inSubset); + sDict.add("nEdges", inSubset.size()); + + dict.add(surf_.edgeSubsetName(subsetIds[i]), sDict); + } + + metaDict_.add("featureEdgeSubsets", dict); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfaceMetaData::triSurfaceMetaData(const triSurf& surface) +: + surf_(surface), + metaDict_() +{ + createMetaData(); +} + +triSurfaceMetaData::~triSurfaceMetaData() +{} + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceMetaData/triSurfaceMetaData.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceMetaData/triSurfaceMetaData.H new file mode 100644 index 0000000000000000000000000000000000000000..9649d7011df7649afe9f281dca3719db7392fae0 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceMetaData/triSurfaceMetaData.H @@ -0,0 +1,103 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfaceMetaData + +Description + Generates meta data of the surface mesh. It contains: + The number of points + The number of triangles + The number of patches + The number of feature edges + The number of subsets, names, and the number of elements in each subset + +SourceFiles + triSurfaceMetaData.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfaceMetaData_H +#define triSurfaceMetaData_H + +#include "triSurf.H" +#include "dictionary.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +/*---------------------------------------------------------------------------*\ + Class triSurfaceMetaData Declaration +\*---------------------------------------------------------------------------*/ + +class triSurfaceMetaData +{ + // Private data + //- const reference to triSurf + const triSurf& surf_; + + //- patches/subsets for removal + dictionary metaDict_; + + // Private member functions + //- create dictionary with meta data + void createMetaData(); + + //- Disallow default bitwise copy construct + triSurfaceMetaData(const triSurfaceMetaData&); + + //- Disallow default bitwise assignment + void operator=(const triSurfaceMetaData&); + +public: + + // Constructors + + //- Construct from triSurf + triSurfaceMetaData(const triSurf& surface); + + // Destructor + + ~triSurfaceMetaData(); + + + // Member Functions + + //- return a constant reference to meta data + const dictionary& metaData() const + { + return metaDict_; + } +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.C b/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.C index 19933881e5f95f3dde43b34d35800633488722e7..d680e63c74793a89606438f9183f1647ac528cf2 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -29,11 +28,8 @@ Description #include "triSurfacePartitioner.H" #include "demandDrivenData.H" -//#define DEBUGMorph - -# ifdef DEBUGMorph +# ifdef DEBUGPartitioner #include <sstream> -#include "writeMeshEnsight.H" # endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -45,19 +41,19 @@ namespace Foam triSurfacePartitioner::triSurfacePartitioner ( - const triSurface& surface + const triSurf& surface ) : - surface_(surface), + surface_(surface), corners_(), - cornerPatches_(), - partitionPartitions_(surface.patches().size()), - edgePartitions_(), - edgePartitionEdgePartitions_(), - partitionsEdgeParts_(), - edgePartitionsCorners_() + cornerPatches_(), + patchPatches_(surface.patches().size()), + edgeGroups_(), + edgeGroupEdgeGroups_(), + patchesEdgeGroups_(), + edgeGroupsCorners_() { - calculatePartitionAddressing(); + calculatePatchAddressing(); } triSurfacePartitioner::~triSurfacePartitioner() @@ -67,84 +63,83 @@ triSurfacePartitioner::~triSurfacePartitioner() const labelList& triSurfacePartitioner::corners() const { - return corners_; + return corners_; } const List<DynList<label> >& triSurfacePartitioner::cornerPatches() const { - return cornerPatches_; + return cornerPatches_; } -const List<labelHashSet>& triSurfacePartitioner::partitionPartitions() const +const List<labelHashSet>& triSurfacePartitioner::patchPatches() const { - return partitionPartitions_; + return patchPatches_; } -const labelList& triSurfacePartitioner::edgePartitions() const +const labelList& triSurfacePartitioner::edgeGroups() const { - return edgePartitions_; + return edgeGroups_; } -const List<labelHashSet>& -triSurfacePartitioner::edgePartitionEdgePartitions() const +const List<labelHashSet>& triSurfacePartitioner::edgeGroupEdgeGroups() const { - return edgePartitionEdgePartitions_; + return edgeGroupEdgeGroups_; } -void triSurfacePartitioner::edgePartitionsBetweenPartitions +void triSurfacePartitioner::edgeGroupsSharedByPatches ( - const label partition1, - const label partition2, - DynList<label>& edgePartitions + const label patch1, + const label patch2, + DynList<label>& edgeGroups ) const { - edgePartitions.clear(); - + edgeGroups.clear(); + std::pair<label, label> pp ( - Foam::min(partition1, partition2), - Foam::max(partition1, partition2) + Foam::min(patch1, patch2), + Foam::max(patch1, patch2) ); - + std::map<std::pair<label, label>, labelHashSet>::const_iterator it = - partitionsEdgeParts_.find(pp); - - if( it != partitionsEdgeParts_.end() ) + patchesEdgeGroups_.find(pp); + + if( it != patchesEdgeGroups_.end() ) { - const labelList edgeParts = it->second.toc(); - - forAll(edgeParts, partI) - edgePartitions.append(edgeParts[partI]); + const labelHashSet& eGroups = it->second; + + forAllConstIter(labelHashSet, eGroups, it) + edgeGroups.append(it.key()); } } -void triSurfacePartitioner::cornersBetweenEdgePartitions +void triSurfacePartitioner::cornersSharedByEdgeGroups ( - const label edgePartition1, - const label edgePartition2, + const label edgeGroup1, + const label edgeGroup2, DynList<label>& corners ) const { corners.clear(); - + std::pair<label, label> ep ( - Foam::min(edgePartition1, edgePartition2), - Foam::max(edgePartition1, edgePartition2) + Foam::min(edgeGroup1, edgeGroup2), + Foam::max(edgeGroup1, edgeGroup2) ); - + std::map<std::pair<label, label>, labelHashSet>::const_iterator it = - edgePartitionsCorners_.find(ep); - - if( it != edgePartitionsCorners_.end() ) + edgeGroupsCorners_.find(ep); + + if( it != edgeGroupsCorners_.end() ) { - const labelList corn = it->second.toc(); - - forAll(corn, cornerI) - corners.append(corn[cornerI]); + const labelHashSet& corn = it->second; + + forAllConstIter(labelHashSet, corn, it) + corners.append(it.key()); } } - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // } // End namespace Foam diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.H b/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.H index d9f261a16117fc96fa62a18edbae8296fb526157..b7d4d2fc21fddfdf13e0bf3f4054e8c4315d3613 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.H +++ b/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitioner.H @@ -1,33 +1,32 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class triSurfacePartitioner Description Provides information regarding surface partitions on the surface - triangulation, and connectivity between various surface partitions. + triangulation, and connectivity between various surface partitions. SourceFiles triSurfacePartitioner.C @@ -37,7 +36,7 @@ SourceFiles #ifndef triSurfacePartitioner_H #define triSurfacePartitioner_H -#include "triSurface.H" +#include "triSurf.H" #include "DynList.H" #include "HashSet.H" @@ -55,47 +54,47 @@ namespace Foam class triSurfacePartitioner { // Private data - //- reference to triSurface - const triSurface& surface_; - - //- corner nodes - labelList corners_; - List<DynList<label> > cornerPatches_; - - //- information which partitions share an edge with a given partition - List<labelHashSet> partitionPartitions_; - + //- reference to triSurf + const triSurf& surface_; + + //- corner nodes + labelList corners_; + List<DynList<label> > cornerPatches_; + + //- information which partitions share an edge with a given partition + List<labelHashSet> patchPatches_; + //- edge partitions - labelList edgePartitions_; - - //- information which edge partitions share a corner - //- with a given partition - List<labelHashSet> edgePartitionEdgePartitions_; - - //- partition of the edge between the surface partitions - std::map<std::pair<label, label>, labelHashSet> partitionsEdgeParts_; - - //- corners shared by edge partitions - std::map<std::pair<label, label>, labelHashSet> edgePartitionsCorners_; + labelList edgeGroups_; + + //- information which edge groups share a corner + //- with a given group + List<labelHashSet> edgeGroupEdgeGroups_; + + //- edge groups between surface patches + std::map<std::pair<label, label>, labelHashSet> patchesEdgeGroups_; + + //- corners shared by edge groups + std::map<std::pair<label, label>, labelHashSet> edgeGroupsCorners_; // Private member functions - //- calculate partitions - void calculatePartitionAddressing(); - - //- find surface corners - void calculateCornersAndAddressing(); - - //- calculate partitionPartitions_ addressing - void calculatePartitionPartitions(); - - //- calculate edge partitions - void calculateEdgePartitions(); - - //- calculate surface partition to edge partitions addressing - void calculatePartitionsToEdgePartitions(); - - //- calculate edge partitions to corner addressing - void calculateEdgePartitionsToCorners(); + //- calculate patch addressing + void calculatePatchAddressing(); + + //- find surface corners + void calculateCornersAndAddressing(); + + //- calculate patch-patches addressing + void calculatePatchPatches(); + + //- calculate edge groups + void calculateEdgeGroups(); + + //- calculate surface patch to edge groups addressing + void calculatePatchToEdgeGroups(); + + //- calculate edge groups to corner addressing + void calculateEdgeGroupsToCorners(); //- Disallow default bitwise copy construct triSurfacePartitioner(const triSurfacePartitioner&); @@ -107,8 +106,8 @@ public: // Constructors - //- Construct from triSurface - triSurfacePartitioner(const triSurface& surface); + //- Construct from triSurf + triSurfacePartitioner(const triSurf& surface); // Destructor @@ -116,32 +115,32 @@ public: // Member Functions - //- return corner nodes - const labelList& corners() const; - - //- return corner patches - const List<DynList<label> >& cornerPatches() const; - - //- return partition-partitions addressing - const List<labelHashSet>& partitionPartitions() const; - - //- return edge partitions. Partitions of edges which are not - //- the feature edges is set to -1 - const labelList& edgePartitions() const; - - //- Edge partition - edge partitions addressing - const List<labelHashSet>& edgePartitionEdgePartitions() const; - - //- Return partitions of feature edges between the given partitions - void edgePartitionsBetweenPartitions + //- return corner nodes + const labelList& corners() const; + + //- return corner patches + const List<DynList<label> >& cornerPatches() const; + + //- return patch-patches addressing + const List<labelHashSet>& patchPatches() const; + + //- return edge groups. Edges which are not + //- feature edges are set to -1 + const labelList& edgeGroups() const; + + //- Edge group - edge groups addressing + const List<labelHashSet>& edgeGroupEdgeGroups() const; + + //- Return groups of feature edges shared by the given patches + void edgeGroupsSharedByPatches ( const label partition1, const label partition2, DynList<label>& edgePartitions ) const; - - //- return corners shared between the given edge partitions - void cornersBetweenEdgePartitions + + //- return corners shared shared by the given edge groups + void cornersSharedByEdgeGroups ( const label edgePartition1, const label edgePartition2, diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitionerCreateAddressing.C b/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitionerCreateAddressing.C index ed56edc8832d2cdc8e6d572c74d93acdde199706..712ab504b3286183ae9c4eff442adfd914e59774 100644 --- a/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitionerCreateAddressing.C +++ b/meshLibrary/utilities/triSurfaceTools/triSurfacePartitioner/triSurfacePartitionerCreateAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -28,7 +27,12 @@ Description #include "triSurfacePartitioner.H" #include "demandDrivenData.H" -#include "labelListPMG.H" +#include "labelLongList.H" +#include "boolList.H" + +# ifdef USE_OMP +#include <omp.h> +# endif // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -37,36 +41,35 @@ namespace Foam // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void triSurfacePartitioner::calculatePartitionAddressing() +void triSurfacePartitioner::calculatePatchAddressing() { - calculateCornersAndAddressing(); - - calculatePartitionPartitions(); - - calculateEdgePartitions(); - - calculatePartitionsToEdgePartitions(); - - calculateEdgePartitionsToCorners(); + calculateCornersAndAddressing(); + + calculatePatchPatches(); + + calculateEdgeGroups(); + + calculatePatchToEdgeGroups(); + calculateEdgeGroupsToCorners(); } - + void triSurfacePartitioner::calculateCornersAndAddressing() { - const labelListList& pointFaces = surface_.pointFaces(); - const edgeList& edges = surface_.edges(); - const labelListList& edgeFaces = surface_.edgeFaces(); - + const VRWGraph& pointFaces = surface_.pointFacets(); + const edgeLongList& edges = surface_.edges(); + const VRWGraph& edgeFaces = surface_.edgeFacets(); + //- find the number of feature edges connected to each surface node - List<direction> nEdgesAtNode(surface_.points().size(), direction(0)); + labelList nEdgesAtNode(surface_.points().size(), 0); forAll(edgeFaces, eI) { - if( edgeFaces[eI].size() != 2 ) + if( edgeFaces.sizeOfRow(eI) != 2 ) continue; - - const label sPatch = surface_[edgeFaces[eI][0]].region(); - const label ePatch = surface_[edgeFaces[eI][1]].region(); - + + const label sPatch = surface_[edgeFaces(eI, 0)].region(); + const label ePatch = surface_[edgeFaces(eI, 1)].region(); + if( sPatch != ePatch ) { const edge& e = edges[eI]; @@ -74,208 +77,211 @@ void triSurfacePartitioner::calculateCornersAndAddressing() ++nEdgesAtNode[e.end()]; } } - + //- count the number of feature edges connected to each surface point //- corners must have 3 or more edges attached to them label nCorners(0); forAll(nEdgesAtNode, pI) { - if( nEdgesAtNode[pI] < direction(3) ) + if( nEdgesAtNode[pI] < 3 ) continue; - + ++nCorners; } - - corners_.setSize(nCorners); - cornerPatches_.setSize(nCorners); - nCorners = 0; - + + corners_.setSize(nCorners); + cornerPatches_.setSize(nCorners); + nCorners = 0; + //- store corner data - DynList<label> patches(10); - forAll(pointFaces, pointI) - { - if( nEdgesAtNode[pointI] < direction(3) ) + DynList<label> patches; + forAll(pointFaces, pointI) + { + if( nEdgesAtNode[pointI] < 3 ) continue; - - const labelList& pf = pointFaces[pointI]; - - patches.clear(); - forAll(pf, pfI) - patches.appendIfNotIn(surface_[pf[pfI]].region()); - + + patches.clear(); + forAllRow(pointFaces, pointI, pfI) + patches.appendIfNotIn(surface_[pointFaces(pointI, pfI)].region()); + corners_[nCorners] = pointI; cornerPatches_[nCorners] = patches; ++nCorners; - } + } } - -void triSurfacePartitioner::calculatePartitionPartitions() + +void triSurfacePartitioner::calculatePatchPatches() { - const labelListList& edgeFaces = surface_.edgeFaces(); - - forAll(edgeFaces, eI) - { - if( edgeFaces[eI].size() != 2 ) - { - Warning << "Surface is not a manifold!!" << endl; - continue; - } - - const label sPatch = surface_[edgeFaces[eI][0]].region(); - const label ePatch = surface_[edgeFaces[eI][1]].region(); - - if( sPatch != ePatch ) - { - partitionPartitions_[sPatch].insert(ePatch); - partitionPartitions_[ePatch].insert(sPatch); - } - } + const VRWGraph& edgeFaces = surface_.edgeFacets(); + + forAll(edgeFaces, eI) + { + if( edgeFaces.sizeOfRow(eI) != 2 ) + { + Warning << "Surface is not a manifold!!" << endl; + continue; + } + + const label sPatch = surface_[edgeFaces(eI, 0)].region(); + const label ePatch = surface_[edgeFaces(eI, 1)].region(); + + if( sPatch != ePatch ) + { + patchPatches_[sPatch].insert(ePatch); + patchPatches_[ePatch].insert(sPatch); + } + } } -void triSurfacePartitioner::calculateEdgePartitions() +void triSurfacePartitioner::calculateEdgeGroups() { - const edgeList& edges = surface_.edges(); - const labelListList& pointEdges = surface_.pointEdges(); - const labelListList& edgeFaces = surface_.edgeFaces(); - + const edgeLongList& edges = surface_.edges(); + const VRWGraph& edgeFaces = surface_.edgeFacets(); + const VRWGraph& pointEdges = surface_.pointEdges(); + + //- make all feature edges boolList featureEdge(edgeFaces.size(), false); - DynList<label> parts(10); + + # ifdef USE_OMP + # pragma omp parallel for schedule(dynamic, 40) + # endif forAll(edgeFaces, eI) { - const labelList& eFaces = edgeFaces[eI]; - - parts.clear(); - forAll(eFaces, efI) - parts.appendIfNotIn(surface_[eFaces[efI]].region()); - - if( parts.size() > 1 ) + DynList<label> patches; + forAllRow(edgeFaces, eI, efI) + patches.appendIfNotIn(surface_[edgeFaces(eI, efI)].region()); + + if( patches.size() > 1 ) featureEdge[eI] = true; } - + //- create a set containing corners for fast searching labelHashSet corners; forAll(corners_, i) corners.insert(corners_[i]); - - edgePartitions_.setSize(edgeFaces. size()); - edgePartitions_ = -1; - - label nPartitions(0); + + edgeGroups_.setSize(edgeFaces.size()); + edgeGroups_ = -1; + + label nGroups(0); forAll(featureEdge, eI) { if( !featureEdge[eI] ) continue; - - labelListPMG front; + if( edgeGroups_[eI] != -1 ) + continue; + + labelLongList front; front.append(eI); - edgePartitions_[eI] = nPartitions; + edgeGroups_[eI] = nGroups; featureEdge[eI] = false; - + while( front.size() ) { const label eLabel = front.removeLastElement(); const edge& e = edges[eLabel]; - + for(label pI=0;pI<2;++pI) { const label pointI = e[pI]; - + if( corners.found(pointI) ) continue; - - const labelList& pEdges = pointEdges[pointI]; - forAll(pEdges, peI) + + forAllRow(pointEdges, pointI, peI) { - const label eJ = pEdges[peI]; - if( featureEdge[eJ] ) + const label eJ = pointEdges(pointI, peI); + + if( featureEdge[eJ] && (edgeGroups_[eJ] == -1) ) { - edgePartitions_[eJ] = nPartitions; + edgeGroups_[eJ] = nGroups; featureEdge[eJ] = false; front.append(eJ); } } } } - - ++nPartitions; + + ++nGroups; } - - Info << nPartitions << " edge partitions found!" << endl; - - edgePartitionEdgePartitions_.clear(); - edgePartitionEdgePartitions_.setSize(nPartitions); + + Info << nGroups << " edge groups found!" << endl; + + edgeGroupEdgeGroups_.clear(); + edgeGroupEdgeGroups_.setSize(nGroups); } -void triSurfacePartitioner::calculatePartitionsToEdgePartitions() +void triSurfacePartitioner::calculatePatchToEdgeGroups() { - const labelListList& edgeFaces = surface_.edgeFaces(); - - DynList<label> partitions(10); + const VRWGraph& edgeFaces = surface_.edgeFacets(); + forAll(edgeFaces, eI) { - if( edgePartitions_[eI] < 0 ) + if( edgeGroups_[eI] < 0 ) continue; - - const labelList& eFaces = edgeFaces[eI]; - - partitions.clear(); - forAll(eFaces, efI) - partitions.appendIfNotIn(surface_[eFaces[efI]].region()); - - forAll(partitions, i) + + DynList<label> patches; + forAllRow(edgeFaces, eI, efI) + patches.appendIfNotIn(surface_[edgeFaces(eI, efI)].region()); + + forAll(patches, i) { - const label partI = partitions[i]; - for(label j=i+1;j<partitions.size();++j) + const label patchI = patches[i]; + + for(label j=i+1;j<patches.size();++j) { - const label partJ = partitions[j]; - + const label patchJ = patches[j]; + const std::pair<label, label> pp ( - Foam::min(partI, partJ), - Foam::max(partI, partJ) + Foam::min(patchI, patchJ), + Foam::max(patchI, patchJ) ); - - partitionsEdgeParts_[pp].insert(edgePartitions_[eI]); + + patchesEdgeGroups_[pp].insert(edgeGroups_[eI]); } } } } -void triSurfacePartitioner::calculateEdgePartitionsToCorners() +void triSurfacePartitioner::calculateEdgeGroupsToCorners() { - const labelListList& pointEdges = surface_.pointEdges(); - + const VRWGraph& pointEdges = surface_.pointEdges(); + forAll(corners_, cornerI) { - DynList<label> edgePartitionsAtCorner(10); - const labelList& pEdges = pointEdges[corners_[cornerI]]; - - forAll(pEdges, peI) - edgePartitionsAtCorner.appendIfNotIn(edgePartitions_[pEdges[peI]]); - - forAll(edgePartitionsAtCorner, i) + DynList<label> edgeGroupsAtCorner; + const label pointI = corners_[cornerI]; + + forAllRow(pointEdges, pointI, peI) + edgeGroupsAtCorner.appendIfNotIn + ( + edgeGroups_[pointEdges(pointI, peI)] + ); + + forAll(edgeGroupsAtCorner, i) { - const label epI = edgePartitionsAtCorner[i]; + const label epI = edgeGroupsAtCorner[i]; if( epI < 0 ) continue; - for(label j=i+1;j<edgePartitionsAtCorner.size();++j) + for(label j=i+1;j<edgeGroupsAtCorner.size();++j) { - const label epJ = edgePartitionsAtCorner[j]; + const label epJ = edgeGroupsAtCorner[j]; if( epJ < 0 ) continue; - + std::pair<label, label> ep ( Foam::min(epI, epJ), Foam::max(epI, epJ) ); - + //- create edgepartition - edge partitions addressing - edgePartitionEdgePartitions_[ep.first].insert(ep.second); - edgePartitionEdgePartitions_[ep.second].insert(ep.first); - - edgePartitionsCorners_[ep].insert(cornerI); + edgeGroupEdgeGroups_[ep.first].insert(ep.second); + edgeGroupEdgeGroups_[ep.second].insert(ep.first); + + edgeGroupsCorners_[ep].insert(cornerI); } } } diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulator.C b/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulator.C new file mode 100644 index 0000000000000000000000000000000000000000..525132bb65eff8eaa79d225f48cc7f6b2c918c62 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulator.C @@ -0,0 +1,238 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfacePatchManipulator.H" +#include "helperFunctions.H" +#include "demandDrivenData.H" +#include "checkMeshDict.H" + +#include <map> + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfacePatchManipulator::triSurfacePatchManipulator(const triSurf& surface) +: + surf_(surface), + featureEdges_(surf_.edges().size(), direction(0)), + facetInPatch_(), + nPatches_(), + newPatchNames_(), + newPatchTypes_() +{ + allocateFeatureEdges(); + + createPatches(); +} + +triSurfacePatchManipulator::~triSurfacePatchManipulator() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfacePatchManipulator::detectedSurfaceRegions +( + VRWGraph& graph +) const +{ + graph.setSize(nPatches_); + + labelLongList nFacetsInPatch(nPatches_, 0); + + forAll(facetInPatch_, triI) + ++nFacetsInPatch[facetInPatch_[triI]]; + + graph.setSizeAndRowSize(nFacetsInPatch); + + nFacetsInPatch = 0; + forAll(facetInPatch_, triI) + { + const label patchI = facetInPatch_[triI]; + + graph(patchI, nFacetsInPatch[patchI]) = triI; + ++nFacetsInPatch[patchI]; + } +} + +const triSurf* triSurfacePatchManipulator::surfaceWithPatches +( + IOdictionary* meshDictPtr, + const word prefix, + const bool forceOverwrite +) const +{ + //- collect patch information + VRWGraph facetsInPatch; + detectedSurfaceRegions(facetsInPatch); + + //- create new list of boundary patches + LongList<labelledTri> newTriangles(facetInPatch_.size()); + label counter(0); + geometricSurfacePatchList newPatches(nPatches_); + + if( forceOverwrite ) + { + forAll(newPatches, patchI) + { + newPatches[patchI].name() = prefix+help::scalarToText(patchI); + newPatches[patchI].geometricType() = "patch"; + newPatches[patchI].index() = patchI; + } + } + else + { + forAll(facetsInPatch, patchI) + { + forAllRow(facetsInPatch, patchI, fpI) + { + const label origPatchI = + surf_[facetsInPatch(patchI, fpI)].region(); + newPatches[patchI].name() = + surf_.patches()[origPatchI].name() + '_' + + help::scalarToText(patchI); + newPatches[patchI].geometricType() = + surf_.patches()[origPatchI].geometricType(); + newPatches[patchI].index() = patchI; + } + } + } + + //- create triangles for the new surface + labelLongList newFacetLabel(newTriangles.size(), -1); + + forAll(facetsInPatch, patchI) + forAllRow(facetsInPatch, patchI, tI) + { + newFacetLabel[facetsInPatch(patchI, tI)] = counter; + labelledTri tria = surf_[facetsInPatch(patchI, tI)]; + tria.region() = patchI; + newTriangles[counter++] = tria; + } + + //- create and return a new surface mesh + triSurf* newSurfPtr = + new triSurf + ( + newTriangles, + newPatches, + edgeLongList(), + surf_.points() + ); + + //- transfer facet subsets + DynList<label> subsetIDs; + surf_.facetSubsetIndices(subsetIDs); + forAll(subsetIDs, subsetI) + { + const word sName = surf_.facetSubsetName(subsetIDs[subsetI]); + + const label newID = newSurfPtr->addFacetSubset(sName); + + labelLongList facetsInSubset; + surf_.facetsInSubset(subsetIDs[subsetI], facetsInSubset); + + forAll(facetsInSubset, i) + { + const label fI = newFacetLabel[facetsInSubset[i]]; + + newSurfPtr->addFacetToSubset(newID, fI); + } + } + + //- transfer point subsets + surf_.pointSubsetIndices(subsetIDs); + forAll(subsetIDs, subsetI) + { + const word sName = surf_.pointSubsetName(subsetIDs[subsetI]); + + const label newID = newSurfPtr->addPointSubset(sName); + + labelLongList pointsInSubset; + surf_.pointsInSubset(subsetIDs[subsetI], pointsInSubset); + + forAll(pointsInSubset, i) + newSurfPtr->addPointToSubset(newID, pointsInSubset[i]); + } + + if( meshDictPtr ) + { + //- create mapping between the patches on the original surface + //- and the renamed patches + std::map<word, wordList> patchesForPatch; + std::map<word, word> patchTypes; + + const geometricSurfacePatchList& origPatches = surf_.patches(); + forAll(origPatches, patchI) + patchTypes[origPatches[patchI].name()] = + origPatches[patchI].geometricType(); + + //- find the mapping of patch ids + List<labelHashSet> patchToNewPatches(origPatches.size()); + forAll(facetsInPatch, patchI) + { + forAllRow(facetsInPatch, patchI, fI) + { + const label opatchI = surf_[facetsInPatch(patchI, fI)].region(); + + patchToNewPatches[opatchI].insert(patchI); + } + } + + forAll(patchToNewPatches, patchI) + { + const word& pName = origPatches[patchI].name(); + patchesForPatch[pName].setSize + ( + patchToNewPatches[patchI].size() + ); + + label counter(0); + + forAllConstIter(labelHashSet, patchToNewPatches[patchI], it) + patchesForPatch[pName][counter++] = newPatches[it.key()].name(); + } + + //- update the values in meshDict based on the created patches + checkMeshDict(*meshDictPtr).updateDictionaries + ( + patchesForPatch, + patchTypes + ); + } + + return newSurfPtr; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulator.H b/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulator.H new file mode 100644 index 0000000000000000000000000000000000000000..0258cadb6bca31cd8adda1152cae482ddd084b86 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulator.H @@ -0,0 +1,119 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfacePatchManipulator + +Description + Generates patches in the surface mesh based + on the user-selected feature edges + +SourceFiles + triSurfacePatchManipulator.C + triSurfacePatchManipulatorFunctions.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfacePatchManipulator_H +#define triSurfacePatchManipulator_H + +#include "triSurf.H" +#include "VRWGraph.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +/*---------------------------------------------------------------------------*\ + Class triSurfacePatchManipulator Declaration +\*---------------------------------------------------------------------------*/ + +class triSurfacePatchManipulator +{ + // Private data + //- const reference to triSurf + const triSurf& surf_; + + //- detected feature edges + List<direction> featureEdges_; + + //- surface patches + labelList facetInPatch_; + + //- number of patches + label nPatches_; + + //- patch names + wordList newPatchNames_; + + //- patch types + wordList newPatchTypes_; + + // Private member functions + //- allocate and fill the feature edges list + void allocateFeatureEdges(); + + //- create patches bounded by a set of feature edges + void createPatches(); + + //- Disallow default bitwise copy construct + triSurfacePatchManipulator(const triSurfacePatchManipulator&); + + //- Disallow default bitwise assignment + void operator=(const triSurfacePatchManipulator&); + +public: + + // Constructors + + //- Construct from triSurface + triSurfacePatchManipulator(const triSurf& surface); + + // Destructor + + ~triSurfacePatchManipulator(); + + + // Member Functions + + void detectedSurfaceRegions(VRWGraph&) const; + + //- store regions into subsets with a given prefix + const triSurf* surfaceWithPatches + ( + IOdictionary* meshDictPtr = NULL, + const word prefix = "patch_", + const bool forceOverwrite = false + ) const; +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulatorFunctions.C b/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulatorFunctions.C new file mode 100644 index 0000000000000000000000000000000000000000..ad442975ad973a70a51b8d9676493aa28c34a784 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfacePatchManipulator/triSurfacePatchManipulatorFunctions.C @@ -0,0 +1,130 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfacePatchManipulator.H" +#include "helperFunctions.H" +#include "triSurfaceDetectPlanarRegions.H" +#include "demandDrivenData.H" + +#include <omp.h> + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfacePatchManipulator::allocateFeatureEdges() +{ + const edgeLongList& edges = surf_.edges(); + const VRWGraph& pEdges = surf_.pointEdges(); + + //- allocate featureEdges list + featureEdges_.setSize(edges.size()); + featureEdges_ = direction(0); + + const edgeLongList& featureEdges = surf_.featureEdges(); + + forAll(featureEdges, feI) + { + const edge& e = featureEdges[feI]; + + forAllRow(pEdges, e.start(), peI) + { + const label eI = pEdges(e.start(), peI); + + if( edges[eI] == e ) + featureEdges_[eI] |= 1; + } + } +} + +void triSurfacePatchManipulator::createPatches() +{ + nPatches_ = 0; + facetInPatch_.setSize(surf_.size()); + facetInPatch_ = -1; + + const VRWGraph& faceEdges = surf_.facetEdges(); + const VRWGraph& edgeFaces = surf_.edgeFacets(); + + forAll(facetInPatch_, triI) + { + if( facetInPatch_[triI] != -1 ) + continue; + + labelLongList front; + front.append(triI); + facetInPatch_[triI] = nPatches_; + + while( front.size() ) + { + const label fLabel = front.removeLastElement(); + + const constRow fEdges = faceEdges[fLabel]; + + forAll(fEdges, feI) + { + const label edgeI = fEdges[feI]; + + //- check if th edges is marked as a feature edge + if( featureEdges_[edgeI] ) + continue; + + const constRow eFaces = edgeFaces[edgeI]; + + //- stop at non-manifold edges + if( eFaces.size() != 2 ) + continue; + + label neiTri = eFaces[0]; + if( neiTri == fLabel ) + neiTri = eFaces[1]; + + //- do not overwrite existing patch information + if( surf_[fLabel].region() != surf_[neiTri].region() ) + continue; + if( facetInPatch_[neiTri] != -1 ) + continue; + + facetInPatch_[neiTri] = nPatches_; + front.append(neiTri); + } + } + + ++nPatches_; + } + + Info << "Created " << nPatches_ << " surface patches" << endl; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacets.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacets.C new file mode 100644 index 0000000000000000000000000000000000000000..128a09f753551dedd31936b2195fa3baf0c01e5f --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacets.C @@ -0,0 +1,63 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfaceRemoveFacets.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +triSurfaceRemoveFacets::triSurfaceRemoveFacets(triSurf& surface) +: + surf_(surface), + selectedEntities_() +{} + +triSurfaceRemoveFacets::~triSurfaceRemoveFacets() +{} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfaceRemoveFacets::selectFacetsInPatch(const word& patchName) +{ + selectedEntities_.append(patchName); +} + +//- add subsets for removal +void triSurfaceRemoveFacets::selectFacetsInSubset(const word& subsetName) +{ + selectedEntities_.append(subsetName); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacets.H b/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacets.H new file mode 100644 index 0000000000000000000000000000000000000000..ccc6c408fb76ccaad88857991f4699c80b4743b5 --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacets.H @@ -0,0 +1,102 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Class + triSurfaceRemoveFacets + +Description + Divides the surface mesh into regions bounded by feature edges + +SourceFiles + triSurfaceRemoveFacets.C + triSurfaceRemoveFacetsFunctions.C + +\*---------------------------------------------------------------------------*/ + +#ifndef triSurfaceRemoveFacets_H +#define triSurfaceRemoveFacets_H + +#include "triSurf.H" +#include "boolList.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +/*---------------------------------------------------------------------------*\ + Class triSurfaceRemoveFacets Declaration +\*---------------------------------------------------------------------------*/ + +class triSurfaceRemoveFacets +{ + // Private data + //- reference to triSurf + triSurf& surf_; + + //- patches/subsets for removal + DynList<word> selectedEntities_; + + // Private member functions + //- remove facets in selected patches/subsets + void markFacetsForRemoval(boolList&) const; + + //- Disallow default bitwise copy construct + triSurfaceRemoveFacets(const triSurfaceRemoveFacets&); + + //- Disallow default bitwise assignment + void operator=(const triSurfaceRemoveFacets&); + +public: + + // Constructors + + //- Construct from octree + triSurfaceRemoveFacets(triSurf& surface); + + // Destructor + + ~triSurfaceRemoveFacets(); + + + // Member Functions + + //- add patch for removal + void selectFacetsInPatch(const word&); + + //- add subsets for removal + void selectFacetsInSubset(const word&); + + //- perform removal of selected facets + void removeFacets(); +}; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacetsFunctions.C b/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacetsFunctions.C new file mode 100644 index 0000000000000000000000000000000000000000..db15df229fe497ef131949d2a7cedc618b2bc12b --- /dev/null +++ b/meshLibrary/utilities/triSurfaceTools/triSurfaceRemoveFacets/triSurfaceRemoveFacetsFunctions.C @@ -0,0 +1,185 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + +\*---------------------------------------------------------------------------*/ + +#include "triSurfaceRemoveFacets.H" +#include "triSurfModifier.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +void triSurfaceRemoveFacets::markFacetsForRemoval(boolList& removeFacet) const +{ + removeFacet.setSize(surf_.size()); + removeFacet = false; + + const geometricSurfacePatchList& patches = surf_.patches(); + + //- mark patches which will be removed + boolList removePatch(patches.size(), false); + + forAll(patches, patchI) + { + if( selectedEntities_.contains(patches[patchI].name()) ) + removePatch[patchI] = true; + } + + //- select facets affected by the deletion of a patch + forAll(surf_, triI) + { + if( removePatch[surf_[triI].region()] ) + removeFacet[triI] = true; + } + + //- mark facets contained in selected subsets + DynList<label> facetSubsetsIDs; + surf_.facetSubsetIndices(facetSubsetsIDs); + + forAll(facetSubsetsIDs, i) + { + const word fsName = surf_.facetSubsetName(facetSubsetsIDs[i]); + + if( selectedEntities_.contains(fsName) ) + { + labelLongList containedFacets; + surf_.facetsInSubset(facetSubsetsIDs[i], containedFacets); + + forAll(containedFacets, cfI) + removeFacet[containedFacets[cfI]] = true; + } + } +} + +void triSurfaceRemoveFacets::removeFacets() +{ + boolList removeFacet; + markFacetsForRemoval(removeFacet); + + //- calculate new indices of vertices and facets + const pointField& points = surf_.points(); + labelLongList newPointLabel(surf_.points().size(), -1); + labelLongList newFacetLabel(surf_.size(), -1); + + label pointCounter(0), facetCounter(0); + + forAll(removeFacet, triI) + { + if( removeFacet[triI] ) + continue; + + const labelledTri& tri = surf_[triI]; + + forAll(tri, pI) + { + if( newPointLabel[tri[pI]] == -1 ) + newPointLabel[tri[pI]] = pointCounter++; + } + + newFacetLabel[triI] = facetCounter++; + } + + //- remove vertices + pointField newPts(pointCounter); + forAll(newPointLabel, pI) + { + if( newPointLabel[pI] < 0 ) + continue; + + newPts[newPointLabel[pI]] = points[pI]; + } + + triSurfModifier(surf_).pointsAccess().transfer(newPts); + surf_.updatePointSubsets(newPointLabel); + + //- remove facets + LongList<labelledTri> newFacets(facetCounter); + + forAll(newFacetLabel, triI) + { + if( newFacetLabel[triI] < 0 ) + continue; + + const labelledTri& tri = surf_[triI]; + + newFacets[newFacetLabel[triI]] = + labelledTri + ( + newPointLabel[tri[0]], + newPointLabel[tri[1]], + newPointLabel[tri[2]], + tri.region() + ); + } + + triSurfModifier(surf_).facetsAccess().transfer(newFacets); + surf_.updateFacetsSubsets(newFacetLabel); + + //- update feature edges + const edgeLongList& featureEdges = surf_.featureEdges(); + label edgeCounter(0); + labelLongList newFeatureEdgeLabel(featureEdges.size(), -1); + + forAll(featureEdges, feI) + { + const edge& e = featureEdges[feI]; + + if( (newPointLabel[e.start()] < 0) || (newPointLabel[e.end()] < 0) ) + continue; + + newFeatureEdgeLabel[feI] = edgeCounter++; + } + + edgeLongList newFeatureEdges(edgeCounter); + forAll(newFeatureEdgeLabel, eI) + { + if( newFeatureEdgeLabel[eI] < 0 ) + continue; + + const edge& e = featureEdges[eI]; + + newFeatureEdges[newFeatureEdgeLabel[eI]] = + edge + ( + newPointLabel[e.start()], + newPointLabel[e.end()] + ); + } + + triSurfModifier(surf_).featureEdgesAccess().transfer(newFeatureEdges); + surf_.updateEdgeSubsets(newFeatureEdgeLabel); + + selectedEntities_.clear(); +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace Foam + +// ************************************************************************* // diff --git a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.C b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.C index da20cc052661efee4064a681db97ca2db5ef010f..a3598570a6a6699f6f9907fc913da87d4ea71d31 100644 --- a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.C +++ b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,15 +34,15 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void voronoiMeshExtractor::clearOut() { - deleteDemandDrivenData(pointEdgesPtr_); - deleteDemandDrivenData(edgesPtr_); - deleteDemandDrivenData(edgeTetsPtr_); - deleteDemandDrivenData(boundaryEdgePtr_); + deleteDemandDrivenData(pointEdgesPtr_); + deleteDemandDrivenData(edgesPtr_); + deleteDemandDrivenData(edgeTetsPtr_); + deleteDemandDrivenData(boundaryEdgePtr_); } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // @@ -52,16 +51,16 @@ void voronoiMeshExtractor::clearOut() voronoiMeshExtractor::voronoiMeshExtractor ( const meshOctree& octree, - const IOdictionary& meshDict, - polyMeshGen& mesh + const IOdictionary& meshDict, + polyMeshGen& mesh ) : tetCreator_(octree, meshDict), - mesh_(mesh), - pointEdgesPtr_(NULL), - edgesPtr_(NULL), - edgeTetsPtr_(NULL), - boundaryEdgePtr_(NULL) + mesh_(mesh), + pointEdgesPtr_(NULL), + edgesPtr_(NULL), + edgeTetsPtr_(NULL), + boundaryEdgePtr_(NULL) { } @@ -69,29 +68,29 @@ voronoiMeshExtractor::voronoiMeshExtractor voronoiMeshExtractor::~voronoiMeshExtractor() { - clearOut(); + clearOut(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void voronoiMeshExtractor::createMesh() { - Info << "Extracting voronoi mesh" << endl; - - //- copy tet points into the mesh - createPoints(); + Info << "Extracting voronoi mesh" << endl; + + //- copy tet points into the mesh + createPoints(); - //- create the mesh + //- create the mesh createPolyMesh(); - - polyMeshGenModifier(mesh_).reorderBoundaryFaces(); - polyMeshGenModifier(mesh_).removeUnusedVertices(); - - Info << "Mesh has :" << nl - << mesh_.points().size() << " vertices " << nl - << mesh_.faces().size() << " faces" << nl - << mesh_.cells().size() << " cells" << endl; - + + polyMeshGenModifier(mesh_).reorderBoundaryFaces(); + polyMeshGenModifier(mesh_).removeUnusedVertices(); + + Info << "Mesh has :" << nl + << mesh_.points().size() << " vertices " << nl + << mesh_.faces().size() << " faces" << nl + << mesh_.cells().size() << " cells" << endl; + Info << "Finished extracting voronoi mesh" << endl; } diff --git a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.H b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.H index b76c22c198badc56122b58041e318465d7dd33e9..40518079af1c58a71f91252fcaf83e1879bbba7d 100644 --- a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.H +++ b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractor.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class voronoiMeshExtractor @@ -53,41 +52,41 @@ namespace Foam class voronoiMeshExtractor { // Private data - //- create tets - tetCreatorOctree tetCreator_; - - //- reference to the mesh - polyMeshGen& mesh_; - - //- edges connected to a vertex in the tet mesh - mutable VRWGraph* pointEdgesPtr_; - - //- edges of the tetrahedrization - mutable LongList<edge>* edgesPtr_; - - //- tets around each edge - mutable VRWGraph* edgeTetsPtr_; - - //- is edge at the boundary - mutable boolList* boundaryEdgePtr_; - + //- create tets + tetCreatorOctree tetCreator_; + + //- reference to the mesh + polyMeshGen& mesh_; + + //- edges connected to a vertex in the tet mesh + mutable VRWGraph* pointEdgesPtr_; + + //- edges of the tetrahedrization + mutable LongList<edge>* edgesPtr_; + + //- tets around each edge + mutable VRWGraph* edgeTetsPtr_; + + //- is edge at the boundary + mutable boolList* boundaryEdgePtr_; + // Private member functions - //- create and return addressing - void createAddressing() const; - - const VRWGraph& pointEdges() const; - const LongList<edge>& edges() const; - const VRWGraph& edgeTets() const; - const boolList& boundaryEdge() const; - + //- create and return addressing + void createAddressing() const; + + const VRWGraph& pointEdges() const; + const LongList<edge>& edges() const; + const VRWGraph& edgeTets() const; + const boolList& boundaryEdge() const; + //- create points of the voronoi mesh void createPoints(); //- create mesh data void createPolyMesh(); - - //- delete all pointer data - void clearOut(); + + //- delete all pointer data + void clearOut(); // Private copy constructor //- Disallow default bitwise copy construct @@ -104,8 +103,8 @@ public: voronoiMeshExtractor ( const meshOctree& octree, - const IOdictionary& meshDict, - polyMeshGen& mesh + const IOdictionary& meshDict, + polyMeshGen& mesh ); // Destructor @@ -114,7 +113,7 @@ public: // Member Functions - void createMesh(); + void createMesh(); }; diff --git a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorAddressing.C b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorAddressing.C index 0220de532285e8e06dc5b8025836de71488f7ba7..af936fb784ef0347f0e404ee7756439b87fae212 100644 --- a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorAddressing.C +++ b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorAddressing.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -36,184 +35,184 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void voronoiMeshExtractor::createAddressing() const { - if( pointEdgesPtr_ ) - return; - pointEdgesPtr_ = new VRWGraph(tetCreator_.tetPoints().size()); - VRWGraph& pointEdges = *pointEdgesPtr_; - - if( edgeTetsPtr_ ) - return; - edgeTetsPtr_ = new VRWGraph(); - VRWGraph& edgeTets = *edgeTetsPtr_; - - if( boundaryEdgePtr_ ) - return; - boundaryEdgePtr_ = new boolList(); - boolList& boundaryEdges = *boundaryEdgePtr_; - - if( edgesPtr_ ) - return; - edgesPtr_ = new LongList<edge>(); - LongList<edge>& edges = *edgesPtr_; - - //- create edges, pointEdges and edgeTets - const LongList<partTet>& tets = tetCreator_.tets(); - forAll(tets, tetI) - { - const edgeList tetEdges = tets[tetI].edges(); - - forAll(tetEdges, eI) - { - const edge& e = tetEdges[eI]; - const label start = e.start(); - - bool store(true); - - forAllRow(pointEdges, start, peI) - { - const label edgeI = pointEdges(start, peI); - - if( edges[edgeI] == e ) - { - store = false; - - edgeTets.append(edgeI, tetI); - } - } - - if( store ) - { - pointEdges.append(start, edges.size()); - pointEdges.append(e.end(), edges.size()); - - FixedList<label, 1> helper; - helper[0] = tetI; - edgeTets.appendList(helper); - - edges.append(e); - } - } - } - - pointEdges.optimizeMemoryUsage(); - edgeTets.optimizeMemoryUsage(); - - //- sort edge-tets in circular order - boundaryEdges.setSize(edgeTets.size()); - boundaryEdges = false; - - forAll(edgeTets, edgeI) - { - labelList eTets(edgeTets.sizeOfRow(edgeI)); - forAll(eTets, etI) - eTets[etI] = edgeTets(edgeI, etI); - - labelList nFound(eTets.size(), 0); - List<FixedList<label, 2> > elNeighbours(eTets.size()); - forAll(elNeighbours, tetI) - elNeighbours[tetI] = -1; - - forAll(eTets, tetI) - { - if( nFound[tetI] == 2 ) - continue; - - const partTet& pt = tets[eTets[tetI]]; - - for(label i=tetI+1;i<eTets.size();++i) - { - const partTet& ptNei = tets[eTets[i]]; - - label nShared(0); - for(label j=0;j<4;++j) - for(label k=0;k<4;++k) - if( pt[j] == ptNei[k] ) - { - ++nShared; - break; - } - - if( nShared == 3 ) - { - elNeighbours[tetI][nFound[tetI]++] = i; - elNeighbours[i][nFound[i]++] = tetI; - } - } - } - - bool sort(true); - forAll(nFound, tetI) - if( nFound[tetI] != 2 ) - { - boundaryEdges[edgeI] = true; - sort = false; - break; - } - - if( sort ) - { - labelList sortedTets(eTets.size()); - - label currI(0), nextI(elNeighbours[0][0]), counter(0); - sortedTets[counter++] = eTets[currI]; - - do - { - sortedTets[counter++] = eTets[nextI]; - - //- find the next element - if( elNeighbours[nextI][0] == currI ) - { - currI = nextI; - nextI = elNeighbours[nextI][1]; - } - else - { - currI = nextI; - nextI = elNeighbours[nextI][0]; - } - } while( counter < eTets.size() ); - - edgeTets.setRow(edgeI, sortedTets); - } - } + if( pointEdgesPtr_ ) + return; + pointEdgesPtr_ = new VRWGraph(tetCreator_.tetPoints().size()); + VRWGraph& pointEdges = *pointEdgesPtr_; + + if( edgeTetsPtr_ ) + return; + edgeTetsPtr_ = new VRWGraph(); + VRWGraph& edgeTets = *edgeTetsPtr_; + + if( boundaryEdgePtr_ ) + return; + boundaryEdgePtr_ = new boolList(); + boolList& boundaryEdges = *boundaryEdgePtr_; + + if( edgesPtr_ ) + return; + edgesPtr_ = new LongList<edge>(); + LongList<edge>& edges = *edgesPtr_; + + //- create edges, pointEdges and edgeTets + const LongList<partTet>& tets = tetCreator_.tets(); + forAll(tets, tetI) + { + const edgeList tetEdges = tets[tetI].edges(); + + forAll(tetEdges, eI) + { + const edge& e = tetEdges[eI]; + const label start = e.start(); + + bool store(true); + + forAllRow(pointEdges, start, peI) + { + const label edgeI = pointEdges(start, peI); + + if( edges[edgeI] == e ) + { + store = false; + + edgeTets.append(edgeI, tetI); + } + } + + if( store ) + { + pointEdges.append(start, edges.size()); + pointEdges.append(e.end(), edges.size()); + + FixedList<label, 1> helper; + helper[0] = tetI; + edgeTets.appendList(helper); + + edges.append(e); + } + } + } + + pointEdges.optimizeMemoryUsage(); + edgeTets.optimizeMemoryUsage(); + + //- sort edge-tets in circular order + boundaryEdges.setSize(edgeTets.size()); + boundaryEdges = false; + + forAll(edgeTets, edgeI) + { + labelList eTets(edgeTets.sizeOfRow(edgeI)); + forAll(eTets, etI) + eTets[etI] = edgeTets(edgeI, etI); + + labelList nFound(eTets.size(), 0); + List<FixedList<label, 2> > elNeighbours(eTets.size()); + forAll(elNeighbours, tetI) + elNeighbours[tetI] = -1; + + forAll(eTets, tetI) + { + if( nFound[tetI] == 2 ) + continue; + + const partTet& pt = tets[eTets[tetI]]; + + for(label i=tetI+1;i<eTets.size();++i) + { + const partTet& ptNei = tets[eTets[i]]; + + label nShared(0); + for(label j=0;j<4;++j) + for(label k=0;k<4;++k) + if( pt[j] == ptNei[k] ) + { + ++nShared; + break; + } + + if( nShared == 3 ) + { + elNeighbours[tetI][nFound[tetI]++] = i; + elNeighbours[i][nFound[i]++] = tetI; + } + } + } + + bool sort(true); + forAll(nFound, tetI) + if( nFound[tetI] != 2 ) + { + boundaryEdges[edgeI] = true; + sort = false; + break; + } + + if( sort ) + { + labelList sortedTets(eTets.size()); + + label currI(0), nextI(elNeighbours[0][0]), counter(0); + sortedTets[counter++] = eTets[currI]; + + do + { + sortedTets[counter++] = eTets[nextI]; + + //- find the next element + if( elNeighbours[nextI][0] == currI ) + { + currI = nextI; + nextI = elNeighbours[nextI][1]; + } + else + { + currI = nextI; + nextI = elNeighbours[nextI][0]; + } + } while( counter < eTets.size() ); + + edgeTets.setRow(edgeI, sortedTets); + } + } } const VRWGraph& voronoiMeshExtractor::pointEdges() const { - if( !pointEdgesPtr_ ) - createAddressing(); - - return *pointEdgesPtr_; + if( !pointEdgesPtr_ ) + createAddressing(); + + return *pointEdgesPtr_; } const LongList<edge>& voronoiMeshExtractor::edges() const { - if( !edgesPtr_ ) - createAddressing(); - - return *edgesPtr_; + if( !edgesPtr_ ) + createAddressing(); + + return *edgesPtr_; } const VRWGraph& voronoiMeshExtractor::edgeTets() const { - if( !edgeTetsPtr_ ) - createAddressing(); - - return *edgeTetsPtr_; + if( !edgeTetsPtr_ ) + createAddressing(); + + return *edgeTetsPtr_; } const boolList& voronoiMeshExtractor::boundaryEdge() const { - if( !boundaryEdgePtr_ ) - createAddressing(); - - return *boundaryEdgePtr_; + if( !boundaryEdgePtr_ ) + createAddressing(); + + return *boundaryEdgePtr_; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorCreateMesh.C b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorCreateMesh.C index 36b69cd6d04c382e46b71177b5eacb9638dfe5f8..0d51251dad7379dd61b6ce868c7b344bfff75630 100644 --- a/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorCreateMesh.C +++ b/meshLibrary/voronoiMesh/voronoiMeshExtractor/voronoiMeshExtractorCreateMesh.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -38,107 +37,107 @@ Description namespace Foam { - + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void voronoiMeshExtractor::createPoints() { - const LongList<point>& tetPoints = tetCreator_.tetPoints(); - const LongList<partTet>& tets = tetCreator_.tets(); - - pointFieldPMG& points = mesh_.points(); - points.setSize(tets.size()); - - # ifdef DEBUGVoronoi - Info << "Number of tets " << tets.size() << endl; - # endif - - forAll(tets, tetI) - { - points[tetI] = tets[tetI].centroid(tetPoints); - - # ifdef DEBUGVoronoi - Info << "Point " << tetI << " has coordinates " - << points[tetI] << endl; - Info << "Tet of origin " << tetI << " has nodes " - << tets[tetI] << endl; - # endif - } + const LongList<point>& tetPoints = tetCreator_.tetPoints(); + const LongList<partTet>& tets = tetCreator_.tets(); + + pointFieldPMG& points = mesh_.points(); + points.setSize(tets.size()); + + # ifdef DEBUGVoronoi + Info << "Number of tets " << tets.size() << endl; + # endif + + forAll(tets, tetI) + { + points[tetI] = tets[tetI].centroid(tetPoints); + + # ifdef DEBUGVoronoi + Info << "Point " << tetI << " has coordinates " + << points[tetI] << endl; + Info << "Tet of origin " << tetI << " has nodes " + << tets[tetI] << endl; + # endif + } } void voronoiMeshExtractor::createPolyMesh() { - const VRWGraph& pointEdges = this->pointEdges(); - const VRWGraph& edgeTets = this->edgeTets(); - const boolList& boundaryEdge = this->boundaryEdge(); - const LongList<edge>& edges = this->edges(); - const LongList<partTet>& tets = tetCreator_.tets(); - - polyMeshGenModifierAddCellByCell meshModifier(mesh_); - - forAll(pointEdges, pointI) - { - bool create(true); - forAllRow(pointEdges, pointI, eI) - if( boundaryEdge[pointEdges(pointI, eI)] ) - { - create = false; - break; - } - - if( !create || (pointEdges.sizeOfRow(pointI) == 0) ) - continue; - - faceList cellFaces(pointEdges.sizeOfRow(pointI)); - - forAllRow(pointEdges, pointI, faceI) - { - const label edgeI = pointEdges(pointI, faceI); - - //- check if the face orientation needs to be changed - bool flip(false); - const partTet& tet = tets[edgeTets(edgeI, 0)]; - const partTet& tet1 = tets[edgeTets(edgeI, 1)]; - tessellationElement tEl(tet[0], tet[1], tet[2], tet[3]); - for(label i=0;i<4;++i) - { - const triFace tf = tEl.face(i); - label nShared(0); - for(label j=0;j<3;++j) - if( tet1.whichPosition(tf[j]) != -1 ) - ++nShared; - - if( nShared == 3 ) - { - const edge& e = edges[edgeI]; - - const edgeList tEdges = tf.edges(); - forAll(tEdges, teI) - if( tEdges[teI] == e ) - { - if( pointI == tEdges[teI].start() ) - flip = true; - - break; - } - - break; - } - } - - face& f = cellFaces[faceI]; - f.setSize(edgeTets.sizeOfRow(edgeI)); - - //- fill the faces with the node labels - forAll(f, pI) - f[pI] = edgeTets(edgeI, pI); - - if( flip ) - f = f.reverseFace(); - } - - meshModifier.addCell(cellFaces); - } + const VRWGraph& pointEdges = this->pointEdges(); + const VRWGraph& edgeTets = this->edgeTets(); + const boolList& boundaryEdge = this->boundaryEdge(); + const LongList<edge>& edges = this->edges(); + const LongList<partTet>& tets = tetCreator_.tets(); + + polyMeshGenModifierAddCellByCell meshModifier(mesh_); + + forAll(pointEdges, pointI) + { + bool create(true); + forAllRow(pointEdges, pointI, eI) + if( boundaryEdge[pointEdges(pointI, eI)] ) + { + create = false; + break; + } + + if( !create || (pointEdges.sizeOfRow(pointI) == 0) ) + continue; + + faceList cellFaces(pointEdges.sizeOfRow(pointI)); + + forAllRow(pointEdges, pointI, faceI) + { + const label edgeI = pointEdges(pointI, faceI); + + //- check if the face orientation needs to be changed + bool flip(false); + const partTet& tet = tets[edgeTets(edgeI, 0)]; + const partTet& tet1 = tets[edgeTets(edgeI, 1)]; + tessellationElement tEl(tet[0], tet[1], tet[2], tet[3]); + for(label i=0;i<4;++i) + { + const triFace tf = tEl.face(i); + label nShared(0); + for(label j=0;j<3;++j) + if( tet1.whichPosition(tf[j]) != -1 ) + ++nShared; + + if( nShared == 3 ) + { + const edge& e = edges[edgeI]; + + const edgeList tEdges = tf.edges(); + forAll(tEdges, teI) + if( tEdges[teI] == e ) + { + if( pointI == tEdges[teI].start() ) + flip = true; + + break; + } + + break; + } + } + + face& f = cellFaces[faceI]; + f.setSize(edgeTets.sizeOfRow(edgeI)); + + //- fill the faces with the node labels + forAll(f, pI) + f[pI] = edgeTets(edgeI, pI); + + if( flip ) + f = f.reverseFace(); + } + + meshModifier.addCell(cellFaces); + } } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.C b/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.C index b5b5f3892e8352d319b235e7543b547d75d4326a..fe7c6ab28d9a0fc9dae5cc2d4b7c46261b7c8d97 100644 --- a/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.C +++ b/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description @@ -35,23 +34,23 @@ Description #include "voronoiMeshExtractor.H" #include "meshSurfaceEngine.H" #include "meshSurfaceMapper.H" -#include "meshSurfaceEdgeExtractorNonTopo.H" -#include "decomposeCellsNearConcaveEdges.H" #include "surfaceMorpherCells.H" #include "meshOptimizer.H" #include "meshSurfaceOptimizer.H" #include "topologicalCleaner.H" #include "boundaryLayers.H" +#include "refineBoundaryLayers.H" #include "renameBoundaryPatches.H" #include "checkMeshDict.H" +#include "triSurfacePatchManipulator.H" -//#define DEBUG -//#define DEBUGfpma +#include "checkCellConnectionsOverFaces.H" +#include "checkIrregularSurfaceConnections.H" +#include "checkNonMappableCellConnections.H" +#include "checkBoundaryFacesSharingTwoEdges.H" +#include "meshSurfaceEdgeExtractorFUN.H" -# ifdef DEBUG -#include "writeMeshEnsight.H" -#include "writeMeshFPMA.H" -# endif +//#define DEBUG // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -61,234 +60,235 @@ namespace Foam // * * * * * * * * * * * * Private member functions * * * * * * * * * * * * // void voronoiMeshGenerator::createVoronoiMesh() -{ - //- create voronoi mesh from octree and Delaunay tets - voronoiMeshExtractor vme(*octreePtr_, meshDict_, mesh_); - - vme.createMesh(); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "voronoiMesh"); - # else - writeMeshEnsight(mesh_, "voronoiMesh"); - # endif - //::exit(EXIT_FAILURE); - # endif +{ + //- create voronoi mesh from octree and Delaunay tets + voronoiMeshExtractor vme(*octreePtr_, meshDict_, mesh_); + + vme.createMesh(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif } - + void voronoiMeshGenerator::surfacePreparation() { - //- removes unnecessary cells and morph the boundary + //- removes unnecessary cells and morph the boundary //- such that there is only one boundary face per cell - //- It also checks topology of cells after morphing is performed - do - { - surfaceMorpherCells* cmPtr = new surfaceMorpherCells(mesh_); - cmPtr->morphMesh(); - deleteDemandDrivenData(cmPtr); - } while( topologicalCleaner(mesh_).cleanTopology() ); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterTopoCleaning"); - # else - writeMeshEnsight(mesh_, "afterTopoCleaning"); - # endif - //::exit(EXIT_FAILURE); - # endif + //- It also checks topology of cells after morphing is performed + do + { + surfaceMorpherCells* cmPtr = new surfaceMorpherCells(mesh_); + cmPtr->morphMesh(); + deleteDemandDrivenData(cmPtr); + } + while( topologicalCleaner(mesh_).cleanTopology() ); + +/* bool changed; + do + { + changed = false; + + checkIrregularSurfaceConnections checkConnections(mesh_); + if( checkConnections.checkAndFixIrregularConnections() ) + changed = true; + + if( checkNonMappableCellConnections(mesh_).removeCells() ) + changed = true; + + if( checkCellConnectionsOverFaces(mesh_).checkCellGroups() ) + changed = true; + } while( changed ); + + checkBoundaryFacesSharingTwoEdges(mesh_).improveTopology(); + */ + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif } - + void voronoiMeshGenerator::mapMeshToSurface() { - //- calculate mesh surface + //- calculate mesh surface meshSurfaceEngine* msePtr = new meshSurfaceEngine(mesh_); - //- map mesh surface on the geometry surface - meshSurfaceMapper mapper(*msePtr, *octreePtr_); + //- map mesh surface on the geometry surface + meshSurfaceMapper mapper(*msePtr, *octreePtr_); mapper.preMapVertices(); mapper.mapVerticesOntoSurface(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterMapping"); - # else - writeMeshEnsight(mesh_, "afterMapping"); - # endif - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif - - //- untangle surface faces - meshSurfaceOptimizer(*msePtr, *octreePtr_).preOptimizeSurface(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "afterSurfaceSmoothing"); - # else - writeMeshEnsight(mesh_, "afterSurfaceSmoothing"); - # endif - mesh_.write(); - ::exit(EXIT_FAILURE); - # endif + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif + + //- untangle surface faces + meshSurfaceOptimizer(*msePtr, *octreePtr_).untangleSurface(); + + # ifdef DEBUG + mesh_.write(); + ::exit(EXIT_FAILURE); + # endif + deleteDemandDrivenData(msePtr); } void voronoiMeshGenerator::mapEdgesAndCorners() { - meshSurfaceEdgeExtractorNonTopo(mesh_, *octreePtr_); - - # ifdef DEBUG - mesh_.write(); - //meshOptimizer(*octreePtr_, mesh_).preOptimize(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "withEdges"); - # else - writeMeshEnsight(mesh_, "withEdges"); - #endif - //::exit(EXIT_FAILURE); - # endif + //meshSurfaceEdgeExtractorNonTopo(mesh_, *octreePtr_); + meshSurfaceEdgeExtractorFUN(mesh_, *octreePtr_); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif } void voronoiMeshGenerator::optimiseMeshSurface() { - meshSurfaceEngine mse(mesh_); - meshSurfaceOptimizer(mse, *octreePtr_).optimizeSurface(); - - # ifdef DEBUG - mesh_.write(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "optSurfaceWithEdges"); - # else - writeMeshEnsight(mesh_, "optSurfaceWithEdges"); - #endif - //::exit(EXIT_FAILURE); - # endif + meshSurfaceEngine mse(mesh_); + meshSurfaceOptimizer surfOptimiser(mse, *octreePtr_); + surfOptimiser.optimizeSurface(); + surfOptimiser.untangleSurface(); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif } void voronoiMeshGenerator::decomposeConcaveCells() { - decomposeCellsNearConcaveEdges dm(mesh_); - - # ifdef DEBUG - mesh_.write(); - //meshOptimizer(*octreePtr_, mesh_).preOptimize(); - # ifdef DEBUGfpma - writeMeshFPMA(mesh_, "decomposedConcaveCells"); - # else - writeMeshEnsight(mesh_, "decomposedConcaveCells"); - #endif - //::exit(EXIT_FAILURE); - # endif + //decomposeCellsNearConcaveEdges dm(mesh_); + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif } - + void voronoiMeshGenerator::generateBoudaryLayers() { - boundaryLayers bl(mesh_); - - if( meshDict_.found("boundaryLayers") ) + boundaryLayers bl(mesh_); + + if( meshDict_.found("boundaryLayers") ) { - wordList createLayers(meshDict_.lookup("boundaryLayers")); - - forAll(createLayers, patchI) - bl.addLayerForPatch(createLayers[patchI]); + boundaryLayers bl(mesh_); + + const dictionary& bndLayers = meshDict_.subDict("boundaryLayers"); + + if( bndLayers.found("nLayers") ) + { + const label nLayers = readLabel(bndLayers.lookup("nLayers")); + + if( nLayers > 0 ) + bl.addLayerForAllPatches(); + } + else if( bndLayers.found("patchBoundaryLayers") ) + { + const dictionary& patchLayers = + bndLayers.subDict("patchBoundaryLayers"); + const wordList createLayers = patchLayers.toc(); + + forAll(createLayers, patchI) + bl.addLayerForPatch(createLayers[patchI]); + } } - else + + # ifdef DEBUG + mesh_.write(); + //::exit(EXIT_FAILURE); + # endif +} + +void voronoiMeshGenerator::refBoundaryLayers() +{ + if( meshDict_.isDict("boundaryLayers") ) { - //bl.createOTopologyLayers(); - bl.addLayerForAllPatches(); - } - - # ifdef DEBUG - writeMeshEnsight(mesh_, "meshWithBndLayer"); - mesh_.write(); - //::exit(EXIT_FAILURE); - # endif + refineBoundaryLayers refLayers(mesh_); + + refineBoundaryLayers::readSettings(meshDict_, refLayers); + + refLayers.refineLayers(); + + meshOptimizer optimizer(mesh_); + + optimizer.untangleMeshFV(); + } } - + void voronoiMeshGenerator::optimiseFinalMesh() { - //- final optimisation - meshOptimizer optimizer(mesh_); - + //- final optimisation + meshOptimizer optimizer(mesh_); + optimizer.optimizeSurface(*octreePtr_); - + deleteDemandDrivenData(octreePtr_); - + optimizer.optimizeMeshFV(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"optimisedMesh"); - # else - writeMeshEnsight(mesh_, "optimisedMesh"); - #endif - # endif + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif } void voronoiMeshGenerator::replaceBoundaries() { renameBoundaryPatches rbp(mesh_, meshDict_); - + # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"renamedPatchesMesh"); - # else - writeMeshEnsight(mesh_, "renamedPatchesMesh"); - #endif - # endif + mesh_.write(); + //::exit(0); + # endif } void voronoiMeshGenerator::renumberMesh() { - polyMeshGenModifier(mesh_).renumberMesh(); - - # ifdef DEBUG - # ifdef DEBUGfpma - writeMeshFPMA(mesh_,"renumberedMesh"); - # else - writeMeshEnsight(mesh_, "renumberedMesh"); - #endif - # endif + polyMeshGenModifier(mesh_).renumberMesh(); + + # ifdef DEBUG + mesh_.write(); + //::exit(0); + # endif } - + void voronoiMeshGenerator::generateMesh() { - createVoronoiMesh(); - - surfacePreparation(); - - mapMeshToSurface(); - - mapEdgesAndCorners(); - - optimiseMeshSurface(); - - decomposeConcaveCells(); - - generateBoudaryLayers(); - - optimiseFinalMesh(); - - renumberMesh(); - + createVoronoiMesh(); + + surfacePreparation(); + + mapMeshToSurface(); + + mapEdgesAndCorners(); + + optimiseMeshSurface(); + + generateBoudaryLayers(); + + optimiseFinalMesh(); + + refBoundaryLayers(); + + renumberMesh(); + replaceBoundaries(); } // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // Construct from Time -voronoiMeshGenerator::voronoiMeshGenerator -( - const Time& time -) +voronoiMeshGenerator::voronoiMeshGenerator(const Time& time) : runTime_(time), surfacePtr_(NULL), - octreePtr_(NULL), - pointRegionsPtr_(NULL), + octreePtr_(NULL), + pointRegionsPtr_(NULL), meshDict_ ( IOobject @@ -300,24 +300,35 @@ voronoiMeshGenerator::voronoiMeshGenerator IOobject::NO_WRITE ) ), - mesh_(time) + mesh_(time) { if( true ) checkMeshDict cmd(meshDict_); - + const fileName surfaceFile = meshDict_.lookup("surfaceFile"); surfacePtr_ = new triSurf(runTime_.path()/surfaceFile); - - if( meshDict_.found("subsetFileName") ) - { - const fileName subsetFileName = meshDict_.lookup("subsetFileName"); - surfacePtr_->readFaceSubsets(runTime_.path()/subsetFileName); - } + + if( surfacePtr_->featureEdges().size() != 0 ) + { + //- create surface patches based on the feature edges + //- and update the meshDict based on the given data + triSurfacePatchManipulator manipulator(*surfacePtr_); + + const triSurf* surfaceWithPatches = + manipulator.surfaceWithPatches(&meshDict_); + + //- delete the old surface and assign the new one + deleteDemandDrivenData(surfacePtr_); + surfacePtr_ = surfaceWithPatches; + } octreePtr_ = new meshOctree(*surfacePtr_); - - meshOctreeCreator(*octreePtr_, meshDict_).createOctreeBoxes(); + + meshOctreeCreator* octreeCreatorPtr = + new meshOctreeCreator(*octreePtr_, meshDict_); + octreeCreatorPtr->createOctreeBoxes(); + deleteDemandDrivenData(octreeCreatorPtr); generateMesh(); } @@ -331,8 +342,8 @@ voronoiMeshGenerator::voronoiMeshGenerator : runTime_(time), surfacePtr_(NULL), - octreePtr_(NULL), - pointRegionsPtr_(NULL), + octreePtr_(NULL), + pointRegionsPtr_(NULL), meshDict_ ( IOobject @@ -344,7 +355,7 @@ voronoiMeshGenerator::voronoiMeshGenerator IOobject::NO_WRITE ) ), - mesh_(time) + mesh_(time) { fileName surfaceFile = meshDict_.lookup("surfaceFile"); @@ -362,14 +373,14 @@ voronoiMeshGenerator::~voronoiMeshGenerator() { deleteDemandDrivenData(surfacePtr_); deleteDemandDrivenData(octreePtr_); - deleteDemandDrivenData(pointRegionsPtr_); + deleteDemandDrivenData(pointRegionsPtr_); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // void voronoiMeshGenerator::writeMesh() const -{ - mesh_.write(); +{ + mesh_.write(); } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // diff --git a/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.H b/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.H index 26ee14dba27daf212ce65e0b885836b4725ca185..59fa5587ec7adf7481ea8edbdd78264eac22257b 100644 --- a/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.H +++ b/meshLibrary/voronoiMesh/voronoiMeshGenerator/voronoiMeshGenerator.H @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Class voronoiMeshGenerator @@ -51,7 +50,7 @@ class meshOctree; class Time; /*---------------------------------------------------------------------------*\ - Class voronoiMeshGenerator Declaration + Class voronoiMeshGenerator Declaration \*---------------------------------------------------------------------------*/ class voronoiMeshGenerator @@ -61,51 +60,54 @@ class voronoiMeshGenerator const Time& runTime_; //- pointer to the surface - triSurf* surfacePtr_; - - //- pointer to the octree + const triSurf* surfacePtr_; + + //- pointer to the octree meshOctree* octreePtr_; - - //- pointer to the list patches for boundary vertices - labelList* pointRegionsPtr_; + + //- pointer to the list patches for boundary vertices + labelList* pointRegionsPtr_; //- IOdictionary containing information about cell sizes, etc.. IOdictionary meshDict_; - - //- mesh - polyMeshGen mesh_; + + //- mesh + polyMeshGen mesh_; // Private member functions - //- create voronoi mesh - void createVoronoiMesh(); - - //- prepare mesh surface - void surfacePreparation(); - - //- map mesh to the surface and untangle surface - void mapMeshToSurface(); - - //- capture edges and corners - void mapEdgesAndCorners(); - - //- optimise surface mesh - void optimiseMeshSurface(); - - //- decompose concave cells - void decomposeConcaveCells(); - - //- add boundary layers - void generateBoudaryLayers(); - - //- mesh optimisation - void optimiseFinalMesh(); - + //- create voronoi mesh + void createVoronoiMesh(); + + //- prepare mesh surface + void surfacePreparation(); + + //- map mesh to the surface and untangle surface + void mapMeshToSurface(); + + //- capture edges and corners + void mapEdgesAndCorners(); + + //- optimise surface mesh + void optimiseMeshSurface(); + + //- decompose concave cells + void decomposeConcaveCells(); + + //- add boundary layers + void generateBoudaryLayers(); + + //- mesh optimisation + void optimiseFinalMesh(); + + //- refine boundary layer + void refBoundaryLayers(); + //- replace boundaries void replaceBoundaries(); - - //- renumber the mesh - void renumberMesh(); - + + //- renumber the mesh + void renumberMesh(); + //- generate mesh void generateMesh(); diff --git a/testingInterfaces/testBoundaryLayer/Make/options b/testingInterfaces/testBoundaryLayer/Make/options index 0fa7a4adb3c4b15013f80f1b3773f0124d78fb17..5206b3c7c0f2a6eacab0bd746cfd2488e3563452 100644 --- a/testingInterfaces/testBoundaryLayer/Make/options +++ b/testingInterfaces/testBoundaryLayer/Make/options @@ -1,2 +1,2 @@ EXE_INC = -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude -EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools +EXE_LIBS = -lmeshLibrary -ltriSurface -lmeshTools diff --git a/testingInterfaces/testBoundaryLayer/testBoundaryLayer.C b/testingInterfaces/testBoundaryLayer/testBoundaryLayer.C index 36ca0a3c2d8d35cb7239ab6befc2dfe766f4cdd3..3237870e3e4c5f7bd8cf67488b3535931164666d 100644 --- a/testingInterfaces/testBoundaryLayer/testBoundaryLayer.C +++ b/testingInterfaces/testBoundaryLayer/testBoundaryLayer.C @@ -26,19 +26,17 @@ Application Test for boundary layers Description - - + - \*---------------------------------------------------------------------------*/ #include "argList.H" -#include "meshOctreeCreator.H" #include "Time.H" #include "objectRegistry.H" -#include "polyMesh.H" #include "polyMeshGen.H" #include "boundaryLayers.H" -#include "writeMeshEnsight.H" -#include "meshOptimizer.H" +#include "refineBoundaryLayers.H" +#include "polyMeshGenChecks.H" using namespace Foam; @@ -50,47 +48,50 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" -# include "createPolyMesh.H" - - objectRegistry registry(runTime); - -/* labelList patchStarts(mesh.boundaryMesh().size()); - labelList patchSizes(mesh.boundaryMesh().size()); - - forAll(mesh.boundaryMesh(), patchI) - { - patchStarts[patchI] = mesh.boundaryMesh()[patchI].start(); - patchSizes[patchI] = mesh.boundaryMesh()[patchI].size(); - } - - polyMeshGen pmg - ( - registry, - mesh.points(), - mesh.faces(), - mesh.cells(), - mesh.boundaryMesh().names(), - patchStarts, - patchSizes - ); -*/ - polyMeshGen pmg(registry); - pmg.read(); - //writeMeshEnsight(pmg, "meshWithoutBndLayers"); - - boundaryLayers bndLayers(pmg); - //bndLayers.addLayerForPatch("inlet"); - //bndLayers.addLayerForPatch("symmetryplane"); - //bndLayers.createOTopologyLayers(); - bndLayers.addLayerForAllPatches(); - - //pmg.write(); - //meshOctree* octreePtr = NULL; - //meshOptimizer(*octreePtr, pmg).preOptimize(); - - writeMeshEnsight(pmg, "meshWithBndLayers"); - //pmg.addressingData().checkMesh(true); - + + polyMeshGen pmg(runTime); + pmg.read(); + + IOdictionary meshDict + ( + IOobject + ( + "meshDict", + runTime.system(), + runTime, + IOobject::MUST_READ, + IOobject::NO_WRITE + ) + ); + + //boundaryLayers bndLayers(pmg); + //bndLayers.addLayerForPatch("inlet"); + //bndLayers.addLayerForPatch("symmetryplane"); + //bndLayers.createOTopologyLayers(); + //bndLayers.addLayerForAllPatches(); + + Info << "Starting bnd layer refinement " + << runTime.elapsedClockTime() << endl; + + //polyMeshGenChecks::checkMesh(pmg, true); + + refineBoundaryLayers refLayers(pmg); + + refineBoundaryLayers::readSettings(meshDict, refLayers); + + refLayers.refineLayers(); + + Info << "Finished with bnd layer refinement " + << runTime.elapsedClockTime() << endl; + + polyMeshGenChecks::checkMesh(pmg, true); + return 0; + pmg.write(); + //meshOctree* octreePtr = NULL; + //meshOptimizer(*octreePtr, pmg).preOptimize(); + + //pmg.addressingData().checkMesh(true); + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testCartesianMeshExtractor/Make/options b/testingInterfaces/testCartesianMeshExtractor/Make/options index 0fa7a4adb3c4b15013f80f1b3773f0124d78fb17..5206b3c7c0f2a6eacab0bd746cfd2488e3563452 100644 --- a/testingInterfaces/testCartesianMeshExtractor/Make/options +++ b/testingInterfaces/testCartesianMeshExtractor/Make/options @@ -1,2 +1,2 @@ EXE_INC = -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude -EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools +EXE_LIBS = -lmeshLibrary -ltriSurface -lmeshTools diff --git a/testingInterfaces/testCartesianMeshExtractor/testCartesianMeshExtractor.C b/testingInterfaces/testCartesianMeshExtractor/testCartesianMeshExtractor.C index 955c6eff980a81e95b18256293d3eb06d6ad7db2..5dae2c706fdaefbd2708af8ce4282d65f680a5bf 100644 --- a/testingInterfaces/testCartesianMeshExtractor/testCartesianMeshExtractor.C +++ b/testingInterfaces/testCartesianMeshExtractor/testCartesianMeshExtractor.C @@ -38,8 +38,6 @@ Description #include "polyMeshGen.H" #include "cartesianMeshExtractor.H" #include "triSurf.H" -#include "writeMeshEnsight.H" -#include "writeOctreeFPMA.H" #include <sstream> @@ -53,8 +51,8 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - IOdictionary meshDict + + IOdictionary meshDict ( IOobject ( @@ -65,51 +63,61 @@ int main(int argc, char *argv[]) IOobject::NO_WRITE ) ); - - fileName surfaceFile = meshDict.lookup("surfaceFile"); + + fileName surfaceFile = meshDict.lookup("surfaceFile"); if( Pstream::parRun() ) - surfaceFile = ".."/surfaceFile; + surfaceFile = ".."/surfaceFile; triSurf surf(runTime.path()/surfaceFile); - - if( meshDict.found("subsetFileName") ) - { - fileName subsetFileName = meshDict.lookup("subsetFileName"); - if( Pstream::parRun() ) - subsetFileName = ".."/subsetFileName; - surf.readFaceSubsets(runTime.path()/subsetFileName); - } - - // construct the octree + + // construct the octree meshOctree mo(surf); - meshOctreeCreator(mo, meshDict).createOctreeBoxes(); - - meshOctreeAutomaticRefinement(mo, meshDict, false).automaticRefinement(); - - writeOctreeFPMA(mo, "refOctree"); - - Info<< "Execution time for octree creation = " + meshOctreeCreator moc(mo, meshDict); + moc.createOctreeBoxes(); + + //meshOctreeAutomaticRefinement(mo, meshDict, false).automaticRefinement(); + + Info<< "Execution time for octree creation = " << runTime.elapsedCpuTime() << " s\n" << endl << endl; - - polyMeshGen pmg(runTime); - cartesianMeshExtractor cmg(mo, meshDict, pmg); - - //cmg.decomposeSplitHexes(); - cmg.createMesh(); - + + polyMeshGen pmg(runTime); + cartesianMeshExtractor cmg(mo, meshDict, pmg); + + //cmg.decomposeSplitHexes(); + cmg.createMesh(); + + const pointFieldPMG& points = pmg.points(); +/* forAll(points, pointI) + { + const point p = points[pointI]; + for(label pointJ=pointI+1;pointJ<points.size();++pointJ) + if( mag(p - points[pointJ]) < 1e-10 ) + Info << "Points " << pointI << " and " << pointJ + << " are duplicates " << endl; + } +*/ + boolList usedPoint(points.size()); + const faceListPMG& faces = pmg.faces(); + forAll(faces, faceI) + { + const face& f = faces[faceI]; + + forAll(f, pI) + usedPoint[f[pI]] = true; + } + + forAll(usedPoint, pointI) + if( !usedPoint[pointI] ) + Info << "Point " << pointI << " is not used !!" << endl; + pmg.write(); - + /* if( Pstream::parRun() ) { std::ostringstream ss; - ss << Pstream::myProcNo(); - writeMeshEnsight(pmg, "cartesianMesh"+ss.str()); + ss << Pstream::myProcNo(); } - else - { - writeMeshEnsight(pmg, "cartesianMesh"); - } */ Info << "End\n" << endl; return 0; diff --git a/testingInterfaces/testCellSurfaceIntersections/Make/files b/testingInterfaces/testCellSurfaceIntersections/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..5a72ec194e685f1ba6bfa759043cfd7e05d1e49f --- /dev/null +++ b/testingInterfaces/testCellSurfaceIntersections/Make/files @@ -0,0 +1,4 @@ + +testCellSurfaceIntersections.C + +EXE = $(FOAM_USER_APPBIN)/testCellSurfaceIntersections diff --git a/testingInterfaces/testCellSurfaceIntersections/Make/options b/testingInterfaces/testCellSurfaceIntersections/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..0fa7a4adb3c4b15013f80f1b3773f0124d78fb17 --- /dev/null +++ b/testingInterfaces/testCellSurfaceIntersections/Make/options @@ -0,0 +1,2 @@ +EXE_INC = -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/GUI/meshGenGUI/meshGenGUIBndLayers.C b/testingInterfaces/testCellSurfaceIntersections/testCellSurfaceIntersections.C similarity index 50% rename from GUI/meshGenGUI/meshGenGUIBndLayers.C rename to testingInterfaces/testCellSurfaceIntersections/testCellSurfaceIntersections.C index 01f407e2f7f1b2214644e32c05e557f73464c391..a007a572dcc79bad851915a4ca7436430c4a5337 100644 --- a/GUI/meshGenGUI/meshGenGUIBndLayers.C +++ b/testingInterfaces/testCellSurfaceIntersections/testCellSurfaceIntersections.C @@ -22,81 +22,77 @@ License along with OpenFOAM; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +Application + Test of the cartesian mesh + Description + - creates an octree and creates cartesian mesh \*---------------------------------------------------------------------------*/ -#include "meshGenGUI.H" +#include "argList.H" +#include "meshOctreeCreator.H" +#include "meshOctreeAutomaticRefinement.H" +#include "Time.H" +#include "polyMesh.H" +#include "polyMeshGen.H" +#include "triSurf.H" +#include "findCellsIntersectingSurface.H" -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +#include <sstream> -namespace Foam -{ +using namespace Foam; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -bool meshGenGUI::bndLayersEntryExist() const -{ - return meshDict_.found("boundaryLayers"); -} +// Main program: -void meshGenGUI::addBndLayersPatches(const word& pName) +int main(int argc, char *argv[]) { - if( bndLayersEntryExist() ) - { - wordList pList(meshDict_.lookup("boundaryLayers")); - - const label size = pList.size(); - pList.setSize(size + 1); - pList[size] = pName; - - meshDict_.remove("boundaryLayers"); - meshDict_.add("boundaryLayers", pList); - } - else - { - wordList pList(1); - pList[0] = pName; - - meshDict_.add("boundaryLayers", pList); - } +# include "setRootCase.H" +# include "createTime.H" + + IOdictionary meshDict + ( + IOobject + ( + "meshDict", + runTime.system(), + runTime, + IOobject::MUST_READ, + IOobject::NO_WRITE + ) + ); + + fileName surfaceFile = meshDict.lookup("surfaceFile"); + if( Pstream::parRun() ) + surfaceFile = ".."/surfaceFile; + + triSurf surf(runTime.path()/surfaceFile); + +/* if( meshDict.found("subsetFileName") ) + { + fileName subsetFileName = meshDict.lookup("subsetFileName"); + if( Pstream::parRun() ) + subsetFileName = ".."/subsetFileName; + surf.readFaceSubsets(runTime.path()/subsetFileName); + } +*/ + // construct the octree + meshOctree mo(surf); + meshOctreeCreator(mo, meshDict).createOctreeBoxes(); + + polyMeshGen pmg(runTime); + pmg.read(); + + findCellsIntersectingSurface ss(pmg, mo); + ss.addIntersectedCellsToSubset("intersectedCells"); + + pmg.write(); + + Info << "End\n" << endl; + return 0; } -void meshGenGUI::removeBndLayersPatches(const word& pName) -{ - if( bndLayersEntryExist() ) - { - wordList pList(meshDict_.lookup("boundaryLayers")); - - label pos(-1); - forAll(pList, elI) - if( pList[elI] == pName ) - { - pos = elI; - break; - } - - pList[pos] = pList[pList.size() - 1]; - pList.setSize(pList.size() - 1); - - meshDict_.remove("boundaryLayers"); - - if( pList.size() != 0 ) - meshDict_.add("boundaryLayers", pList); - } -} - -wordList meshGenGUI::keepBndLayersPatches() const -{ - if( !bndLayersEntryExist() ) - return wordList(); - - wordList pNames(meshDict_.lookup("boundaryLayers")); - return pNames; -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -} // End namespace Foam // ************************************************************************* // diff --git a/testingInterfaces/testChainFromEdges/testChainFromEdges.C b/testingInterfaces/testChainFromEdges/testChainFromEdges.C index ce4f337319ce860e3cc528550821645242b6fb25..17ad38a761a76223a06b615cc37b286218ad26ef 100644 --- a/testingInterfaces/testChainFromEdges/testChainFromEdges.C +++ b/testingInterfaces/testChainFromEdges/testChainFromEdges.C @@ -40,25 +40,25 @@ using namespace Foam; int main(int argc, char *argv[]) { - DynList<edge> bEdges; - bEdges.append(edge(33, 34)); - bEdges.append(edge(33, 12)); - bEdges.append(edge(34, 12)); - bEdges.append(edge(12, 35)); - bEdges.append(edge(40, 41)); - bEdges.append(edge(40, 12)); - bEdges.append(edge(41, 36)); - bEdges.append(edge(35, 36)); - - bEdges.append(edge(41, 50)); - bEdges.append(edge(48, 57)); - bEdges.append(edge(50, 57)); - bEdges.append(edge(41, 48)); - - sortEdgesIntoChains seic(bEdges); - - Info << "Sorted chains are " << seic.sortedChains() << endl; - + DynList<edge> bEdges; + bEdges.append(edge(33, 34)); + bEdges.append(edge(33, 12)); + bEdges.append(edge(34, 12)); + bEdges.append(edge(12, 35)); + bEdges.append(edge(40, 41)); + bEdges.append(edge(40, 12)); + bEdges.append(edge(41, 36)); + bEdges.append(edge(35, 36)); + + bEdges.append(edge(41, 50)); + bEdges.append(edge(48, 57)); + bEdges.append(edge(50, 57)); + bEdges.append(edge(41, 48)); + + sortEdgesIntoChains seic(bEdges); + + Info << "Sorted chains are " << seic.sortedChains() << endl; + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testConcaveCellUnfolder/testConcaveCellUnfolder.C b/testingInterfaces/testConcaveCellUnfolder/testConcaveCellUnfolder.C index 59932b86409fd88c0d68fa7c595eb6697db39f14..de8bdf759e48181ff65385fdfa680a06876ccad1 100644 --- a/testingInterfaces/testConcaveCellUnfolder/testConcaveCellUnfolder.C +++ b/testingInterfaces/testConcaveCellUnfolder/testConcaveCellUnfolder.C @@ -41,7 +41,6 @@ Description #include "dualUnfoldConcaveCells.H" #include "meshSurfaceOptimizer.H" #include "triSurf.H" -#include "writeMeshEnsight.H" using namespace Foam; @@ -54,10 +53,10 @@ int main(int argc, char *argv[]) # include "setRootCase.H" # include "createTime.H" # include "createPolyMesh.H" - - objectRegistry registry(runTime); - - IOdictionary meshDict + + objectRegistry registry(runTime); + + IOdictionary meshDict ( IOobject ( @@ -68,48 +67,47 @@ int main(int argc, char *argv[]) IOobject::NO_WRITE ) ); - - const fileName surfaceFile = meshDict.lookup("surfaceFile"); + + const fileName surfaceFile = meshDict.lookup("surfaceFile"); triSurf surf(registry.path()/surfaceFile); - // construct the octree + // construct the octree meshOctree mo(surf); - meshOctreeCreator(mo, meshDict).createOctreeWithRefinedBoundary(8); - - // construct the polyMeshGen - labelList starts(mesh.boundaryMesh().names().size()); - labelList nFacesInPatch(starts.size()); - - forAll(mesh.boundaryMesh(), patchI) - { - starts[patchI] = mesh.boundaryMesh()[patchI].start(); - nFacesInPatch[patchI] = mesh.boundaryMesh()[patchI].size(); - } - - polyMeshGen pmg - ( - registry, - mesh.points(), - mesh.faces(), - mesh.cells(), - mesh.boundaryMesh().names(), - starts, - nFacesInPatch - ); - - //- optimize surface to get rid of nearby vertices - meshSurfaceEngine* msePtr = new meshSurfaceEngine(pmg); - meshSurfaceOptimizer(*msePtr, mo).optimizeSurface(); - deleteDemandDrivenData(msePtr); - - - dualUnfoldConcaveCells(pmg, mo).unfoldInvalidCells(); - - pmg.write(); - writeMeshEnsight(pmg, "correctedEdges"); - pmg.addressingData().checkMesh(true); - + meshOctreeCreator(mo, meshDict).createOctreeWithRefinedBoundary(8); + + // construct the polyMeshGen + labelList starts(mesh.boundaryMesh().names().size()); + labelList nFacesInPatch(starts.size()); + + forAll(mesh.boundaryMesh(), patchI) + { + starts[patchI] = mesh.boundaryMesh()[patchI].start(); + nFacesInPatch[patchI] = mesh.boundaryMesh()[patchI].size(); + } + + polyMeshGen pmg + ( + registry, + mesh.points(), + mesh.faces(), + mesh.cells(), + mesh.boundaryMesh().names(), + starts, + nFacesInPatch + ); + + //- optimize surface to get rid of nearby vertices + meshSurfaceEngine* msePtr = new meshSurfaceEngine(pmg); + meshSurfaceOptimizer(*msePtr, mo).optimizeSurface(); + deleteDemandDrivenData(msePtr); + + + dualUnfoldConcaveCells(pmg, mo).unfoldInvalidCells(); + + pmg.write(); + pmg.addressingData().checkMesh(true); + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testDelaunay/testDelaunay.C b/testingInterfaces/testDelaunay/testDelaunay.C index bdb1b4ee441cb01b55450849532151303de99a7e..ca699a01f057e481495d632fbf2044c73e0a817a 100644 --- a/testingInterfaces/testDelaunay/testDelaunay.C +++ b/testingInterfaces/testDelaunay/testDelaunay.C @@ -42,28 +42,28 @@ using namespace Foam; int main(int argc, char *argv[]) { - Random ranGen(label(0)); - - DynListHP<point> points; - - scalar scale = 5; + Random ranGen(label(0)); + + DynListHP<point> points; + + scalar scale = 5; vector refPoint(10, -20, 0); - for(label i=0;i<16;++i) - points.append(scale*(ranGen.vector01() + refPoint)); - - cpuTime executionTime; - delaunayTessellation dt(points); - - for(label i=0;i<16;++i) - while( !dt.addPoint(i) ) - {} - - Info<< "ExecutionTime = " + for(label i=0;i<16;++i) + points.append(scale*(ranGen.vector01() + refPoint)); + + cpuTime executionTime; + delaunayTessellation dt(points); + + for(label i=0;i<16;++i) + while( !dt.addPoint(i) ) + {} + + Info<< "ExecutionTime = " << executionTime.elapsedCpuTime() - << " s\n" << endl << endl; - - dt.checkTessellation(); - + << " s\n" << endl << endl; + + dt.checkTessellation(); + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testDualMeshExtractor/testDualMeshExtractor.C b/testingInterfaces/testDualMeshExtractor/testDualMeshExtractor.C index 4f8fb3428bc737704e4a7742cd50d3f9dac8542d..998d4f008d0e4854d0459518ec6bd799f37f3b42 100644 --- a/testingInterfaces/testDualMeshExtractor/testDualMeshExtractor.C +++ b/testingInterfaces/testDualMeshExtractor/testDualMeshExtractor.C @@ -39,8 +39,6 @@ Description #include "polyMeshGenAddressing.H" #include "dualMeshExtractor.H" #include "triSurf.H" -#include "writeMeshEnsight.H" -#include "writeMeshFPMA.H" using namespace Foam; @@ -52,10 +50,10 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - objectRegistry registry(runTime); - - IOdictionary meshDict + + objectRegistry registry(runTime); + + IOdictionary meshDict ( IOobject ( @@ -66,28 +64,26 @@ int main(int argc, char *argv[]) IOobject::NO_WRITE ) ); - - const fileName surfaceFile = meshDict.lookup("surfaceFile"); + + const fileName surfaceFile = meshDict.lookup("surfaceFile"); triSurf surf(registry.path()/surfaceFile); - // construct the octree + // construct the octree meshOctree mo(surf); - meshOctreeCreator(mo, meshDict).createOctreeBoxes(); - - polyMeshGen pmg(registry); - - dualMeshExtractor dme(mo, meshDict, pmg); - dme.createMesh(); - - meshOptimizer mOpt(pmg); - mOpt.untangleMeshFV(); - - writeMeshEnsight(pmg, "dualMesh"); - //writeMeshFPMA(pmg, "dualMesh"); - pmg.addressingData().checkMesh(true); - pmg.write(); - + meshOctreeCreator(mo, meshDict).createOctreeBoxes(); + + polyMeshGen pmg(registry); + + dualMeshExtractor dme(mo, meshDict, pmg); + dme.createMesh(); + + meshOptimizer mOpt(pmg); + mOpt.untangleMeshFV(); + + pmg.addressingData().checkMesh(true); + pmg.write(); + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testDynList/Make/files b/testingInterfaces/testDynList/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..0b2a31c1752d42f87454f8b123a6203ec93d803a --- /dev/null +++ b/testingInterfaces/testDynList/Make/files @@ -0,0 +1,4 @@ + +testDynList.C + +EXE = $(FOAM_USER_APPBIN)/testDynList diff --git a/testingInterfaces/testDynList/Make/options b/testingInterfaces/testDynList/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..3d3f939d40d0b8f2cabed10e75ceb65e61f6aa55 --- /dev/null +++ b/testingInterfaces/testDynList/Make/options @@ -0,0 +1,2 @@ +EXE_INC = -g -ggdb -DFULLDEBUG -O0 -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/executables/dualMesh/dualMesh.C b/testingInterfaces/testDynList/testDynList.C similarity index 69% rename from executables/dualMesh/dualMesh.C rename to testingInterfaces/testDynList/testDynList.C index 3f021c348d8cc024f26f3c969b05a0700cda1134..2af2c0da9ce0ef407b85e3f8b5de5b4aeaa41688 100644 --- a/executables/dualMesh/dualMesh.C +++ b/testingInterfaces/testDynList/testDynList.C @@ -23,18 +23,17 @@ License Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA Application - Generates a dual mesh from the octree. + Test of the octree dual Description - - creates an octree and generates its dual. - - dual is used as mesh template which is the treated to conform to - - the geometry surface + - creates an octree and calculates its dual \*---------------------------------------------------------------------------*/ #include "argList.H" #include "Time.H" -#include "dualMeshGenerator.H" +#include "DynList.H" +#include "point.H" using namespace Foam; @@ -44,16 +43,34 @@ using namespace Foam; int main(int argc, char *argv[]) { -# include "setRootCase.H" -# include "createTime.H" - - dualMeshGenerator omg(runTime); - - Info<< "ExecutionTime = " << runTime.elapsedCpuTime() << " s\n" - << "ClockTime = " << runTime.elapsedClockTime() << endl; - - omg.writeMesh(); - + +//# include "setRootCase.H" +//# include "createTime.H" + + //objectRegistry registry(runTime); + + for(label i=0;i<2;++i) + { + DynList<label> dlist; + + dlist.setSize(6); + + dlist = 11; + + Info << dlist << endl; + + for(label j=0;j<150;j++) + dlist.append(j); + + Info << dlist.size() << " " << dlist.containsAtPosition(88) << endl; + + dlist.shrink(); + + dlist.setSize(10); + + Info << "dlist" << dlist << endl; + } + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testDynListHP/testDynListHP.C b/testingInterfaces/testDynListHP/testDynListHP.C index 3597691e49904030edc58a57ca359ae51d217b72..9e752fbcdc0383e393b4d90455267f6c51d64e1a 100644 --- a/testingInterfaces/testDynListHP/testDynListHP.C +++ b/testingInterfaces/testDynListHP/testDynListHP.C @@ -32,7 +32,7 @@ Description #include "argList.H" #include "Time.H" -#include "labelListPMG.H" +#include "labelLongList.H" #include "pointFieldPMG.H" #include "DynList.H" #include "FCWGraph.H" @@ -46,11 +46,11 @@ using namespace Foam; int main(int argc, char *argv[]) { - + //# include "setRootCase.H" //# include "createTime.H" - - //objectRegistry registry(runTime); + + //objectRegistry registry(runTime); for(label i=0;i<2;++i) { @@ -75,29 +75,29 @@ int main(int argc, char *argv[]) } - /* - for(label i=0;i<2;i++) - { - DynListHP<point*> l1; + /* + for(label i=0;i<2;i++) + { + DynListHP<point*> l1; - labelListPMG l2(1000000, 15); - - l2.append(13); - l2.append(18); - l2.shrink(); + labelLongList l2(1000000, 15); + + l2.append(13); + l2.append(18); + l2.shrink(); for(label i=0;i<10000000;++i) l2.append(i); - - //Info << "l2 " << l2 << endl; - - DynListHP<point> points(100000); - forAll(points, pI) - points[pI] = point(pI+1, pI+2, pI+3); - - points.append(point(1, 0, 0)); - points.append(point(15, 5, 3)); - points.append(point(2, 3, 1)); + + //Info << "l2 " << l2 << endl; + + DynListHP<point> points(100000); + forAll(points, pI) + points[pI] = point(pI+1, pI+2, pI+3); + + points.append(point(1, 0, 0)); + points.append(point(15, 5, 3)); + points.append(point(2, 3, 1)); FCWGraph<label, 8> lg(10000000); forAll(lg, i) @@ -105,15 +105,15 @@ int main(int argc, char *argv[]) FixedList<label, 8> lst(10); lg.setRow(i, lst); } - - forAll(points, pI) - l1.append(&points[pI]); - } + + forAll(points, pI) + l1.append(&points[pI]); + } if( Pstream::parRun() ) { Pout << "Here" << endl; - labelListPMG data; + labelLongList data; if( Pstream::myProcNo() == 0 ) { data.setSize(100); @@ -131,7 +131,7 @@ int main(int argc, char *argv[]) Pout << "Values " << d << endl; } } - */ + */ Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testFacesFromChain/testFacesFromChain.C b/testingInterfaces/testFacesFromChain/testFacesFromChain.C index 51622a8184379e83b9d1150f1c42f725df24954f..dcdfe1ca5acc796bf86f31e8b510e50f4b7c8444 100644 --- a/testingInterfaces/testFacesFromChain/testFacesFromChain.C +++ b/testingInterfaces/testFacesFromChain/testFacesFromChain.C @@ -40,54 +40,54 @@ using namespace Foam; int main(int argc, char *argv[]) { - labelList chainPoints(10); - forAll(chainPoints, pI) - chainPoints[pI] = pI; - - List<DynList<label> > pointPatches(10); - pointPatches[0].append(1); - pointPatches[0].append(2); - - pointPatches[1].append(2); - - pointPatches[2].append(2); - pointPatches[2].append(3); - - pointPatches[3].append(3); - - pointPatches[4].append(2); - pointPatches[4].append(3); - - pointPatches[5].append(2); - - pointPatches[6].append(0); - pointPatches[6].append(2); - - pointPatches[7].append(0); + labelList chainPoints(10); + forAll(chainPoints, pI) + chainPoints[pI] = pI; + + List<DynList<label> > pointPatches(10); + pointPatches[0].append(1); + pointPatches[0].append(2); + + pointPatches[1].append(2); + + pointPatches[2].append(2); + pointPatches[2].append(3); + + pointPatches[3].append(3); + + pointPatches[4].append(2); + pointPatches[4].append(3); + + pointPatches[5].append(2); + + pointPatches[6].append(0); + pointPatches[6].append(2); + + pointPatches[7].append(0); - pointPatches[8].append(0); - pointPatches[8].append(1); - - pointPatches[9].append(1); - - boundaryFacesGenerator::createFacesFromChain cffc - ( - chainPoints, - pointPatches - ); - - cffc.createFacesWithoutACorner(); - - Info << "1. Created faces are " << cffc.createdFaces() << endl; - Info << "1. Face patches " << cffc.faceRegion() << endl; - Info << "1. Unresolved points " << cffc.unresolvedPoints() << endl; - - cffc.createFacesWithACorner(10); - - Info << "2. Created faces are " << cffc.createdFaces() << endl; - Info << "2. Face patches " << cffc.faceRegion() << endl; - Info << "2. Unresolved points " << cffc.unresolvedPoints() << endl; - + pointPatches[8].append(0); + pointPatches[8].append(1); + + pointPatches[9].append(1); + + boundaryFacesGenerator::createFacesFromChain cffc + ( + chainPoints, + pointPatches + ); + + cffc.createFacesWithoutACorner(); + + Info << "1. Created faces are " << cffc.createdFaces() << endl; + Info << "1. Face patches " << cffc.faceRegion() << endl; + Info << "1. Unresolved points " << cffc.unresolvedPoints() << endl; + + cffc.createFacesWithACorner(10); + + Info << "2. Created faces are " << cffc.createdFaces() << endl; + Info << "2. Face patches " << cffc.faceRegion() << endl; + Info << "2. Unresolved points " << cffc.unresolvedPoints() << endl; + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testFrontalMarking/Make/files b/testingInterfaces/testFrontalMarking/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..713f3682902f4aba64d7e850b630d88e95199765 --- /dev/null +++ b/testingInterfaces/testFrontalMarking/Make/files @@ -0,0 +1,4 @@ + +testFrontalMarking.C + +EXE = $(FOAM_USER_APPBIN)/testFrontalMarking diff --git a/testingInterfaces/testFrontalMarking/Make/options b/testingInterfaces/testFrontalMarking/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..013002936aa6f69bde71ccc7f3bf4a211015a867 --- /dev/null +++ b/testingInterfaces/testFrontalMarking/Make/options @@ -0,0 +1,7 @@ +EXE_INC = \ + -DUSE_OMP -g -ggdb -DFULLDEBUG -O0 \ + -I$(LIB_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude \ + -I../../meshLibrary/lnInclude + +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/testingInterfaces/testFrontalMarking/testFrontalMarking.C b/testingInterfaces/testFrontalMarking/testFrontalMarking.C new file mode 100644 index 0000000000000000000000000000000000000000..6d37d8546f003284eef4b133054c783fc1781f9c --- /dev/null +++ b/testingInterfaces/testFrontalMarking/testFrontalMarking.C @@ -0,0 +1,292 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2 of the License, or (at your + option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM; if not, write to the Free Software Foundation, + Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + +Application + Test of the cartesian mesh + +Description + - creates an octree and creates cartesian mesh + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "meshOctreeCreator.H" +#include "meshOctreeAutomaticRefinement.H" +#include "Time.H" +#include "polyMesh.H" +#include "polyMeshGen.H" +#include "cartesianMeshExtractor.H" +#include "triSurf.H" +#include "helperFunctions.H" +#include "findCellsIntersectingSurface.H" + +#include <sstream> + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +//- find octree leaves connected over faces +class octreeNeighbours +{ + const meshOctree& octree_; + +public: + + octreeNeighbours(const meshOctree& octree) + : + octree_(octree) + {} + + label size() const + { + return octree_.numberOfLeaves(); + } + + void operator()(const label leafI, DynList<label>& neighbours) const + { + octree_.findNeighboursForLeaf(leafI, neighbours); + } +}; + +class octreeSelectOperator +{ + const meshOctree& octree_; + +public: + + octreeSelectOperator(const meshOctree& octree) + : + octree_(octree) + {} + + bool operator()(const label leafI) const + { + if( octree_.returnLeaf(leafI).cubeType() & meshOctreeCube::DATA ) + return false; + + return true; + } +}; + +class meshNeighbourOperator +{ + const polyMeshGen& mesh_; + +public: + + meshNeighbourOperator(const polyMeshGen& mesh) + : + mesh_(mesh) + {} + + label size() const + { + return mesh_.cells().size(); + } + + void operator()(const label cellI, DynList<label>& neighbourCells) const + { + neighbourCells.clear(); + + const labelList& owner = mesh_.owner(); + const labelList& neighbour = mesh_.neighbour(); + + const cell& c = mesh_.cells()[cellI]; + + forAll(c, fI) + { + label nei = owner[c[fI]]; + + if( nei == cellI ) + nei = neighbour[c[fI]]; + + if( nei >= 0 ) + neighbourCells.append(nei); + } + } + + template<class labelListType> + void collectGroups + ( + std::map<label, DynList<label> >& neiGroups, + const labelListType& elementInGroup, + const DynList<label>& localGroupLabel + ) const + { + const PtrList<processorBoundaryPatch>& procBoundaries = + mesh_.procBoundaries(); + const labelList& owner = mesh_.owner(); + + //- send the data to other processors + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + const label size = procBoundaries[patchI].patchSize(); + + labelList groupOwner(procBoundaries[patchI].patchSize()); + for(label faceI=0;faceI<size;++faceI) + { + const label groupI = elementInGroup[owner[start+faceI]]; + + if( groupI < 0 ) + { + groupOwner[faceI] = -1; + continue; + } + + groupOwner[faceI] = localGroupLabel[groupI]; + } + + OPstream toOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo(), + groupOwner.byteSize() + ); + + toOtherProc << groupOwner; + } + + //- receive data from other processors + forAll(procBoundaries, patchI) + { + const label start = procBoundaries[patchI].patchStart(); + + labelList receivedData; + + IPstream fromOtherProc + ( + Pstream::blocking, + procBoundaries[patchI].neiProcNo() + ); + + fromOtherProc >> receivedData; + + forAll(receivedData, faceI) + { + if( receivedData[faceI] < 0 ) + continue; + + const label groupI = elementInGroup[owner[start+faceI]]; + + if( groupI < 0 ) + continue; + + DynList<label>& ng = neiGroups[localGroupLabel[groupI]]; + + //- store the connection over the inter-processor boundary + ng.appendIfNotIn(receivedData[faceI]); + } + } + } +}; + +class meshSelectorOperator +{ + const VRWGraph& patchesIntersectingCell_; + +public: + + meshSelectorOperator(const VRWGraph& patchesIntersectingCell) + : + patchesIntersectingCell_(patchesIntersectingCell) + {} + + bool operator()(const label cellI) const + { + if( patchesIntersectingCell_[cellI].size() ) + return false; + + return true; + } +}; + +// Main program: + +int main(int argc, char *argv[]) +{ +# include "setRootCase.H" +# include "createTime.H" + + IOdictionary meshDict + ( + IOobject + ( + "meshDict", + runTime.system(), + runTime, + IOobject::MUST_READ, + IOobject::NO_WRITE + ) + ); + + fileName surfaceFile = meshDict.lookup("surfaceFile"); + if( Pstream::parRun() ) + surfaceFile = ".."/surfaceFile; + + triSurf surf; + surf.readSurface(runTime.path()/surfaceFile); + + // construct the octree + meshOctree mo(surf); + meshOctreeCreator(mo).createOctreeWithRefinedBoundary(10, 30); + + //- create and read the mesh + polyMeshGen pmg(runTime); + pmg.read(); + + //- find cells intersecting surface + findCellsIntersectingSurface fis(pmg, mo); + + meshNeighbourOperator mnop(pmg); + meshSelectorOperator msop(fis.facetsIntersectingCells()); + + labelLongList result; + help::frontalMarking(result, 0, mnop, msop); + Info << "Cells in the group " << result.size() << endl; + + const label nGroups = help::groupMarking(result, mnop, msop); + + Info << "Number of groups " << nGroups << endl; + labelList groupId(nGroups); + forAll(groupId, i) + groupId[i] = pmg.addCellSubset("group_"+help::scalarToText(i)); + + forAll(result, cellI) + { + if( result[cellI] < 0 ) + continue; + + pmg.addCellToSubset(groupId[result[cellI]], cellI); + } + + pmg.write(); + + Info << "End\n" << endl; + return 0; +} + + +// ************************************************************************* // diff --git a/testingInterfaces/testGraph/testGraph.C b/testingInterfaces/testGraph/testGraph.C index 8fef37c80efa454a46513f5ac813a3ec7f7de891..f318cc825f1235536ff0841c06c0496d82650735 100644 --- a/testingInterfaces/testGraph/testGraph.C +++ b/testingInterfaces/testGraph/testGraph.C @@ -45,7 +45,7 @@ using namespace Foam; int main(int argc, char *argv[]) { - + //# include "setRootCase.H" //# include "createTime.H" @@ -97,7 +97,7 @@ int main(int argc, char *argv[]) //Info << "Orig graph " << origGraph << endl; //Info << "Reversed graph " << reverse << endl; - + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testMaterialDetector/testMaterialDetector.C b/testingInterfaces/testMaterialDetector/testMaterialDetector.C index b9043521d4c16eebd6b8dec0bef9734fa3d70bab..8d8873aa6192dcf025964d9245708b87f2a726de 100644 --- a/testingInterfaces/testMaterialDetector/testMaterialDetector.C +++ b/testingInterfaces/testMaterialDetector/testMaterialDetector.C @@ -34,7 +34,6 @@ Description #include "Time.H" #include "triSurf.H" #include "triSurfaceDetectMaterials.H" -#include "writeMeshEnsight.H" #include <sstream> @@ -48,8 +47,8 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - IOdictionary meshDict + + IOdictionary meshDict ( IOobject ( @@ -60,19 +59,19 @@ int main(int argc, char *argv[]) IOobject::NO_WRITE ) ); - - fileName surfaceFile = meshDict.lookup("surfaceFile"); + + fileName surfaceFile = meshDict.lookup("surfaceFile"); if( Pstream::parRun() ) - surfaceFile = ".."/surfaceFile; + surfaceFile = ".."/surfaceFile; triSurf surf(runTime.path()/surfaceFile); - + triSurfaceDetectMaterials detector(surf); detector.detectMaterialsAndInternalWalls(); Info << "Found " << detector.numberOfPartitions() << " partitions" << endl; Info << "Found " << detector.numberOfDomains() << " domains" << endl; detector.writeMaterials("trala.mat"); - + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testMatrix3D/Make/files b/testingInterfaces/testMatrix3D/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..bac7ab5b6148b6c44d0b8371319259b0db8ef332 --- /dev/null +++ b/testingInterfaces/testMatrix3D/Make/files @@ -0,0 +1,4 @@ + +testMatrix3D.C + +EXE = $(FOAM_USER_APPBIN)/testMatrix3D diff --git a/testingInterfaces/testMatrix3D/Make/options b/testingInterfaces/testMatrix3D/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..3d3f939d40d0b8f2cabed10e75ceb65e61f6aa55 --- /dev/null +++ b/testingInterfaces/testMatrix3D/Make/options @@ -0,0 +1,2 @@ +EXE_INC = -g -ggdb -DFULLDEBUG -O0 -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/meshLibrary/utilities/dataConversion/foamToFLMA/writeMeshFLMA.C b/testingInterfaces/testMatrix3D/testMatrix3D.C similarity index 56% rename from meshLibrary/utilities/dataConversion/foamToFLMA/writeMeshFLMA.C rename to testingInterfaces/testMatrix3D/testMatrix3D.C index 5ec66cdf92a70654a57d729b15136364efdc735f..2eeefb83f40dca55a88235fb1d4473f84c75ce40 100644 --- a/meshLibrary/utilities/dataConversion/foamToFLMA/writeMeshFLMA.C +++ b/testingInterfaces/testMatrix3D/testMatrix3D.C @@ -20,53 +20,63 @@ License You should have received a copy of the GNU General Public License along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + +Application + Test of the octree dual Description - Translates FOAM mesh to EnSight format + - creates an octree and calculates its dual \*---------------------------------------------------------------------------*/ -#include "objectRegistry.H" +#include "argList.H" #include "Time.H" -#include "polyMeshGen.H" -#include "OFstream.H" -#include "IOmanip.H" -#include "fileName.H" - -#include "flmaMesh.H" -#include "writeMeshFLMA.H" +#include "matrix3D.H" -namespace Foam -{ +using namespace Foam; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void writeMeshFLMA(const polyMeshGen& mesh, const word& fName) +// Main program: + +int main(int argc, char *argv[]) { - const Time& time = mesh.returnTime(); - - const word postProcDir = "FLMA"; - - fileName postProcPath = time.path()/postProcDir; - - if( !Foam::isDir(postProcPath) ) - { - mkDir(postProcPath); - } - - // Open the flma file - const fileName flmaFileName = fName + ".flma"; - - Info << "Writting mesh into " << flmaFileName << endl; - - OFstream flmaGeometryFile(postProcPath/flmaFileName); - - // Construct the flma mesh - flmaMesh Mesh(mesh); - Mesh.write(flmaGeometryFile); + +//# include "setRootCase.H" +//# include "createTime.H" + + //objectRegistry registry(runTime); + + for(label i=0;i<2;++i) + { + matrix3D mat; + mat[0][0] = 1.0; + mat[0][1] = 0.5; + mat[0][2] = 0.5; + mat[1][0] = 0.5; + mat[1][1] = 1.0; + mat[1][2] = 0.5; + mat[2][0] = 0.5; + mat[2][1] = 0.5; + mat[2][2] = 1.0; + + Info << "Determinant " << mat.determinant() << endl; + + Info << "Inverse matrix " << mat.inverse() << endl; + FixedList<scalar, 3> source; + source[0] = 0; + source[1] = 1; + source[2] = 2; + + FixedList<scalar, 3> sol = mat.solve(source); + + Info << "Solution " << sol << endl; + } + + Info << "End\n" << endl; + return 0; } -} // ************************************************************************* // diff --git a/testingInterfaces/testNonManifoldInterfaces/Make/files b/testingInterfaces/testNonManifoldInterfaces/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..32811e40590ddfc427590942c9c7789450d4a13f --- /dev/null +++ b/testingInterfaces/testNonManifoldInterfaces/Make/files @@ -0,0 +1,4 @@ + +testNonManifoldInterfaces.C + +EXE = $(FOAM_USER_APPBIN)/testNonManifoldInterfaces diff --git a/testingInterfaces/testNonManifoldInterfaces/Make/options b/testingInterfaces/testNonManifoldInterfaces/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..0fa7a4adb3c4b15013f80f1b3773f0124d78fb17 --- /dev/null +++ b/testingInterfaces/testNonManifoldInterfaces/Make/options @@ -0,0 +1,2 @@ +EXE_INC = -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/GUI/meshGenGUI/meshGenGUI.C b/testingInterfaces/testNonManifoldInterfaces/testNonManifoldInterfaces.C similarity index 56% rename from GUI/meshGenGUI/meshGenGUI.C rename to testingInterfaces/testNonManifoldInterfaces/testNonManifoldInterfaces.C index ec4a697e542f33db8e1e3200e53e15762ff3a645..6a5d13204328e87bd19557ae2ac87dab1683874a 100644 --- a/GUI/meshGenGUI/meshGenGUI.C +++ b/testingInterfaces/testNonManifoldInterfaces/testNonManifoldInterfaces.C @@ -22,71 +22,66 @@ License along with OpenFOAM; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +Application + Test for smoothers + Description + - reads the mesh and tries to untangle negative volume cells \*---------------------------------------------------------------------------*/ -#include "meshGenGUI.H" -#include "triSurface.H" -#include "objectRegistry.H" +#include "argList.H" +#include "findNonManifoldInterfaces.H" +#include "meshOctree.H" +#include "meshOctreeCreator.H" +#include "triSurf.H" #include "Time.H" +#include "polyMeshGen.H" -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +using namespace Foam; -namespace Foam -{ +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -// * * * * * * * * * * * * Private member functions * * * * * * * * * * * * // +// Main program: -void meshGenGUI::createSurface(const fileName& name) const +int main(int argc, char *argv[]) { - surfacePtr_ = new triSurface(name); -} +# include "setRootCase.H" +# include "createTime.H" -const triSurface& meshGenGUI::surface() const -{ - if( !surfacePtr_ ) - createSurface(surfaceFileName()); - - return *surfacePtr_; -} + polyMeshGen pmg(runTime); + pmg.read(); + + Info << "Finished reading mesh" << endl; -// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // - -// Construct from objectRegistry -meshGenGUI::meshGenGUI -( - const objectRegistry& reg -) -: - meshDict_ - ( - IOobject + IOdictionary meshDict + ( + IOobject ( "meshDict", - reg.time().system(), - reg, - IOobject::READ_IF_PRESENT, - IOobject::AUTO_WRITE + runTime.system(), + runTime, + IOobject::MUST_READ, + IOobject::NO_WRITE ) - ), - surfacePtr_(NULL) -{ - Info << meshDict_ << endl; -} + ); -// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // + const fileName surfaceFile = meshDict.lookup("surfaceFile"); -meshGenGUI::~meshGenGUI() -{ - deleteDemandDrivenData(surfacePtr_); -} + triSurf surf(runTime.path()/surfaceFile); -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + // construct the octree + meshOctree octree(surf); + meshOctreeCreator(octree, meshDict).createOctreeWithRefinedBoundary(8); + findNonManifoldInterfaces nmi(pmg, octree); + nmi.createNonManifoldInterfaces(); -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + pmg.write(); + + Info << "End\n" << endl; + return 0; +} -} // End namespace Foam // ************************************************************************* // diff --git a/testingInterfaces/testOctree/testOctree.C b/testingInterfaces/testOctree/testOctree.C index 12625c3ebb390a0d914cd239089a8eda53b756d6..07279f599cb35d5ca0d81b23b327c593f2151e9e 100644 --- a/testingInterfaces/testOctree/testOctree.C +++ b/testingInterfaces/testOctree/testOctree.C @@ -36,7 +36,6 @@ Description #include "Time.H" #include "objectRegistry.H" #include "triSurf.H" -#include "writeOctreeEnsight.H" #include <sstream> @@ -71,22 +70,24 @@ int main(int argc, char *argv[]) if( Pstream::parRun() ) surfaceFile = ".."/surfaceFile; + Info << "Reading surface from file " << surfaceFile << endl; triSurf surf(runTime.path()/surfaceFile); - if( meshDict.found("subsetFileName") ) +/* if( meshDict.found("subsetFileName") ) { fileName subsetFileName = meshDict.lookup("subsetFileName"); if( Pstream::parRun() ) subsetFileName = ".."/subsetFileName; surf.readFaceSubsets(runTime.path()/subsetFileName); } +*/ - surf.edgeFaces(); - surf.faceEdges(); + surf.edgeFacets(); + surf.facetEdges(); const scalar startTime = runTime.elapsedClockTime(); - meshOctree* moPtr = new meshOctree(surf); + meshOctree* moPtr = new meshOctree(surf, true); meshOctreeCreator* mcPtr = new meshOctreeCreator(*moPtr, meshDict); mcPtr->createOctreeBoxes(); deleteDemandDrivenData(mcPtr); @@ -104,25 +105,7 @@ int main(int argc, char *argv[]) << " and " << moPtr->returnLeaf(i-1).coordinates() << abort(FatalError); } - /* if( Pstream::parRun() ) - { - std::ostringstream ss; - - ss << Pstream::myProcNo(); - - //writeOctreeEnsight(*moPtr, "insideBoxes"+ss.str(), meshOctreeCube::INSIDE); - //writeOctreeEnsight(*moPtr, "unknownBoxes"+ss.str(), meshOctreeCube::UNKNOWN); - //writeOctreeEnsight(*moPtr, "outsideBoxes"+ss.str(), meshOctreeCube::OUTSIDE); - writeOctreeEnsight(*moPtr, "dataBoxes"+ss.str(), meshOctreeCube::DATA); - } - else - { - writeOctreeEnsight(*moPtr, "insideBoxes", meshOctreeCube::INSIDE); - //writeOctreeEnsight(*moPtr, "unknownBoxes", meshOctreeCube::UNKNOWN); - writeOctreeEnsight(*moPtr, "outsideBoxes", meshOctreeCube::OUTSIDE); - writeOctreeEnsight(*moPtr, "dataBoxes", meshOctreeCube::DATA); - } - */ + deleteDemandDrivenData(moPtr); Info<< "Execution time for octree creation = " diff --git a/testingInterfaces/testParallelMesh/testParallelMesh.C b/testingInterfaces/testParallelMesh/testParallelMesh.C index 329eac95e45ebe1a68a02c249fffa817cd48f85a..4c0e21eda48fce362990589fac6493801f416c4c 100644 --- a/testingInterfaces/testParallelMesh/testParallelMesh.C +++ b/testingInterfaces/testParallelMesh/testParallelMesh.C @@ -37,7 +37,6 @@ Description #include "polyMeshGen.H" #include "surfaceMorpherCells.H" #include "topologicalCleaner.H" -#include "writeMeshEnsight.H" #include "polyMeshGenAddressing.H" using namespace Foam; @@ -50,20 +49,20 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - polyMeshGen pmg(runTime); - pmg.read(); - + + polyMeshGen pmg(runTime); + pmg.read(); + //- test number of nodes per processor face const pointFieldPMG& points = pmg.points(); const faceListPMG& faces = pmg.faces(); - const PtrList<writeProcessorPatch>& procBoundaries = + const PtrList<processorBoundaryPatch>& procBoundaries = pmg.procBoundaries(); - + //- check face count const label nIntFaces = pmg.nInternalFaces(); label nBndFaces(0); - const PtrList<writePatch>& boundaries = pmg.boundaries(); + const PtrList<boundaryPatch>& boundaries = pmg.boundaries(); forAll(boundaries, patchI) nBndFaces += boundaries[patchI].patchSize(); label nProcFaces(0); @@ -72,17 +71,17 @@ int main(int argc, char *argv[]) if( (nIntFaces+nBndFaces+nProcFaces) != faces.size() ) FatalError << "Number of faces is not correct!" << abort(FatalError); - + //- check if the centres of the proc patch match forAll(procBoundaries, patchI) { vectorField cents(procBoundaries[patchI].patchSize()); - + const label start = procBoundaries[patchI].patchStart(); const label end = start + cents.size(); for(label faceI=start;faceI<end;++faceI) cents[faceI-start] = faces[faceI].centre(points); - + OPstream toOtherProc ( Pstream::nonBlocking, @@ -90,7 +89,7 @@ int main(int argc, char *argv[]) ); toOtherProc << cents; } - + forAll(procBoundaries, patchI) { vectorField otherCentres; @@ -100,7 +99,7 @@ int main(int argc, char *argv[]) procBoundaries[patchI].neiProcNo() ); fromOtherProc >> otherCentres; - + const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); for(label faceI=start;faceI<end;++faceI) @@ -115,7 +114,7 @@ int main(int argc, char *argv[]) Serr << "Face centres do not match!" << endl; } } - + //- check number of vertices in proc-boundary faces forAll(procBoundaries, patchI) { @@ -124,7 +123,7 @@ int main(int argc, char *argv[]) const label end = start + nVrtPerFace.size(); for(label faceI=start;faceI<end;++faceI) nVrtPerFace[faceI-start] = faces[faceI].size(); - + OPstream toOtherProc ( Pstream::nonBlocking, @@ -132,7 +131,7 @@ int main(int argc, char *argv[]) ); toOtherProc << nVrtPerFace; } - + forAll(procBoundaries, patchI) { labelList nVrtPerFace; @@ -142,21 +141,21 @@ int main(int argc, char *argv[]) procBoundaries[patchI].neiProcNo() ); fromOtherProc >> nVrtPerFace; - + label nTotalNei(0); forAll(nVrtPerFace, fI) nTotalNei += nVrtPerFace[fI]; - + label nTotalOwn(0); - + const label start = procBoundaries[patchI].patchStart(); const label end = start + nVrtPerFace.size(); for(label faceI=start;faceI<end;++faceI) nTotalOwn += faces[faceI].size(); - + if( nTotalNei != nTotalOwn ) Serr << "Patches do not contain same number of points!" << endl; - + for(label faceI=start;faceI<end;++faceI) if( nVrtPerFace[faceI-start] != faces[faceI].size() ) { @@ -170,7 +169,7 @@ int main(int argc, char *argv[]) << abort(FatalError); } } - + //- test if vertices of processor boundaries match forAll(procBoundaries, patchI) { @@ -179,7 +178,7 @@ int main(int argc, char *argv[]) label nPointsToSend(0); for(label faceI=start;faceI<end;++faceI) nPointsToSend += faces[faceI].size(); - + pointField pointsToSend(nPointsToSend); nPointsToSend = 0; for(label faceI=start;faceI<end;++faceI) @@ -188,7 +187,7 @@ int main(int argc, char *argv[]) forAll(f, pI) pointsToSend[nPointsToSend++] = points[f[pI]]; } - + OPstream toOtherProc ( Pstream::nonBlocking, @@ -196,18 +195,18 @@ int main(int argc, char *argv[]) ); toOtherProc << pointsToSend; } - + forAll(procBoundaries, patchI) { pointField pointsToReceive; - + IPstream fromOtherProc ( Pstream::nonBlocking, procBoundaries[patchI].neiProcNo() ); fromOtherProc >> pointsToReceive; - + label counter(0); const label start = procBoundaries[patchI].patchStart(); const label end = start + procBoundaries[patchI].patchSize(); @@ -224,8 +223,8 @@ int main(int argc, char *argv[]) << patchI << " is not correct!" << abort(FatalError); } } - } - + } + /* Serr << Pstream::myProcNo() << "Global point labels " << pmg.addressingData().globalPointLabel() << endl; Serr << Pstream::myProcNo() << "Point procs " diff --git a/testingInterfaces/testRenumberMesh/testRenumberMesh.C b/testingInterfaces/testRenumberMesh/testRenumberMesh.C index 937983e8c43a7ca5a581123e69a43b7cf8f800e0..5b1d09327099d531961dd491a9b93ad987e706b3 100644 --- a/testingInterfaces/testRenumberMesh/testRenumberMesh.C +++ b/testingInterfaces/testRenumberMesh/testRenumberMesh.C @@ -46,43 +46,43 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - objectRegistry registry(runTime); - - polyMeshGen pmg(registry); - pmg.read(); - - const labelList& owner = pmg.owner(); - const labelList& neighbour = pmg.neighbour(); - - label band(0); - forAll(owner, fI) - { - const label diff = neighbour[fI] - owner[fI]; - if( diff > band ) - band = diff; - } - - Info << "Band before renumbering is " << band << endl; - - polyMeshGenModifier(pmg).renumberMesh(); - - const labelList& newOwner = pmg.owner(); - const labelList& newNeighbour = pmg.neighbour(); - band = 0; - forAll(newOwner, fI) - { - const label diff = newNeighbour[fI] - newOwner[fI]; - if( diff > band ) - band = diff; - } - - Info << "Band after renumbering is " << band << endl; - - pmg.addressingData().checkMesh(true); - - //pmg.write(); - + + objectRegistry registry(runTime); + + polyMeshGen pmg(registry); + pmg.read(); + + const labelList& owner = pmg.owner(); + const labelList& neighbour = pmg.neighbour(); + + label band(0); + forAll(owner, fI) + { + const label diff = neighbour[fI] - owner[fI]; + if( diff > band ) + band = diff; + } + + Info << "Band before renumbering is " << band << endl; + + polyMeshGenModifier(pmg).renumberMesh(); + + const labelList& newOwner = pmg.owner(); + const labelList& newNeighbour = pmg.neighbour(); + band = 0; + forAll(newOwner, fI) + { + const label diff = newNeighbour[fI] - newOwner[fI]; + if( diff > band ) + band = diff; + } + + Info << "Band after renumbering is " << band << endl; + + pmg.addressingData().checkMesh(true); + + //pmg.write(); + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testSurfaceEdgeExtractor/testSurfaceEdgeExtractor.C b/testingInterfaces/testSurfaceEdgeExtractor/testSurfaceEdgeExtractor.C index 65f3bd60fff030997711faa298519ba9adfd5676..3275f3e8eef670b56586dd6c58513f6a8fa906e1 100644 --- a/testingInterfaces/testSurfaceEdgeExtractor/testSurfaceEdgeExtractor.C +++ b/testingInterfaces/testSurfaceEdgeExtractor/testSurfaceEdgeExtractor.C @@ -37,7 +37,6 @@ Description #include "meshSurfaceEngine.H" #include "meshSurfaceEdgeExtractor.H" #include "triSurf.H" -#include "writeMeshEnsight.H" using namespace Foam; @@ -49,10 +48,10 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - objectRegistry registry(runTime); - - IOdictionary meshDict + + objectRegistry registry(runTime); + + IOdictionary meshDict ( IOobject ( @@ -63,40 +62,39 @@ int main(int argc, char *argv[]) IOobject::NO_WRITE ) ); - - const fileName surfaceFile = meshDict.lookup("surfaceFile"); + + const fileName surfaceFile = meshDict.lookup("surfaceFile"); triSurf surf(registry.path()/surfaceFile); - // construct the octree + // construct the octree meshOctree mo(surf); - meshOctreeCreator(mo, meshDict).createOctreeWithRefinedBoundary(8); - - // construct the polyMeshGen - polyMeshGen pmg(registry); - pmg.read(); - - // find regions for boundary vertices - meshSurfaceEngine mse(pmg); - - labelList pointRegion(pmg.points().size(), -1); - - Info << "Finding boundary regions for boundary vertices" << endl; - const labelList& bPoints = mse.boundaryPoints(); - forAll(bPoints, bpI) - { - point& p = pmg.points()[bPoints[bpI]]; - point np; - mo.findNearestSurfacePoint(np, pointRegion[bPoints[bpI]], p); - p = np; - } - - Info << "Extracting edges" << endl; - meshSurfaceEdgeExtractor(pmg, mo, pointRegion); - - writeMeshEnsight(pmg, "meshWithEdges"); - pmg.addressingData().checkMesh(true); - + meshOctreeCreator(mo, meshDict).createOctreeWithRefinedBoundary(8); + + // construct the polyMeshGen + polyMeshGen pmg(registry); + pmg.read(); + + // find regions for boundary vertices + meshSurfaceEngine mse(pmg); + + labelList pointRegion(pmg.points().size(), -1); + + Info << "Finding boundary regions for boundary vertices" << endl; + const labelList& bPoints = mse.boundaryPoints(); + forAll(bPoints, bpI) + { + point& p = pmg.points()[bPoints[bpI]]; + point np; + mo.findNearestSurfacePoint(np, pointRegion[bPoints[bpI]], p); + p = np; + } + + Info << "Extracting edges" << endl; + meshSurfaceEdgeExtractor(pmg, mo, pointRegion); + + pmg.addressingData().checkMesh(true); + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testSurfaceMorpher/testSurfaceMorpher.C b/testingInterfaces/testSurfaceMorpher/testSurfaceMorpher.C index 0e01d1329fb0dd22ea5d01084f7866c4c1480134..3fe9fc43e9e3244c1f2815da98a551ea2ec233ca 100644 --- a/testingInterfaces/testSurfaceMorpher/testSurfaceMorpher.C +++ b/testingInterfaces/testSurfaceMorpher/testSurfaceMorpher.C @@ -37,7 +37,6 @@ Description #include "polyMeshGen.H" #include "surfaceMorpherCells.H" #include "topologicalCleaner.H" -#include "writeMeshEnsight.H" #include "meshOptimizer.H" using namespace Foam; @@ -50,21 +49,20 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - + polyMeshGen pmg(runTime); pmg.read(); - + do { surfaceMorpherCells* morpherPtr = new surfaceMorpherCells(pmg); morpherPtr->morphMesh(); deleteDemandDrivenData(morpherPtr); } while( topologicalCleaner(pmg).cleanTopology() ); - - writeMeshEnsight(pmg, "morphedMesh"); + //pmg.addressingData().checkMesh(true); pmg.write(); - + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testSurfaceOptimizer/Make/files b/testingInterfaces/testSurfaceOptimizer/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..b5d02570bd6402845b320c5dc8cad8724b510cf5 --- /dev/null +++ b/testingInterfaces/testSurfaceOptimizer/Make/files @@ -0,0 +1,4 @@ + +testSurfaceOptimizer.C + +EXE = $(FOAM_USER_APPBIN)/testSurfaceOptimizer diff --git a/testingInterfaces/testSurfaceOptimizer/Make/options b/testingInterfaces/testSurfaceOptimizer/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..0fa7a4adb3c4b15013f80f1b3773f0124d78fb17 --- /dev/null +++ b/testingInterfaces/testSurfaceOptimizer/Make/options @@ -0,0 +1,2 @@ +EXE_INC = -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/meshLibrary/utilities/dataConversion/simplexToFLMA/writeSimplexFLMA.C b/testingInterfaces/testSurfaceOptimizer/testSurfaceOptimizer.C similarity index 58% rename from meshLibrary/utilities/dataConversion/simplexToFLMA/writeSimplexFLMA.C rename to testingInterfaces/testSurfaceOptimizer/testSurfaceOptimizer.C index 8c72c657448c55059c7894c951efb01d53f3eb24..810edf928eaf554dc26cf8201fc347c1cad66daa 100644 --- a/meshLibrary/utilities/dataConversion/simplexToFLMA/writeSimplexFLMA.C +++ b/testingInterfaces/testSurfaceOptimizer/testSurfaceOptimizer.C @@ -20,51 +20,56 @@ License You should have received a copy of the GNU General Public License along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + +Application + Test for smoothers Description - Translates FOAM mesh to EnSight format + - reads the mesh and tries to untangle negative volume cells \*---------------------------------------------------------------------------*/ -#include "objectRegistry.H" +#include "argList.H" +#include "surfaceOptimizer.H" #include "Time.H" #include "polyMeshGen.H" -#include "OFstream.H" -#include "IOmanip.H" -#include "fileName.H" - -#include "simplexMesh.H" -#include "writeSimplexFLMA.H" -namespace Foam -{ +using namespace Foam; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -void writeSimplexFLMA(const partTetMeshSimplex& simplex, const word& fName) +// Main program: + +int main(int argc, char *argv[]) { - const word postProcDir = "FLMA"; + DynList<point> points; + DynList<triFace> trias; - fileName postProcPath = postProcDir; + points.append(point(-0.5, 1.2, 0)); // point which gets moved - if( !Foam::isDir(postProcPath) ) - { - mkDir(postProcPath); - } + points.append(point(0, 0, 0)); + points.append(point(1, 0, 0)); + points.append(point(1, 1, 0)); + points.append(point(0.5, -0.01, 0)); + points.append(point(0, 1, 0)); - // Open the flma file - const fileName flmaFileName = fName + ".flma"; - - Info << "Writting mesh into " << flmaFileName << endl; + Info << "Points before movement " << points << endl; - OFstream flmaGeometryFile(postProcPath/flmaFileName); - - // Construct the flma mesh - simplexMesh Mesh(simplex); - Mesh.write(flmaGeometryFile); -} + trias.append(triFace(0, 1, 2)); + trias.append(triFace(0, 2, 3)); + trias.append(triFace(0, 3, 4)); + trias.append(triFace(0, 4, 5)); + trias.append(triFace(0, 5, 1)); + + surfaceOptimizer sOpt(points, trias); + sOpt.optimizePoint(1e-3); + Info << "Points after movement " << points << endl; + + Info << "End\n" << endl; + return 0; } + // ************************************************************************* // diff --git a/testingInterfaces/testSurfaceOrientation/Make/files b/testingInterfaces/testSurfaceOrientation/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..b444f54a5d2f5bd4ead7823957d2a1df7da2ebcd --- /dev/null +++ b/testingInterfaces/testSurfaceOrientation/Make/files @@ -0,0 +1,3 @@ +testSurfaceOrientation.C + +EXE = $(FOAM_USER_APPBIN)/testSurfaceOrientation diff --git a/testingInterfaces/testSurfaceOrientation/Make/options b/testingInterfaces/testSurfaceOrientation/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..0fa7a4adb3c4b15013f80f1b3773f0124d78fb17 --- /dev/null +++ b/testingInterfaces/testSurfaceOrientation/Make/options @@ -0,0 +1,2 @@ +EXE_INC = -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/testingInterfaces/testSurfaceOrientation/testSurfaceOrientation.C b/testingInterfaces/testSurfaceOrientation/testSurfaceOrientation.C new file mode 100644 index 0000000000000000000000000000000000000000..18df3fdc30154ca0f782cf0fdb605e84d2288f6c --- /dev/null +++ b/testingInterfaces/testSurfaceOrientation/testSurfaceOrientation.C @@ -0,0 +1,121 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2 of the License, or (at your + option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM; if not, write to the Free Software Foundation, + Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + +Application + Test the triSurfaceClassifyEdges + +Description + - creates an octree and checks which edges in the surface mesh are convex + or concave + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "meshOctreeCreator.H" +#include "meshOctreeAutomaticRefinement.H" +#include "triSurfaceClassifyEdges.H" +#include "Time.H" +#include "polyMesh.H" +#include "polyMeshGen.H" +#include "cartesianMeshExtractor.H" +#include "triSurf.H" + +#include <sstream> + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +// Main program: + +int main(int argc, char *argv[]) +{ +# include "setRootCase.H" +# include "createTime.H" + + IOdictionary meshDict + ( + IOobject + ( + "meshDict", + runTime.system(), + runTime, + IOobject::MUST_READ, + IOobject::NO_WRITE + ) + ); + + fileName surfaceFile = meshDict.lookup("surfaceFile"); + if( Pstream::parRun() ) + surfaceFile = ".."/surfaceFile; + + triSurf surf(runTime.path()/surfaceFile); + + // construct the octree + meshOctree mo(surf); + meshOctreeCreator(mo, meshDict).createOctreeBoxes(); + + meshOctreeAutomaticRefinement(mo, meshDict, false).automaticRefinement(); + + Info<< "Execution time for octree creation = " + << runTime.elapsedCpuTime() + << " s\n" << endl << endl; + + triSurfaceClassifyEdges tce(mo); + const List<direction>& edgeTypes = tce.edgeTypes(); + const edgeLongList& edges = surf.edges(); + + const label featureNodes = surf.addPointSubset("featureNodes"); + const label convexId = surf.addPointSubset("convexEdges"); + const label concaveId = surf.addPointSubset("concaveEdges"); + + forAll(edgeTypes, edgeI) + { + if( !(edgeTypes[edgeI] & triSurfaceClassifyEdges::FEATUREEDGE) ) + continue; + + surf.addPointToSubset(featureNodes, edges[edgeI].start()); + surf.addPointToSubset(featureNodes, edges[edgeI].end()); + + if( edgeTypes[edgeI] & triSurfaceClassifyEdges::CONVEXEDGE ) + { + surf.addPointToSubset(convexId, edges[edgeI].start()); + surf.addPointToSubset(convexId, edges[edgeI].end()); + } + else if( edgeTypes[edgeI] & triSurfaceClassifyEdges::CONCAVEEDGE ) + { + surf.addPointToSubset(concaveId, edges[edgeI].start()); + surf.addPointToSubset(concaveId, edges[edgeI].end()); + } + } + + Info << "Writting surface to a file" << endl; + surf.writeSurface("surfWithEdgeTypes.fms"); + + Info << "End\n" << endl; + return 0; +} + + +// ************************************************************************* // diff --git a/testingInterfaces/testSurfaceSmoothing/testSurfaceSmoothing.C b/testingInterfaces/testSurfaceSmoothing/testSurfaceSmoothing.C index 3f1c8b718ccbf9ddd164683db48a2937cdb3fc0a..db2a659b60eac2758d33088dd7febfda6a5d5e23 100644 --- a/testingInterfaces/testSurfaceSmoothing/testSurfaceSmoothing.C +++ b/testingInterfaces/testSurfaceSmoothing/testSurfaceSmoothing.C @@ -38,7 +38,6 @@ Description #include "meshOctreeCreator.H" #include "triSurf.H" #include "polyMeshGen.H" -#include "writeMeshEnsight.H" using namespace Foam; @@ -50,9 +49,9 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - objectRegistry registry(runTime); - + + objectRegistry registry(runTime); + IOdictionary meshDict ( IOobject @@ -64,84 +63,26 @@ int main(int argc, char *argv[]) IOobject::NO_WRITE ) ); - + fileName surfaceFile = meshDict.lookup("surfaceFile"); if( Pstream::parRun() ) - surfaceFile = ".."/surfaceFile; + surfaceFile = ".."/surfaceFile; triSurf surf(registry.path()/surfaceFile); - - if( meshDict.found("subsetFileName") ) - { - fileName subsetFileName = meshDict.lookup("subsetFileName"); - if( Pstream::parRun() ) - subsetFileName = ".."/subsetFileName; - surf.readFaceSubsets(registry.path()/subsetFileName); - } - - // construct the octree + + // construct the octree meshOctree moc(surf); - meshOctreeCreator(moc, meshDict).createOctreeBoxes(); - - polyMeshGen pmg(registry); - pmg.read(); - - // make sure that mesh contains all surface patches - if( - Pstream::parRun() && - (pmg.patchNames().size() != surf.patches().size()) - ) - { - wordList patchNames(surf.patches().size()); - labelList patchStart(patchNames.size(), pmg.nInternalFaces()); - labelList nFacesInPatch(patchNames.size(), 0); - - forAll(patchNames, patchI) - patchNames[patchI] = surf.patches()[patchI].name(); - - forAll(pmg.patchNames(), patchI) - { - label pos(-1); - forAll(patchNames, nameI) - if( patchNames[nameI] == pmg.patchNames()[patchI] ) - { - pos = nameI; - break; - } - - nFacesInPatch[pos] = pmg.numFacesInPatch()[patchI]; - patchStart[pos] = pmg.patchStart()[patchI]; - - for(label i=pos+1;i<patchNames.size();++i) - patchStart[i] += nFacesInPatch[pos]; - } - - polyMeshGenModifier meshModifier(pmg); - meshModifier.patchNamesAccess() = patchNames; - meshModifier.patchStartAccess() = patchStart; - meshModifier.nFacesInPatchAccess() = nFacesInPatch; - } - - meshSurfaceEngine ms(pmg); - meshSurfaceOptimizer mo(ms, moc); - - /* - labelList pointRegion(pmg.points().size(), -1); - for(label faceI=mesh.nInternalFaces();faceI<pmg.faces().size();faceI++) - { - const face& f = pmg.faces()[faceI]; - - forAll(f, pI) - pointRegion[f[pI]] = 1; - } - - mo.preOptimizeSurface(pointRegion); - */ + meshOctreeCreator(moc, meshDict).createOctreeBoxes(); + + polyMeshGen pmg(registry); + pmg.read(); + + mo.optimizeSurface(); - + mo.untangleSurface(); + pmg.write(); - writeMeshEnsight(pmg, "smoothMesh"); - + Info << "End\n" << endl; return 0; } diff --git a/testingInterfaces/testVolumeOptimizer/Make/files b/testingInterfaces/testVolumeOptimizer/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..d4ed71106dbb4cb10d02fbd6a167b486bde71128 --- /dev/null +++ b/testingInterfaces/testVolumeOptimizer/Make/files @@ -0,0 +1,4 @@ + +testVolumeOptimizer.C + +EXE = $(FOAM_USER_APPBIN)/testVolumeOptimizer diff --git a/testingInterfaces/testVolumeOptimizer/Make/options b/testingInterfaces/testVolumeOptimizer/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..0fa7a4adb3c4b15013f80f1b3773f0124d78fb17 --- /dev/null +++ b/testingInterfaces/testVolumeOptimizer/Make/options @@ -0,0 +1,2 @@ +EXE_INC = -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I../../meshLibrary/lnInclude +EXE_LIBS = -lMeshLibrary -ltriSurface -lmeshTools diff --git a/testingInterfaces/testVolumeOptimizer/testVolumeOptimizer.C b/testingInterfaces/testVolumeOptimizer/testVolumeOptimizer.C new file mode 100644 index 0000000000000000000000000000000000000000..64333f6f5cef8a6d87a2d3c48a765496981f3c8c --- /dev/null +++ b/testingInterfaces/testVolumeOptimizer/testVolumeOptimizer.C @@ -0,0 +1,105 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 2 of the License, or (at your + option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM; if not, write to the Free Software Foundation, + Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + +Application + Test for smoothers + +Description + - reads the mesh and tries to untangle negative volume cells + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "volumeOptimizer.H" +#include "Time.H" +#include "polyMeshGen.H" +#include "partTetMeshSimplex.H" + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +// Main program: + +int main(int argc, char *argv[]) +{ + DynList<labelledPoint> points; + + points.append(labelledPoint(0, point(-0.5, -0.5, -1))); // point which gets moved + + points.append(labelledPoint(1, point(0, 0, 0))); + points.append(labelledPoint(2, point(1, 0, 0))); + points.append(labelledPoint(3, point(1, 1, 0))); + points.append(labelledPoint(4, point(0, 1, 0))); + + points.append(labelledPoint(5, point(0, 0, 1))); + points.append(labelledPoint(6, point(1, 0, 1))); + points.append(labelledPoint(7, point(1, 1, 1))); + points.append(labelledPoint(8, point(0, 1, 1))); + + points.append(labelledPoint(9, point(0.5, 0.25, 0.999))); + + Info << "Points before movement " << points << endl; + + DynList<parPartTet> tets; + //- tets at z = 0 + tets.append(parPartTet(points[1], points[2], points[9], points[0])); + tets.append(parPartTet(points[2], points[3], points[9], points[0])); + tets.append(parPartTet(points[3], points[4], points[9], points[0])); + tets.append(parPartTet(points[4], points[1], points[9], points[0])); + + //- tets at z = 1 + tets.append(parPartTet(points[6], points[5], points[8], points[0])); + tets.append(parPartTet(points[6], points[8], points[7], points[0])); + + //- tets at y = 0 + tets.append(parPartTet(points[2], points[1], points[5], points[0])); + tets.append(parPartTet(points[5], points[6], points[2], points[0])); + + //- tets at y = 1 + tets.append(parPartTet(points[4], points[3], points[7], points[0])); + tets.append(parPartTet(points[7], points[8], points[4], points[0])); + + //- tets at x = 0 + tets.append(parPartTet(points[5], points[1], points[4], points[0])); + tets.append(parPartTet(points[5], points[4], points[8], points[0])); + + //- tets at x = 1 + tets.append(parPartTet(points[2], points[6], points[7], points[0])); + tets.append(parPartTet(points[2], points[7], points[3], points[0])); + + partTetMeshSimplex simplex(tets, 0); + + volumeOptimizer volOpt(simplex); + + volOpt.optimizeNodePosition(1e-4); + + Info << "Points after movement " << simplex.pts() << endl; + + Info << "End\n" << endl; + return 0; +} + + +// ************************************************************************* // diff --git a/testingInterfaces/testVoronoiMeshExtractor/testVoronoiMeshExtractor.C b/testingInterfaces/testVoronoiMeshExtractor/testVoronoiMeshExtractor.C index 0a20f47e022ba4194043ef237478da7f176d15e0..1bb4f90a1d3a59d2877b7f72d6e82104352c989c 100644 --- a/testingInterfaces/testVoronoiMeshExtractor/testVoronoiMeshExtractor.C +++ b/testingInterfaces/testVoronoiMeshExtractor/testVoronoiMeshExtractor.C @@ -38,7 +38,6 @@ Description #include "polyMeshGen.H" #include "voronoiMeshExtractor.H" #include "triSurf.H" -#include "writeMeshEnsight.H" using namespace Foam; @@ -50,10 +49,10 @@ int main(int argc, char *argv[]) { # include "setRootCase.H" # include "createTime.H" - - objectRegistry registry(runTime); - - IOdictionary meshDict + + objectRegistry registry(runTime); + + IOdictionary meshDict ( IOobject ( @@ -64,27 +63,26 @@ int main(int argc, char *argv[]) IOobject::NO_WRITE ) ); - - const fileName surfaceFile = meshDict.lookup("surfaceFile"); + + const fileName surfaceFile = meshDict.lookup("surfaceFile"); triSurf surf(registry.path()/surfaceFile); - // construct the octree + // construct the octree meshOctree mo(surf); - meshOctreeCreator(mo, meshDict).createOctreeBoxes(); - - Info<< "Execution time for octree creation = " + meshOctreeCreator(mo, meshDict).createOctreeBoxes(); + + Info<< "Execution time for octree creation = " << runTime.elapsedCpuTime() << " s\n" << endl << endl; - - polyMeshGen pmg(registry); - voronoiMeshExtractor vmg(mo, meshDict, pmg); - - vmg.createMesh(); - - pmg.write(); - writeMeshEnsight(pmg, "voronoiMesh"); - + + polyMeshGen pmg(registry); + voronoiMeshExtractor vmg(mo, meshDict, pmg); + + vmg.createMesh(); + + pmg.write(); + Info << "End\n" << endl; return 0; } diff --git a/tutorials/Allclean b/tutorials/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..6f7f4cf988cd9af2fd39b5e777fc27bb3bf88b1d --- /dev/null +++ b/tutorials/Allclean @@ -0,0 +1,65 @@ +#!/bin/sh + +# Source tutorial clean functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cd cartesianMesh +# Delete data generated by cartesianMesh + +cd asmoOctree + cleanCase + rm -rf constant/polyMesh > /dev/null 2>&1 + rm log.* +cd .. + +cd bunnyOctree + cleanCase + rm -rf constant/polyMesh > /dev/null 2>&1 + rm log.* +cd .. + +cd intakePortOctree + cleanCase + rm -rf constant/polyMesh > /dev/null 2>&1 + rm log.* +cd .. + +cd sawOctree + cleanCase + rm -rf processor* > /dev/null 2>&1 + rm log.* +cd .. + +cd sBendOctree + cleanCase + rm -rf constant/polyMesh > /dev/null 2>&1 + rm log.* +cd .. + +cd .. +cd cartesian2DMesh +# Delete data generated by cartesian2DMesh + +cd hatOctree + cleanCase + rm -rf constant/polyMesh > /dev/null 2>&1 + rm log.* +cd .. + +cd .. +cd tetMesh +# Delete data generated by tetMesh + +cd cutCubeOctree + cleanCase + rm -rf constant/polyMesh > /dev/null 2>&1 + rm log.* +cd .. + +cd socketOctree + cleanCase + rm -rf constant/polyMesh > /dev/null 2>&1 + rm log.* +cd .. + +cd .. diff --git a/tutorials/FanOctree/system/controlDict b/tutorials/FanOctree/system/controlDict index fd49f811bdd3edc4fea3d5a93d09ea1a7bb9c215..821c4de94046fc523da88cc8bf0ae25302c3ccda 100644 --- a/tutorials/FanOctree/system/controlDict +++ b/tutorials/FanOctree/system/controlDict @@ -1,13 +1,29 @@ +<<<<<<< HEAD +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +======= /*---------------------------------------------------------------------------*\ | ========= | | | \\ / F ield | OpenFOAM: The Open Source CFD Toolbox | | \\ / O peration | Version: 1.0 | | \\ / A nd | Web: http://www.openfoam.org | | \\/ M anipulation | | +>>>>>>> parent of aee3c13... Removed Fan from tutorials \*---------------------------------------------------------------------------*/ FoamFile { +<<<<<<< HEAD + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +======= version 2.0; format ascii; @@ -18,11 +34,16 @@ FoamFile class dictionary; object controlDict; +>>>>>>> parent of aee3c13... Removed Fan from tutorials } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +<<<<<<< HEAD +application ; +======= application icoFoam; +>>>>>>> parent of aee3c13... Removed Fan from tutorials startFrom latestTime; diff --git a/tutorials/FanOctree/system/meshDict b/tutorials/FanOctree/system/meshDict index 24907a17814595697677b208fa5fc968e815d259..20960ac83059013da85c5524eba16e7ae070d693 100755 --- a/tutorials/FanOctree/system/meshDict +++ b/tutorials/FanOctree/system/meshDict @@ -1,3 +1,21 @@ +<<<<<<< HEAD +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} +======= // The FOAM Project // File: adaptiveProperties /* ------------------------------------------------------------------------------- @@ -25,6 +43,7 @@ note "fvSchemes for Foam"; class dictionary; object adaptiveProperties; +>>>>>>> parent of aee3c13... Removed Fan from tutorials // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -34,36 +53,143 @@ maxCellSize 40; boundaryCellSize 10; +<<<<<<< HEAD +minCellSize 1.25; + +localRefinement +{ + // outer rim + patch0 + { + cellSize 5; + } + // blade seat edge + patch5 + { + cellSize 1.25; + } + + // shaft + patch6 + { + cellSize 10; + } + + // thin edges at blade ends + patch37 + { + cellSize 0.625; + } + patch55 + { + cellSize 0.625; + } + patch72 + { + cellSize 0.625; + } + patch89 + { + cellSize 0.625; + } + patch86 + { + cellSize 0.625; + } + patch114 + { + cellSize 0.625; + } + patch138 + { + cellSize 0.625; + } + patch157 + { + cellSize 0.625; + } + + // blades + patch8 + { + cellSize 5; + } + patch11 + { + cellSize 5; + } + patch12 + { + cellSize 5; + } + patch16 + { + cellSize 5; + } + patch19 + { + cellSize 5; + } + patch24 + { + cellSize 5; + } + patch27 + { + cellSize 5; + } + patch30 + { + cellSize 5; + } +); + +keepCellsIntersectingPatches +{ + patch0 + { + keepCells 1; + } + patch1 + { + keepCells 1; + } + patch2 + { + keepCells 1; + } +} +======= patchCellSize 19 ( - // outer rim - patch0 5 - // blade seat edge - patch5 1.25 - - // shaft - patch6 10 - - // thin edges at blade ends - patch37 0.625 - patch55 0.625 - patch72 0.625 - patch89 0.625 - patch86 0.625 - patch114 0.625 - patch138 0.625 - patch157 0.625 - - // blades - patch8 5 - patch11 5 + // outer rim + patch0 5 + // blade seat edge + patch5 1.25 + + // shaft + patch6 10 + + // thin edges at blade ends + patch37 0.625 + patch55 0.625 + patch72 0.625 + patch89 0.625 + patch86 0.625 + patch114 0.625 + patch138 0.625 + patch157 0.625 + + // blades + patch8 5 + patch11 5 patch12 5 - patch16 5 - patch19 5 - patch24 5 - patch27 5 - patch30 5 + patch16 5 + patch19 5 + patch24 5 + patch27 5 + patch30 5 ); subsetFileName "Fan1.sftr"; @@ -71,16 +197,17 @@ subsetFileName "Fan1.sftr"; subsetCellSize 1 ( - _refine_1 2.5 + _refine_1 2.5 ); keepCellsIntersectingPatches 3 ( - patch0 - patch1 - patch2 + patch0 + patch1 + patch2 ); +>>>>>>> parent of aee3c13... Removed Fan from tutorials keepCellsIntersectingBoundary 1; checkForGluedMesh 1; diff --git a/tutorials/asmoOctree/system/meshDict b/tutorials/asmoOctree/system/meshDict deleted file mode 100755 index 01f3c63373aba5031f7e7418bafa5a04953b18a2..0000000000000000000000000000000000000000 --- a/tutorials/asmoOctree/system/meshDict +++ /dev/null @@ -1,58 +0,0 @@ -// The FOAM Project // File: adaptiveProperties -/* -------------------------------------------------------------------------------- - ========= | dictionary - \\ / | - \\ / | Name: adaptiveProperties - \\ / | Family: Data file - \\/ | - F ield | FOAM version: 1.9.6 - O peration | Product of Nabla Ltd. - A and | - M anipulation | Email: Enquiries@Nabla.co.uk -------------------------------------------------------------------------------- -*/ - -version 0.5; -format ascii; - -root "/home/larson/franjo/foam/run"; -case "thetaTest"; -instance "system"; -local ""; - -note "fvSchemes for Foam"; - -class dictionary; -object adaptiveProperties; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -surfaceFile "geom.stl"; - -maxCellSize 0.2; - -boundaryCellSize 0.025; - -minCellSize 0.0125; - -patchCellSize -3 -( - defaultFaces0006 0.005 - defaultFaces0007 0.0025 - defaultFaces0009 0.0025 -); -/* -keepCellsIntersectingPatches -3 -( - defaultFaces0006 - defaultFaces0007 - defaultFaces0009 -); -*/ - -internalVertex (1.5 -0.4 0.8); - -// ************************************************************************* // diff --git a/tutorials/bunnyOctree/system/meshDict b/tutorials/bunnyOctree/system/meshDict deleted file mode 100755 index 1f89a2cd53f60b338b00ee94b281a5e4bfafc404..0000000000000000000000000000000000000000 --- a/tutorials/bunnyOctree/system/meshDict +++ /dev/null @@ -1,83 +0,0 @@ -// The FOAM Project // File: adaptiveProperties -/* -------------------------------------------------------------------------------- - ========= | dictionary - \\ / | - \\ / | Name: adaptiveProperties - \\ / | Family: Data file - \\/ | - F ield | FOAM version: 1.9.6 - O peration | Product of Nabla Ltd. - A and | - M anipulation | Email: Enquiries@Nabla.co.uk -------------------------------------------------------------------------------- -*/ - -version 0.5; -format ascii; - -root "/home/larson/franjo/foam/run"; -case "thetaTest"; -instance "system"; -local ""; - -note "fvSchemes for Foam"; - -class dictionary; -object adaptiveProperties; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -surfaceFile "bunnyWrapped.stl"; - -maxCellSize 30.0; - -boundaryCellSize 7.5; - -objectRefinements -5 -( -ear1 -{ - cellSize 3.75; - type cone; - p0 (-100 1873 -320); - radius0 200; - p1 (-560 1400 0); - radius1 200; -} -ear2 -{ - cellSize 3.75; - type cone; - p0 (-650 1873 -620); - radius0 200; - p1 (-670 1300 0); - radius1 200; -} -tail -{ - cellSize 3.75; - type box; - centre (500 500 150); - lengthX 100; - lengthY 150; - lengthZ 200; -} -insideTheBody -{ - cellSize 3.75; - type sphere; - centre (0 700 0); - radius 50; -} -muzzlePiercing -{ - cellSize 3.75; - type line; - p0 (-750 1000 450); - p1 (-750 1500 450); -} -); - -// ************************************************************************* // diff --git a/tutorials/cartesian2DMesh/hatOctree/0/.gitignore b/tutorials/cartesian2DMesh/hatOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesian2DMesh/hatOctree/Allclean b/tutorials/cartesian2DMesh/hatOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..b928b6cfea9e31cf9680fd810604054f9fe8b007 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/Allclean @@ -0,0 +1,12 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh diff --git a/tutorials/cartesian2DMesh/hatOctree/Allrun b/tutorials/cartesian2DMesh/hatOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..315349422cb5b0963268d8caa8fbde12e3347a54 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/Allrun @@ -0,0 +1,6 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication cartesian2DMesh +runApplication checkMesh diff --git a/tutorials/cartesian2DMesh/hatOctree/README b/tutorials/cartesian2DMesh/hatOctree/README new file mode 100644 index 0000000000000000000000000000000000000000..7cc7f69e0a4626841b83a593bb5ab78fa4f75035 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/README @@ -0,0 +1 @@ +Please run cartesian2DMesh to generate a 2D mesh. diff --git a/tutorials/cartesian2DMesh/hatOctree/constant/.gitignore b/tutorials/cartesian2DMesh/hatOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesian2DMesh/hatOctree/geom.fms b/tutorials/cartesian2DMesh/hatOctree/geom.fms new file mode 100644 index 0000000000000000000000000000000000000000..cfc545ad1dd74c772bded99482272f71336c218c --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/geom.fms @@ -0,0 +1,70 @@ + +5 +( +left +wall + +bottom +wall + +right +wall + +top0 +wall + +top1 +wall + +) + + +10 +( +(-1 0 0) +(1 0 0) +(1 1 0) +(0 0.5 0) +(-1 1 0) + +(-1 0 0.1) +(1 0 0.1) +(1 1 0.1) +(0 0.5 0.1) +(-1 1 0.1) +) + + +10 +( +((0 1 6) 0) +((0 6 5) 0) + +((1 2 7) 1) +((1 7 6) 1) + +((2 3 8) 2) +((2 8 7) 2) + +((3 4 9) 3) +((3 9 8) 3) + +((4 0 5) 4) +((4 5 9) 4) +) + +0() + +0 +( +) + + +0 +( +) + + +0 +( +) diff --git a/tutorials/cartesian2DMesh/hatOctree/system/controlDict b/tutorials/cartesian2DMesh/hatOctree/system/controlDict new file mode 100644 index 0000000000000000000000000000000000000000..a3a832a31816f59d3d08c0c1882eb07a0e534d83 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/system/controlDict @@ -0,0 +1,36 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +application ; +deltaT 1; +endTime 50; +graphFormat raw; +purgeWrite 0; +runTimeModifiable yes; +startFrom startTime; +startTime 0; +stopAt endTime; +timeFormat general; +timePrecision 6; +writeCompression uncompressed; +writeControl timeStep; +writeFormat ascii; +writeInterval 20; +writePrecision 6; + +// ************************************************************************* // \ No newline at end of file diff --git a/tutorials/cartesian2DMesh/hatOctree/system/fvSchemes b/tutorials/cartesian2DMesh/hatOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/cartesian2DMesh/hatOctree/system/fvSolution b/tutorials/cartesian2DMesh/hatOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/cartesian2DMesh/hatOctree/system/meshDict b/tutorials/cartesian2DMesh/hatOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..66128306d12081a575b84bf1757a775631db528c --- /dev/null +++ b/tutorials/cartesian2DMesh/hatOctree/system/meshDict @@ -0,0 +1,30 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | OpenFOAM GUI Project: creativeFields | +| \\ / O peration | Version: 0.8.9.0 | +| \\ / A nd | Web: www.c-fields.com | +| \\/ M anipulation | | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ +version 2; +format ascii; +class dictionary; +location "system"; +object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +maxCellSize 0.01; + +surfaceFile "geom.fms"; + +boundaryLayers +{ + nLayers 6; + thicknessRatio 1.2; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/asmoOctree/0/.gitignore b/tutorials/cartesianMesh/asmoOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesianMesh/asmoOctree/Allclean b/tutorials/cartesianMesh/asmoOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..b928b6cfea9e31cf9680fd810604054f9fe8b007 --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/Allclean @@ -0,0 +1,12 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh diff --git a/tutorials/cartesianMesh/asmoOctree/Allrun b/tutorials/cartesianMesh/asmoOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..f22963cc7cda9c3ab87f4cf45e02c0338a81c8f4 --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/Allrun @@ -0,0 +1,6 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication cartesianMesh +runApplication checkMesh diff --git a/tutorials/cartesianMesh/asmoOctree/README b/tutorials/cartesianMesh/asmoOctree/README new file mode 100644 index 0000000000000000000000000000000000000000..dd8b841ea54f014109a0274d460d23f799264e09 --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/README @@ -0,0 +1 @@ +Please run cartesianMesh to generate the mesh diff --git a/tutorials/cartesianMesh/asmoOctree/constant/.gitignore b/tutorials/cartesianMesh/asmoOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/asmoOctree/geom.stl b/tutorials/cartesianMesh/asmoOctree/geom.stl similarity index 100% rename from tutorials/asmoOctree/geom.stl rename to tutorials/cartesianMesh/asmoOctree/geom.stl diff --git a/tutorials/asmoOctree/system/controlDict b/tutorials/cartesianMesh/asmoOctree/system/controlDict similarity index 61% rename from tutorials/asmoOctree/system/controlDict rename to tutorials/cartesianMesh/asmoOctree/system/controlDict index b4a4f2ee97c3b0ef3febaab1f6feb7b76f76a01a..1bda0db6a50d363e90c229f004b9d89395bdb33e 100644 --- a/tutorials/asmoOctree/system/controlDict +++ b/tutorials/cartesianMesh/asmoOctree/system/controlDict @@ -1,31 +1,24 @@ -/*---------------------------------------------------------------------------*\ -| ========= | | -| \\ / F ield | OpenFOAM: The Open Source CFD Toolbox | -| \\ / O peration | Version: 1.0 | -| \\ / A nd | Web: http://www.openfoam.org | -| \\/ M anipulation | | +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | \*---------------------------------------------------------------------------*/ -// FoamX Case Dictionary. - FoamFile { - version 2.0; - format ascii; - - root "/home/franjo/OpenFOAM/franjo-1.0/run"; - case "asmo2"; - instance "system"; - local ""; - - class dictionary; - object controlDict; + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Foam Application Class -applicationClass simpleFoam; +applicationClass ; // Start point of run startFrom latestTime; diff --git a/tutorials/cartesianMesh/asmoOctree/system/fvSchemes b/tutorials/cartesianMesh/asmoOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/asmoOctree/system/fvSolution b/tutorials/cartesianMesh/asmoOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/asmoOctree/system/meshDict b/tutorials/cartesianMesh/asmoOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..0367bfe85a1f694b7f0ddc33258c6e9a5782d56b --- /dev/null +++ b/tutorials/cartesianMesh/asmoOctree/system/meshDict @@ -0,0 +1,44 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +surfaceFile "geom.stl"; + +maxCellSize 0.2; + +boundaryCellSize 0.025; + +minCellSize 0.0125; + +localRefinement +{ + defaultFaces0006 + { + cellSize 0.005; + } + defaultFaces0007 + { + cellSize 0.0025; + } + defaultFaces0009 + { + cellSize 0.0025; + } +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/bunnyOctree/0/.gitignore b/tutorials/cartesianMesh/bunnyOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesianMesh/bunnyOctree/Allclean b/tutorials/cartesianMesh/bunnyOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..b928b6cfea9e31cf9680fd810604054f9fe8b007 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/Allclean @@ -0,0 +1,12 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh diff --git a/tutorials/cartesianMesh/bunnyOctree/Allrun b/tutorials/cartesianMesh/bunnyOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..f22963cc7cda9c3ab87f4cf45e02c0338a81c8f4 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/Allrun @@ -0,0 +1,6 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication cartesianMesh +runApplication checkMesh diff --git a/tutorials/cartesianMesh/bunnyOctree/README b/tutorials/cartesianMesh/bunnyOctree/README new file mode 100644 index 0000000000000000000000000000000000000000..3f61346ec42a7f194155269324ab7b446edd51e0 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/README @@ -0,0 +1 @@ +This tutorials demonstrates the usage of primitive refinement sources diff --git a/tutorials/bunnyOctree/bunnyWrapped.stl b/tutorials/cartesianMesh/bunnyOctree/bunnyWrapped.stl similarity index 100% rename from tutorials/bunnyOctree/bunnyWrapped.stl rename to tutorials/cartesianMesh/bunnyOctree/bunnyWrapped.stl diff --git a/tutorials/cartesianMesh/bunnyOctree/constant/.gitignore b/tutorials/cartesianMesh/bunnyOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/bunnyOctree/system/controlDict b/tutorials/cartesianMesh/bunnyOctree/system/controlDict similarity index 51% rename from tutorials/bunnyOctree/system/controlDict rename to tutorials/cartesianMesh/bunnyOctree/system/controlDict index 13239a782de757ea725809f2b49ed9fee50bd813..9a7ae05a8762e098bea0ff443cd20aa66d49c9b3 100644 --- a/tutorials/bunnyOctree/system/controlDict +++ b/tutorials/cartesianMesh/bunnyOctree/system/controlDict @@ -1,28 +1,23 @@ -/*---------------------------------------------------------------------------*\ -| ========= | | -| \\ / F ield | OpenFOAM: The Open Source CFD Toolbox | -| \\ / O peration | Version: 1.0 | -| \\ / A nd | Web: http://www.openfoam.org | -| \\/ M anipulation | | +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | \*---------------------------------------------------------------------------*/ FoamFile { - version 2.0; - format ascii; - - root ""; - case ""; - instance ""; - local ""; - - class dictionary; - object controlDict; + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; } // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -application icoFoam; +application ; startFrom latestTime; diff --git a/tutorials/cartesianMesh/bunnyOctree/system/decomposeParDict b/tutorials/cartesianMesh/bunnyOctree/system/decomposeParDict new file mode 100644 index 0000000000000000000000000000000000000000..d3dfec8bdb9a2df8a5d7a725e087f27c214d4a64 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/system/decomposeParDict @@ -0,0 +1,22 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | foam-extend: Open Source CFD | +| \\ / O peration | Version: 3.0 | +| \\ / A nd | Web: http://www.extend-project.de | +| \\/ M anipulation | | +\*---------------------------------------------------------------------------*/ +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + note "mesh decomposition control dictionary"; + location "system"; + object decomposeParDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +numberOfSubdomains 4; + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/bunnyOctree/system/fvSchemes b/tutorials/cartesianMesh/bunnyOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/bunnyOctree/system/fvSolution b/tutorials/cartesianMesh/bunnyOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/bunnyOctree/system/meshDict b/tutorials/cartesianMesh/bunnyOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..5c878d223ba59541f7a1c7584f61ccda948e74d9 --- /dev/null +++ b/tutorials/cartesianMesh/bunnyOctree/system/meshDict @@ -0,0 +1,71 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +surfaceFile "bunnyWrapped.stl"; + +maxCellSize 30.0; + +boundaryCellSize 7.5; + +objectRefinements +{ + ear1 + { + cellSize 3.75; + type cone; + p0 (-100 1873 -320); + radius0 200; + p1 (-560 1400 0); + radius1 200; + } + ear2 + { + cellSize 3.75; + type cone; + p0 (-650 1873 -620); + radius0 200; + p1 (-670 1300 0); + radius1 200; + } + tail + { + cellSize 3.75; + type box; + centre (500 500 150); + lengthX 100; + lengthY 150; + lengthZ 200; + } + insideTheBody + { + cellSize 3.75; + type sphere; + centre (0 700 0); + radius 50; + } + muzzlePiercing + { + cellSize 3.75; + type line; + p0 (-750 1000 450); + p1 (-750 1500 450); + } +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/intakePortOctree/0/.gitignore b/tutorials/cartesianMesh/intakePortOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesianMesh/intakePortOctree/Allclean b/tutorials/cartesianMesh/intakePortOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..b928b6cfea9e31cf9680fd810604054f9fe8b007 --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/Allclean @@ -0,0 +1,12 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh diff --git a/tutorials/cartesianMesh/intakePortOctree/Allrun b/tutorials/cartesianMesh/intakePortOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..f22963cc7cda9c3ab87f4cf45e02c0338a81c8f4 --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/Allrun @@ -0,0 +1,6 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication cartesianMesh +runApplication checkMesh diff --git a/tutorials/cartesianMesh/intakePortOctree/constant/.gitignore b/tutorials/cartesianMesh/intakePortOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/intakePortOctree/geom2.stl b/tutorials/cartesianMesh/intakePortOctree/geom2.stl similarity index 100% rename from tutorials/intakePortOctree/geom2.stl rename to tutorials/cartesianMesh/intakePortOctree/geom2.stl diff --git a/tutorials/cartesianMesh/intakePortOctree/system/controlDict b/tutorials/cartesianMesh/intakePortOctree/system/controlDict new file mode 100644 index 0000000000000000000000000000000000000000..ebbe91cdcf3a7f234ca7e8c49040972b71436abd --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/system/controlDict @@ -0,0 +1,53 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// ************************************************************************* // + +applicationClass ; + +startFrom latestTime; + +startTime 0; + +stopAt endTime; + +endTime 500; + +deltaT 1; + +writeControl timeStep; + +writeInterval 100; + +cycleWrite 0; + +writeFormat ascii; + +writeCompression uncompressed; + +timeFormat general; + +timePrecision 6; + +runTimeModifiable yes; + +nCorrectors 2; + +nNonOrthogonalCorrectors 0; + + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/intakePortOctree/system/fvSchemes b/tutorials/cartesianMesh/intakePortOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/intakePortOctree/system/fvSolution b/tutorials/cartesianMesh/intakePortOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/intakePortOctree/system/meshDict b/tutorials/cartesianMesh/intakePortOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..be436257a315697c7c03a70e54709bb17aa36417 --- /dev/null +++ b/tutorials/cartesianMesh/intakePortOctree/system/meshDict @@ -0,0 +1,64 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +surfaceFile "geom2.stl"; + +maxCellSize 10; + +boundaryCellSize 1.25; + +minCellSize 2.0; + +localRefinement +{ + patch001 + { + cellSize 0.625; + } + patch002 + { + cellSize 0.625; + } + patch003 + { + cellSize 0.625; + } + patch004 + { + cellSize 0.625; + } + patch005 + { + cellSize 0.625; + } + patch006 + { + cellSize 0.625; + } + patch007 + { + cellSize 0.625; + } + patch008 + { + cellSize 0.625; + } +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sBendOctree/0/.gitignore b/tutorials/cartesianMesh/sBendOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesianMesh/sBendOctree/Allclean b/tutorials/cartesianMesh/sBendOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..b928b6cfea9e31cf9680fd810604054f9fe8b007 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/Allclean @@ -0,0 +1,12 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh diff --git a/tutorials/cartesianMesh/sBendOctree/Allrun b/tutorials/cartesianMesh/sBendOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..f22963cc7cda9c3ab87f4cf45e02c0338a81c8f4 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/Allrun @@ -0,0 +1,6 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication cartesianMesh +runApplication checkMesh diff --git a/tutorials/cartesianMesh/sBendOctree/README b/tutorials/cartesianMesh/sBendOctree/README new file mode 100644 index 0000000000000000000000000000000000000000..d0dea91e5ea466af2f46904ac6cc262b31c15292 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/README @@ -0,0 +1 @@ +The exmaple demonstrates usage of subsets for refinement, and how to set up boundary layer properties. To generate the mesh please run cartesianMesh or tetMesh. diff --git a/tutorials/cartesianMesh/sBendOctree/constant/.gitignore b/tutorials/cartesianMesh/sBendOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesianMesh/sBendOctree/sBend.fms b/tutorials/cartesianMesh/sBendOctree/sBend.fms new file mode 100644 index 0000000000000000000000000000000000000000..aa7482bd91422e12ef76154c7683f0cdaf5472d7 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/sBend.fms @@ -0,0 +1,2383 @@ +5( +object +wall +inlet +patch +outlet +patch +symm +symmetryPlane +walls +wall) +852((-2 1.39469 -0.128242) (-2 1.415 -3.91402e-17) (-2 1.5 -4.9133e-17) (-2 1.31385 -0.101976) (-2 1.47553 -0.154509) (-2 1.33 -2.91474e-17) (-2 1.26698 -0.193969) (-2 1.40451 -0.293893) (-2 1.23301 -0.0757092) (-2 1.33574 -0.243931) (-2 1.245 -1.91546e-17) (-2 1.19821 -0.144007) (-2 1.19397 -0.266976) (-2 1.24393 -0.335742) (-2 1.15217 -0.0494427) (-2 1.14401 -0.198209) (-2 1.29389 -0.404509) (-2 1.16 -9.16178e-18) (-2 1.09405 -0.129443) (-2 1.12944 -0.0940456) (-2 1.10198 -0.313849) (-2 1.15451 -0.475528) (-2 1.07133 -0.0231763) (-2 1.07571 -0.233009) (-2 1.06068 -0.0440838) (-2 1.12824 -0.394688) (-2 1.075 8.31019e-19) (-2 1.04944 -0.152169) (-2 1 -0.33) (-2 1 -0.5) (-2 1.04408 -0.0606762) (-2 1 -0.245) (-2 1.02318 -0.0713292) (-2 1 -0.415) (-2 1 -0.16) (-2 1 -0.075) (-2 0.924291 -0.233009) (-2 0.898024 -0.313849) (-2 0.845491 -0.475528) (-2 0.871758 -0.394688) (-2 0.950557 -0.152169) (-2 0.806031 -0.266976) (-2 0.756069 -0.335742) (-2 0.905954 -0.129443) (-2 0.976824 -0.0713292) (-2 0.855993 -0.198209) (-2 0.706107 -0.404509) (-2 0.955916 -0.0606763) (-2 0.733024 -0.193969) (-2 0.595491 -0.293893) (-2 0.870557 -0.0940456) (-2 0.801791 -0.144007) (-2 0.664258 -0.243931) (-2 0.939324 -0.0440839) (-2 0.686151 -0.101976) (-2 0.766991 -0.0757092) (-2 0.524472 -0.154509) (-2 0.928671 -0.0231763) (-2 0.605312 -0.128242) (-2 0.847831 -0.0494427) (-2 0.67 -3.3749e-23) (-2 0.585 -4.33443e-23) (-2 0.84 -1.45584e-23) (-2 0.925 -4.96308e-24) (-2 0.755 -2.41537e-23) (-2 0.5 -5.29396e-23) (6 -0.585 4.32569e-18) (6 -0.605312 -0.128242) (6 -0.524472 -0.154509) (6 -0.686151 -0.101976) (6 -0.664258 -0.243931) (6 -0.5 6.21687e-18) (6 -0.67 2.43451e-18) (6 -0.595491 -0.293893) (6 -0.733024 -0.193969) (6 -0.766991 -0.0757092) (6 -0.756069 -0.335742) (6 -0.755 5.43323e-19) (6 -0.706107 -0.404509) (6 -0.801791 -0.144007) (6 -0.806031 -0.266976) (6 -0.84 -1.34786e-18) (6 -0.845491 -0.475528) (6 -0.870557 -0.0940456) (6 -0.855993 -0.198209) (6 -0.898024 -0.313849) (6 -0.847831 -0.0494427) (6 -0.871758 -0.394688) (6 -0.905954 -0.129443) (6 -0.924291 -0.233009) (6 -0.925 -3.23904e-18) (6 -1 -0.415) (6 -0.955916 -0.0606763) (6 -0.928671 -0.0231763) (6 -1 -0.33) (6 -1 -0.5) (6 -0.950557 -0.152169) (6 -0.939324 -0.0440839) (6 -1 -0.245) (6 -1.12824 -0.394689) (6 -0.976824 -0.0713292) (6 -1 -0.16) (6 -1.07571 -0.233009) (6 -1.15451 -0.475528) (6 -1 -0.075) (6 -1.10198 -0.313849) (6 -1.04944 -0.152169) (6 -1.24393 -0.335742) (6 -1.14401 -0.198209) (6 -1.09405 -0.129443) (6 -1.29389 -0.404509) (6 -1.02318 -0.0713293) (6 -1.19397 -0.266976) (6 -1.40451 -0.293893) (6 -1.33574 -0.243931) (6 -1.26698 -0.193969) (6 -1.19821 -0.144007) (6 -1.04408 -0.0606763) (6 -1.12944 -0.0940457) (6 -1.06068 -0.0440839) (6 -1.39469 -0.128242) (6 -1.23301 -0.0757092) (6 -1.15217 -0.0494427) (6 -1.47553 -0.154509) (6 -1.31385 -0.101976) (6 -1.5 1.05879e-22) (6 -1.415 1.11173e-22) (6 -1.33 1.16467e-22) (6 -1.245 1.21761e-22) (6 -1.07133 -0.0231763) (6 -1.16 1.27055e-22) (6 -1.075 1.32349e-22) (-1.6 0.5 -5.29396e-23) (-1.6 0.585 -4.33443e-23) (-1.2 0.585 -4.33443e-23) (-1.2 0.5 -5.29396e-23) (-1.2 0.67 -3.3749e-23) (-1.6 0.67 -3.3749e-23) (-0.8 0.585 -4.33443e-23) (-0.8 0.67 -3.3749e-23) (-0.8 0.5 -5.29396e-23) (-0.8 0.755 -2.41537e-23) (-1.2 0.755 -2.41537e-23) (-1.6 0.755 -2.41537e-23) (-0.4 0.585 -4.33443e-23) (-0.4 0.67 -3.3749e-23) (-0.4 0.755 -2.41537e-23) (-0.4 0.5 -5.29396e-23) (-0.4 0.84 -1.45584e-23) (-0.8 0.84 -1.45584e-23) (-1.2 0.84 -1.45584e-23) (-1.6 0.84 -1.45584e-23) (2.38228e-23 0.585 -4.33443e-23) (2.11758e-23 0.67 -3.3749e-23) (1.85288e-23 0.755 -2.41537e-23) (1.58819e-23 0.84 -1.45584e-23) (2.64698e-23 0.5 -5.29396e-23) (1.32349e-23 0.925 -4.96308e-24) (-0.4 0.925 -4.96308e-24) (-0.8 0.925 -4.96308e-24) (-1.2 0.925 -4.96308e-24) (-1.6 0.925 -4.96308e-24) (0.180775 0.556368 -3.40137e-23) (0.207041 0.637208 -2.69992e-23) (0.259574 0.798888 -1.29702e-23) (0.154509 0.475528 -4.10282e-23) (0.233308 0.718048 -1.99847e-23) (0.285841 0.879727 -5.9557e-24) (0.343854 0.473275 -2.46831e-23) (0.393816 0.542041 -2.02494e-23) (0.49374 0.679574 -1.1382e-23) (0.543701 0.748341 -6.94832e-24) (0.293893 0.404509 -2.91168e-23) (0.443778 0.610808 -1.58157e-23) (0.473275 0.343854 -1.53525e-23) (0.542041 0.393816 -1.34996e-23) (0.610808 0.443778 -1.16467e-23) (0.679574 0.49374 -9.79382e-24) (0.748341 0.543701 -7.94093e-24) (0.404509 0.293893 -1.72054e-23) (0.475528 0.154509 -5.29396e-24) (0.556368 0.180775 -6.02187e-24) (0.718048 0.233308 -7.47771e-24) (0.798888 0.259574 -8.20563e-24) (0.637208 0.207041 -6.74979e-24) (0.879727 0.285841 -8.93355e-24) (0.5 -1.32349e-23 6.61744e-24) (0.585 1.05879e-23 3.30872e-24) (0.755 5.82335e-23 -3.30872e-24) (0.925 1.05879e-22 -9.92617e-24) (0.67 3.44107e-23 -7.34684e-40) (0.84 8.20563e-23 -6.61744e-24) (0.573415 -0.463525 2.64698e-23) (0.654255 -0.437259 2.48816e-23) (0.815935 -0.384726 2.17052e-23) (0.977614 -0.332193 1.85288e-23) (0.735095 -0.410993 2.32934e-23) (0.896775 -0.35846 2.0117e-23) (0.786475 -0.881678 4.63221e-23) (0.924007 -0.781754 4.65868e-23) (1.06154 -0.681831 4.68515e-23) (0.855241 -0.831716 4.64545e-23) (0.992774 -0.731793 4.67192e-23) (1.13031 -0.631869 4.69839e-23) (1.16828 -1.14476 6.80273e-23) (1.21825 -1.07599 6.98802e-23) (1.31817 -0.93846 7.3586e-23) (1.36813 -0.869693 7.54389e-23) (1.11832 -1.21353 6.61744e-23) (1.26821 -1.00723 7.17331e-23) (1.53647 -1.42658 8.60268e-23) (1.56274 -1.34574 8.96002e-23) (1.61527 -1.18407 9.6747e-23) (1.64154 -1.10323 1.0032e-22) (1.58901 -1.26491 9.31736e-23) (1.66781 -1.02239 1.03894e-22) (2 -1.5 1.05879e-22) (2 -1.415 1.11173e-22) (2 -1.245 1.21761e-22) (2 -1.16 1.27055e-22) (2 -1.33 1.16467e-22) (2 -1.075 1.32349e-22) (2.4 -1.415 1.11173e-22) (2.4 -1.33 1.16467e-22) (2.4 -1.16 1.27055e-22) (2.4 -1.245 1.21761e-22) (2.4 -1.075 1.32349e-22) (2.4 -1.5 1.05879e-22) (2.8 -1.415 1.11173e-22) (2.8 -1.33 1.16467e-22) (2.8 -1.245 1.21761e-22) (2.8 -1.16 1.27055e-22) (2.8 -1.075 1.32349e-22) (2.8 -1.5 1.05879e-22) (3.2 -1.415 1.11173e-22) (3.2 -1.33 1.16467e-22) (3.2 -1.245 1.21761e-22) (3.2 -1.16 1.27055e-22) (3.2 -1.075 1.32349e-22) (3.2 -1.5 1.05879e-22) (3.6 -1.415 1.11173e-22) (3.6 -1.33 1.16467e-22) (3.6 -1.245 1.21761e-22) (3.6 -1.16 1.27055e-22) (3.6 -1.075 1.32349e-22) (3.6 -1.5 1.05879e-22) (4 -1.415 1.11173e-22) (4 -1.33 1.16467e-22) (4 -1.245 1.21761e-22) (4 -1.16 1.27055e-22) (4 -1.075 1.32349e-22) (4 -1.5 1.05879e-22) (4.4 -1.415 1.11173e-22) (4.4 -1.33 1.16467e-22) (4.4 -1.245 1.21761e-22) (4.4 -1.16 1.27055e-22) (4.4 -1.075 1.32349e-22) (4.4 -1.5 1.05879e-22) (4.8 -1.415 1.11173e-22) (4.8 -1.33 1.16467e-22) (4.8 -1.245 1.21761e-22) (4.8 -1.16 1.27055e-22) (4.8 -1.075 1.32349e-22) (4.8 -1.5 1.05879e-22) (5.2 -1.415 1.11173e-22) (5.2 -1.33 1.16467e-22) (5.2 -1.245 1.21761e-22) (5.2 -1.16 1.27055e-22) (5.2 -1.075 1.32349e-22) (5.2 -1.5 1.05879e-22) (5.6 -1.415 1.11173e-22) (5.6 -1.33 1.16467e-22) (5.6 -1.245 1.21761e-22) (5.6 -1.16 1.27055e-22) (5.6 -1.075 1.32349e-22) (5.6 -1.5 1.05879e-22) (-1.6 1.415 -3.91402e-17) (-1.6 1.33 -2.91474e-17) (-1.6 1.5 -4.9133e-17) (-1.2 1.33 -2.91474e-17) (-1.2 1.415 -3.91402e-17) (-1.6 1.245 -1.91546e-17) (-1.2 1.245 -1.91546e-17) (-1.2 1.5 -4.9133e-17) (-0.8 1.245 -1.91546e-17) (-0.8 1.33 -2.91474e-17) (-0.8 1.415 -3.91402e-17) (-1.6 1.16 -9.16178e-18) (-1.2 1.16 -9.16178e-18) (-0.8 1.16 -9.16178e-18) (-0.8 1.5 -4.9133e-17) (-0.4 1.16 -9.16178e-18) (-0.4 1.245 -1.91546e-17) (-0.4 1.33 -2.91474e-17) (-0.4 1.415 -3.91402e-17) (-1.6 1.075 8.31019e-19) (-1.2 1.075 8.31019e-19) (-0.8 1.075 8.31019e-19) (-0.4 1.075 8.31019e-19) (-0.4 1.5 -4.9133e-17) (-6.61744e-24 1.075 8.31019e-19) (-2.64698e-23 1.16 -9.16178e-18) (-4.63221e-23 1.245 -1.91546e-17) (-6.61744e-23 1.33 -2.91474e-17) (-8.60268e-23 1.415 -3.91402e-17) (-1.05879e-22 1.5 -4.9133e-17) (0.332193 1.02239 -4.05649e-19) (0.35846 1.10323 -7.20103e-18) (0.384726 1.18407 -1.39964e-17) (0.410993 1.26491 -2.07918e-17) (0.463525 1.42658 -3.43825e-17) (0.437259 1.34574 -2.75872e-17) (0.681831 0.93846 -5.24027e-18) (0.731793 1.00723 -8.83823e-18) (0.831716 1.14476 -1.60341e-17) (0.881678 1.21353 -1.96321e-17) (0.631869 0.869693 -1.64232e-18) (0.781754 1.07599 -1.24362e-17) (1.00723 0.731793 -3.68005e-18) (0.93846 0.681831 -3.27952e-18) (1.07599 0.781754 -4.08059e-18) (1.21353 0.881678 -4.88165e-18) (1.14476 0.831716 -4.48112e-18) (0.869693 0.631869 -2.87899e-18) (1.26491 0.410993 4.27501e-18) (1.10323 0.35846 -1.31877e-18) (1.02239 0.332193 -4.11565e-18) (1.34574 0.437259 7.0719e-18) (1.18407 0.384726 1.47812e-18) (1.42658 0.463525 9.86879e-18) (1.33 1.48231e-22 1.26306e-17) (1.245 1.69407e-22 6.6363e-18) (1.16 1.90582e-22 6.41987e-19) (1.415 1.27055e-22 1.86249e-17) (1.075 2.11758e-22 -5.35232e-18) (1.5 1.05879e-22 2.46192e-17) (1.44363 -0.180775 1.57651e-17) (1.36279 -0.207041 1.05914e-17) (1.28195 -0.233308 5.4177e-18) (1.20111 -0.259574 2.44018e-19) (1.52447 -0.154509 2.09388e-17) (1.12027 -0.285841 -4.92967e-18) (1.52672 -0.343855 1.29052e-17) (1.38919 -0.443778 4.19911e-18) (1.25166 -0.543702 -4.50701e-18) (1.59549 -0.293893 1.72583e-17) (1.45796 -0.393816 8.55217e-18) (1.32043 -0.49374 -1.53951e-19) (1.65615 -0.473275 1.00454e-17) (1.60618 -0.542042 6.51295e-18) (1.55622 -0.610808 2.98051e-18) (1.50626 -0.679575 -5.51921e-19) (1.70611 -0.404509 1.35778e-17) (1.4563 -0.748341 -4.08435e-18) (1.81922 -0.556368 7.18553e-18) (1.76669 -0.718048 1.76192e-18) (1.71416 -0.879727 -3.6617e-18) (1.79296 -0.637208 4.47373e-18) (1.84549 -0.475528 9.89734e-18) (1.74043 -0.798888 -9.4989e-19) (2 -0.585 4.32569e-18) (2 -0.755 5.43323e-19) (2 -0.925 -3.23904e-18) (2 -0.67 2.43451e-18) (2 -0.5 6.21687e-18) (2 -0.84 -1.34786e-18) (2.4 -0.67 2.43451e-18) (2.4 -0.585 4.32569e-18) (2.4 -0.755 5.43323e-19) (2.4 -0.84 -1.34786e-18) (2.4 -0.925 -3.23904e-18) (2.4 -0.5 6.21687e-18) (2.8 -0.755 5.43323e-19) (2.8 -0.67 2.43451e-18) (2.8 -0.585 4.32569e-18) (2.8 -0.84 -1.34786e-18) (2.8 -0.925 -3.23904e-18) (2.8 -0.5 6.21687e-18) (3.2 -0.84 -1.34786e-18) (3.2 -0.755 5.43323e-19) (3.2 -0.67 2.43451e-18) (3.2 -0.585 4.32569e-18) (3.2 -0.925 -3.23904e-18) (3.2 -0.5 6.21687e-18) (3.6 -0.925 -3.23904e-18) (3.6 -0.84 -1.34786e-18) (3.6 -0.755 5.43323e-19) (3.6 -0.67 2.43451e-18) (3.6 -0.585 4.32569e-18) (3.6 -0.5 6.21687e-18) (4 -0.925 -3.23904e-18) (4 -0.84 -1.34786e-18) (4 -0.755 5.43323e-19) (4 -0.67 2.43451e-18) (4 -0.585 4.32569e-18) (4 -0.5 6.21687e-18) (4.4 -0.925 -3.23904e-18) (4.4 -0.84 -1.34786e-18) (4.4 -0.755 5.43323e-19) (4.4 -0.67 2.43451e-18) (4.4 -0.585 4.32569e-18) (4.4 -0.5 6.21687e-18) (4.8 -0.925 -3.23904e-18) (4.8 -0.84 -1.34786e-18) (4.8 -0.755 5.43323e-19) (4.8 -0.67 2.43451e-18) (4.8 -0.585 4.32569e-18) (4.8 -0.5 6.21687e-18) (5.2 -0.925 -3.23904e-18) (5.2 -0.84 -1.34786e-18) (5.2 -0.755 5.43323e-19) (5.2 -0.67 2.43451e-18) (5.2 -0.585 4.32569e-18) (5.2 -0.5 6.21687e-18) (5.6 -0.925 -3.23904e-18) (5.6 -0.84 -1.34786e-18) (5.6 -0.755 5.43323e-19) (5.6 -0.67 2.43451e-18) (5.6 -0.585 4.32569e-18) (5.6 -0.5 6.21687e-18) (-1.6 0.928671 -0.0231763) (-1.2 0.928671 -0.0231763) (-1.2 0.939324 -0.0440839) (-1.6 0.939324 -0.0440839) (-0.8 0.928671 -0.0231763) (-0.8 0.939324 -0.0440839) (-0.8 0.955916 -0.0606763) (-1.2 0.955916 -0.0606763) (-1.6 0.955916 -0.0606763) (-0.4 0.928671 -0.0231763) (-0.4 0.939324 -0.0440839) (-0.4 0.955916 -0.0606763) (-0.4 0.976824 -0.0713292) (-0.8 0.976824 -0.0713292) (-1.2 0.976824 -0.0713292) (-1.6 0.976824 -0.0713292) (7.94093e-24 0.928671 -0.0231763) (2.64698e-24 0.939324 -0.0440839) (-2.64698e-24 0.955916 -0.0606763) (-7.94093e-24 0.976824 -0.0713292) (-1.32349e-23 1 -0.075) (-0.4 1 -0.075) (-0.8 1 -0.075) (-1.2 1 -0.075) (-1.6 1 -0.075) (0.28821 0.88493 -0.0231763) (0.291976 0.895718 -0.0440839) (0.302746 0.93025 -0.0713292) (0.309017 0.951057 -0.075) (0.29693 0.911258 -0.0606763) (0.315288 0.971863 -0.0713292) (-0.4 1.02318 -0.0713292) (-0.8 1.02318 -0.0713292) (-1.2 1.02318 -0.0713292) (-1.6 1.02318 -0.0713292) (0.547986 0.753678 -0.0231763) (0.555064 0.763205 -0.0440839) (0.575698 0.791976 -0.0713292) (0.587785 0.809017 -0.075) (0.599873 0.826058 -0.0713292) (-1.19114e-23 1.02318 -0.0713292) (0.564518 0.776296 -0.0606763) (0.611052 0.841738 -0.0606763) (0.321104 0.990855 -0.0606762) (-0.8 1.04408 -0.0606762) (-0.4 1.04408 -0.0606762) (-1.2 1.04408 -0.0606762) (-1.6 1.04408 -0.0606762) (0.753678 0.547986 -0.0231763) (0.763205 0.555064 -0.0440839) (0.776296 0.564518 -0.0606763) (0.791976 0.575698 -0.0713292) (0.809017 0.587785 -0.075) (0.826058 0.599873 -0.0713292) (0.841738 0.611052 -0.0606763) (-1.05879e-23 1.04408 -0.0606762) (0.854829 0.620506 -0.0440839) (0.620506 0.854829 -0.0440839) (0.326058 1.0064 -0.0440839) (-1.2 1.06068 -0.0440838) (-0.8 1.06068 -0.0440838) (-0.4 1.06068 -0.0440838) (-1.6 1.06068 -0.0440838) (0.88493 0.28821 -0.0231763) (0.895718 0.291976 -0.0440839) (0.911258 0.29693 -0.0606763) (0.93025 0.302746 -0.0713292) (0.951057 0.309017 -0.075) (0.971863 0.315288 -0.0713293) (0.990855 0.321104 -0.0606763) (-9.26442e-24 1.06068 -0.0440838) (1.0064 0.326058 -0.0440839) (0.864356 0.627584 -0.0231763) (0.329824 1.01718 -0.0231763) (-7.94093e-24 1.07133 -0.0231763) (-1.6 1.07133 -0.0231763) (-1.2 1.07133 -0.0231763) (-0.8 1.07133 -0.0231763) (-0.4 1.07133 -0.0231763) (0.928671 8.47033e-23 -0.0231763) (0.939324 6.35275e-23 -0.0440839) (0.955916 4.23516e-23 -0.0606763) (0.976824 2.11758e-23 -0.0713292) (1 0 -0.075) (1.02318 4.23516e-23 -0.0713293) (1.01718 0.329824 -0.0231763) (1.04408 8.47033e-23 -0.0606763) (0.627584 0.864356 -0.0231763) (1.07133 1.69407e-22 -0.0231763) (1.06068 1.27055e-22 -0.0440839) (0.982817 -0.329824 -0.0231763) (0.993605 -0.326058 -0.0440839) (1.00914 -0.321104 -0.0606763) (1.02814 -0.315287 -0.0713292) (1.04894 -0.309017 -0.075) (1.06975 -0.302746 -0.0713293) (1.10428 -0.291976 -0.0440839) (1.08874 -0.29693 -0.0606763) (1.11507 -0.28821 -0.0231763) (1.14517 -0.620506 -0.0440839) (1.13564 -0.627584 -0.0231763) (1.15826 -0.611052 -0.0606763) (1.17394 -0.599872 -0.0713293) (1.19098 -0.587785 -0.075) (1.20802 -0.575698 -0.0713293) (1.24632 -0.547987 -0.0231763) (1.23679 -0.555064 -0.0440839) (1.2237 -0.564518 -0.0606763) (1.37949 -0.854828 -0.0440839) (1.37242 -0.864355 -0.0231763) (1.38895 -0.841738 -0.0606763) (1.41221 -0.809017 -0.075) (1.4243 -0.791976 -0.0713293) (1.45201 -0.753679 -0.0231763) (1.43548 -0.776296 -0.0606763) (1.40013 -0.826058 -0.0713293) (1.44494 -0.763206 -0.0440839) (1.67018 -1.01718 -0.0231763) (1.6789 -0.990855 -0.0606763) (1.68471 -0.971863 -0.0713293) (1.69098 -0.951056 -0.075) (1.69725 -0.93025 -0.0713292) (1.70307 -0.911258 -0.0606763) (1.71179 -0.88493 -0.0231763) (1.70802 -0.895718 -0.0440839) (1.67394 -1.00639 -0.0440839) (2 -1.07133 -0.0231763) (2 -1.02318 -0.0713293) (2 -1.04408 -0.0606763) (2 -1 -0.075) (2 -0.976824 -0.0713292) (2 -0.955916 -0.0606763) (2 -0.939324 -0.0440839) (2 -0.928671 -0.0231763) (2 -1.06068 -0.0440839) (2.4 -1.07133 -0.0231763) (2.4 -1.06068 -0.0440839) (2.4 -1 -0.075) (2.4 -1.02318 -0.0713293) (2.4 -1.04408 -0.0606763) (2.4 -0.976824 -0.0713292) (2.4 -0.955916 -0.0606763) (2.4 -0.939324 -0.0440839) (2.4 -0.928671 -0.0231763) (2.8 -1.07133 -0.0231763) (2.8 -1.06068 -0.0440839) (2.8 -1.04408 -0.0606763) (2.8 -1 -0.075) (2.8 -1.02318 -0.0713293) (2.8 -0.976824 -0.0713292) (2.8 -0.955916 -0.0606763) (2.8 -0.939324 -0.0440839) (2.8 -0.928671 -0.0231763) (3.2 -1.07133 -0.0231763) (3.2 -1.06068 -0.0440839) (3.2 -1.04408 -0.0606763) (3.2 -1.02318 -0.0713293) (3.2 -1 -0.075) (3.2 -0.976824 -0.0713292) (3.2 -0.955916 -0.0606763) (3.2 -0.939324 -0.0440839) (3.2 -0.928671 -0.0231763) (3.6 -1.07133 -0.0231763) (3.6 -1.06068 -0.0440839) (3.6 -1.04408 -0.0606763) (3.6 -1.02318 -0.0713293) (3.6 -1 -0.075) (3.6 -0.976824 -0.0713292) (3.6 -0.955916 -0.0606763) (3.6 -0.939324 -0.0440839) (3.6 -0.928671 -0.0231763) (4 -1.07133 -0.0231763) (4 -1.06068 -0.0440839) (4 -1.04408 -0.0606763) (4 -1.02318 -0.0713293) (4 -1 -0.075) (4 -0.976824 -0.0713292) (4 -0.955916 -0.0606763) (4 -0.939324 -0.0440839) (4 -0.928671 -0.0231763) (4.4 -1.07133 -0.0231763) (4.4 -1.06068 -0.0440839) (4.4 -1.04408 -0.0606763) (4.4 -1.02318 -0.0713293) (4.4 -1 -0.075) (4.4 -0.976824 -0.0713292) (4.4 -0.955916 -0.0606763) (4.4 -0.939324 -0.0440839) (4.4 -0.928671 -0.0231763) (4.8 -1.07133 -0.0231763) (4.8 -1.06068 -0.0440839) (4.8 -1.04408 -0.0606763) (4.8 -1.02318 -0.0713293) (4.8 -1 -0.075) (4.8 -0.976824 -0.0713292) (4.8 -0.955916 -0.0606763) (4.8 -0.939324 -0.0440839) (4.8 -0.928671 -0.0231763) (5.2 -1.07133 -0.0231763) (5.2 -1.06068 -0.0440839) (5.2 -1.04408 -0.0606763) (5.2 -1.02318 -0.0713293) (5.2 -1 -0.075) (5.2 -0.976824 -0.0713292) (5.2 -0.955916 -0.0606763) (5.2 -0.939324 -0.0440839) (5.2 -0.928671 -0.0231763) (5.6 -1.07133 -0.0231763) (5.6 -1.06068 -0.0440839) (5.6 -1.04408 -0.0606763) (5.6 -1.02318 -0.0713293) (5.6 -1 -0.075) (5.6 -0.976824 -0.0713292) (5.6 -0.955916 -0.0606763) (5.6 -0.939324 -0.0440839) (5.6 -0.928671 -0.0231763) (-1.6 1.47553 -0.154509) (-1.2 1.47553 -0.154509) (-1.2 1.40451 -0.293893) (-1.6 1.40451 -0.293893) (-0.8 1.47553 -0.154509) (-0.8 1.40451 -0.293893) (-0.8 1.29389 -0.404509) (-1.2 1.29389 -0.404509) (-1.6 1.29389 -0.404509) (-0.4 1.47553 -0.154509) (-0.4 1.40451 -0.293893) (-0.4 1.29389 -0.404509) (-0.4 1.15451 -0.475528) (-0.8 1.15451 -0.475528) (-1.2 1.15451 -0.475528) (-1.6 1.15451 -0.475528) (-8.73503e-23 1.47553 -0.154509) (-6.88214e-23 1.40451 -0.293893) (-5.02926e-23 1.29389 -0.404509) (-3.17637e-23 1.15451 -0.475528) (-1.32349e-23 1 -0.5) (-0.4 1 -0.5) (-0.8 1 -0.5) (-1.2 1 -0.5) (-1.6 1 -0.5) (0.447729 1.3919 -0.154509) (0.422624 1.31998 -0.293893) (0.389599 1.21638 -0.404509) (0.35082 1.08977 -0.475528) (0.309017 0.951057 -0.5) (-0.4 0.845491 -0.475528) (-0.8 0.845491 -0.475528) (-1.2 0.845491 -0.475528) (-1.6 0.845491 -0.475528) (0.853111 1.17794 -0.154509) (0.805924 1.11443 -0.293893) (0.742899 1.02716 -0.404509) (0.668367 0.922624 -0.475528) (0.267214 0.812344 -0.475528) (-5.29396e-24 0.845491 -0.475528) (0.587785 0.809017 -0.5) (0.507203 0.69541 -0.475528) (-0.8 0.706107 -0.404509) (-0.4 0.706107 -0.404509) (-1.2 0.706107 -0.404509) (-1.6 0.706107 -0.404509) (1.17794 0.853111 -0.154509) (1.11443 0.805924 -0.293893) (1.02716 0.742899 -0.404509) (0.922624 0.668367 -0.475528) (0.809017 0.587785 -0.5) (0.228435 0.685731 -0.404509) (0.432671 0.590878 -0.404509) (2.64698e-24 0.706107 -0.404509) (0.69541 0.507203 -0.475528) (-1.2 0.595491 -0.293893) (-0.8 0.595491 -0.293893) (-0.4 0.595491 -0.293893) (-1.6 0.595491 -0.293893) (1.31998 0.422624 -0.293893) (1.21638 0.389599 -0.404509) (1.08977 0.35082 -0.475528) (0.951057 0.309017 -0.5) (0.19541 0.582133 -0.293893) (0.369646 0.503607 -0.293893) (0.590878 0.432671 -0.404509) (1.05879e-23 0.595491 -0.293893) (1.3919 0.447729 -0.154509) (0.812344 0.267214 -0.475528) (-1.6 0.524472 -0.154509) (-1.2 0.524472 -0.154509) (-0.8 0.524472 -0.154509) (-0.4 0.524472 -0.154509) (1.29389 4.23516e-23 -0.404509) (1.40451 6.35275e-23 -0.293893) (1.15451 2.11758e-23 -0.475528) (1 0 -0.5) (0.170305 0.510211 -0.154509) (0.32246 0.440093 -0.154509) (0.503607 0.369646 -0.293893) (0.685731 0.228435 -0.404509) (1.85288e-23 0.524472 -0.154509) (1.47553 8.47033e-23 -0.154509) (0.845491 -2.64698e-24 -0.475528) (1.31427 -0.228435 -0.404509) (1.41787 -0.19541 -0.293893) (1.48979 -0.170305 -0.154509) (1.18766 -0.267214 -0.475528) (0.440093 0.32246 -0.154509) (0.582133 0.19541 -0.293893) (0.706107 -5.29396e-24 -0.404509) (1.04894 -0.309017 -0.5) (0.910231 -0.35082 -0.475528) (0.783618 -0.389599 -0.404509) (1.49639 -0.369646 -0.293893) (1.40912 -0.432671 -0.404509) (1.55991 -0.32246 -0.154509) (1.30459 -0.507203 -0.475528) (0.510211 0.170305 -0.154509) (0.595491 -7.94093e-24 -0.293893) (0.68002 -0.422624 -0.293893) (1.19098 -0.587785 -0.5) (1.07738 -0.668367 -0.475528) (0.972844 -0.742899 -0.404509) (0.885573 -0.805924 -0.293893) (1.63035 -0.503607 -0.293893) (1.56733 -0.590878 -0.404509) (1.67754 -0.440093 -0.154509) (1.41221 -0.809017 -0.5) (0.524472 -1.05879e-23 -0.154509) (0.608098 -0.447729 -0.154509) (0.822059 -0.853111 -0.154509) (1.4928 -0.69541 -0.475528) (1.33163 -0.922624 -0.475528) (1.2571 -1.02716 -0.404509) (1.14689 -1.17794 -0.154509) (1.80459 -0.582133 -0.293893) (1.77156 -0.685731 -0.404509) (1.73279 -0.812344 -0.475528) (1.8297 -0.510211 -0.154509) (1.69098 -0.951056 -0.5) (1.19408 -1.11443 -0.293893) (1.64918 -1.08977 -0.475528) (1.6104 -1.21638 -0.404509) (1.57738 -1.31998 -0.293893) (2 -0.595491 -0.293893) (2 -0.706107 -0.404509) (2 -0.845491 -0.475528) (2 -1 -0.5) (2 -0.524472 -0.154509) (1.55227 -1.3919 -0.154509) (2 -1.15451 -0.475528) (2 -1.29389 -0.404509) (2 -1.40451 -0.293893) (2.4 -0.595491 -0.293893) (2.4 -0.706107 -0.404509) (2.4 -0.845491 -0.475528) (2.4 -1 -0.5) (2.4 -0.524472 -0.154509) (2 -1.47553 -0.154509) (2.4 -1.15451 -0.475528) (2.4 -1.29389 -0.404509) (2.4 -1.40451 -0.293893) (2.8 -0.595491 -0.293893) (2.8 -0.706107 -0.404509) (2.8 -0.845491 -0.475528) (2.8 -1 -0.5) (2.8 -0.524472 -0.154509) (2.4 -1.47553 -0.154509) (2.8 -1.15451 -0.475528) (2.8 -1.29389 -0.404509) (2.8 -1.40451 -0.293893) (3.2 -0.595491 -0.293893) (3.2 -0.706107 -0.404509) (3.2 -0.845491 -0.475528) (3.2 -1 -0.5) (3.2 -0.524472 -0.154509) (2.8 -1.47553 -0.154509) (3.2 -1.15451 -0.475528) (3.2 -1.29389 -0.404509) (3.2 -1.40451 -0.293893) (3.6 -0.595491 -0.293893) (3.6 -0.706107 -0.404509) (3.6 -0.845491 -0.475528) (3.6 -1 -0.5) (3.6 -0.524472 -0.154509) (3.2 -1.47553 -0.154509) (3.6 -1.15451 -0.475528) (3.6 -1.29389 -0.404509) (3.6 -1.40451 -0.293893) (4 -0.595491 -0.293893) (4 -0.706107 -0.404509) (4 -0.845491 -0.475528) (4 -1 -0.5) (4 -0.524472 -0.154509) (3.6 -1.47553 -0.154509) (4 -1.15451 -0.475528) (4 -1.29389 -0.404509) (4 -1.40451 -0.293893) (4.4 -0.595491 -0.293893) (4.4 -0.706107 -0.404509) (4.4 -0.845491 -0.475528) (4.4 -1 -0.5) (4.4 -0.524472 -0.154509) (4 -1.47553 -0.154509) (4.4 -1.15451 -0.475528) (4.4 -1.29389 -0.404509) (4.4 -1.40451 -0.293893) (4.8 -0.595491 -0.293893) (4.8 -0.706107 -0.404509) (4.8 -0.845491 -0.475528) (4.8 -1 -0.5) (4.8 -0.524472 -0.154509) (4.4 -1.47553 -0.154509) (4.8 -1.15451 -0.475528) (4.8 -1.29389 -0.404509) (4.8 -1.40451 -0.293893) (5.2 -0.595491 -0.293893) (5.2 -0.706107 -0.404509) (5.2 -0.845491 -0.475528) (5.2 -1 -0.5) (5.2 -0.524472 -0.154509) (4.8 -1.47553 -0.154509) (5.2 -1.15451 -0.475528) (5.2 -1.29389 -0.404509) (5.2 -1.40451 -0.293893) (5.6 -0.595491 -0.293893) (5.6 -0.706107 -0.404509) (5.6 -0.845491 -0.475528) (5.6 -1 -0.5) (5.6 -0.524472 -0.154509) (5.2 -1.47553 -0.154509) (5.6 -1.15451 -0.475528) (5.6 -1.29389 -0.404509) (5.6 -1.40451 -0.293893) (5.6 -1.47553 -0.154509)) +1700 +( +((0 1 2) 1) +((1 0 3) 1) +((2 4 0) 1) +((3 5 1) 1) +((6 3 0) 1) +((0 4 7) 1) +((5 3 8) 1) +((8 3 6) 1) +((0 9 6) 1) +((7 9 0) 1) +((8 10 5) 1) +((6 11 8) 1) +((12 6 9) 1) +((13 9 7) 1) +((10 8 14) 1) +((15 11 6) 1) +((14 8 11) 1) +((6 12 15) 1) +((9 13 12) 1) +((7 16 13) 1) +((14 17 10) 1) +((11 15 18) 1) +((11 19 14) 1) +((15 12 20) 1) +((20 12 13) 1) +((13 16 21) 1) +((17 14 22) 1) +((18 19 11) 1) +((18 15 23) 1) +((14 19 24) 1) +((20 23 15) 1) +((13 25 20) 1) +((21 25 13) 1) +((22 26 17) 1) +((24 22 14) 1) +((24 19 18) 1) +((23 27 18) 1) +((23 20 28) 1) +((28 20 25) 1) +((25 21 29) 1) +((18 30 24) 1) +((27 23 31) 1) +((18 27 32) 1) +((28 31 23) 1) +((25 33 28) 1) +((29 33 25) 1) +((32 30 18) 1) +((31 34 27) 1) +((35 32 27) 1) +((36 31 28) 1) +((37 28 33) 1) +((33 29 38) 1) +((34 31 36) 1) +((27 34 35) 1) +((28 37 36) 1) +((33 39 37) 1) +((38 39 33) 1) +((36 40 34) 1) +((35 34 40) 1) +((36 37 41) 1) +((37 39 42) 1) +((42 39 38) 1) +((43 40 36) 1) +((40 44 35) 1) +((42 41 37) 1) +((41 45 36) 1) +((38 46 42) 1) +((40 43 47) 1) +((36 45 43) 1) +((47 44 40) 1) +((48 41 42) 1) +((45 41 48) 1) +((42 46 49) 1) +((47 43 50) 1) +((43 45 51) 1) +((42 52 48) 1) +((48 51 45) 1) +((49 52 42) 1) +((51 50 43) 1) +((50 53 47) 1) +((54 48 52) 1) +((55 51 48) 1) +((52 49 56) 1) +((50 51 55) 1) +((57 53 50) 1) +((48 54 55) 1) +((52 58 54) 1) +((56 58 52) 1) +((55 59 50) 1) +((50 59 57) 1) +((55 54 60) 1) +((54 58 61) 1) +((61 58 56) 1) +((62 59 55) 1) +((63 57 59) 1) +((61 60 54) 1) +((60 64 55) 1) +((56 65 61) 1) +((59 62 63) 1) +((55 64 62) 1) +((66 67 68) 2) +((69 67 66) 2) +((68 67 70) 2) +((68 71 66) 2) +((70 67 69) 2) +((66 72 69) 2) +((70 73 68) 2) +((69 74 70) 2) +((75 69 72) 2) +((73 70 76) 2) +((74 69 75) 2) +((76 70 74) 2) +((72 77 75) 2) +((76 78 73) 2) +((75 79 74) 2) +((74 80 76) 2) +((75 77 81) 2) +((82 78 76) 2) +((83 79 75) 2) +((74 79 84) 2) +((84 80 74) 2) +((76 80 85) 2) +((81 86 75) 2) +((76 87 82) 2) +((79 83 88) 2) +((75 86 83) 2) +((88 84 79) 2) +((80 84 89) 2) +((85 87 76) 2) +((89 85 80) 2) +((86 81 90) 2) +((82 87 91) 2) +((92 88 83) 2) +((83 86 93) 2) +((89 84 88) 2) +((91 87 85) 2) +((94 85 89) 2) +((90 93 86) 2) +((91 95 82) 2) +((96 88 92) 2) +((83 97 92) 2) +((93 97 83) 2) +((88 96 89) 2) +((85 94 91) 2) +((89 98 94) 2) +((95 91 99) 2) +((92 100 96) 2) +((89 96 101) 2) +((99 91 94) 2) +((101 98 89) 2) +((94 98 102) 2) +((99 103 95) 2) +((96 100 104) 2) +((104 101 96) 2) +((94 105 99) 2) +((98 101 106) 2) +((102 105 94) 2) +((106 102 98) 2) +((103 99 107) 2) +((106 101 104) 2) +((107 99 105) 2) +((105 102 108) 2) +((102 106 109) 2) +((107 110 103) 2) +((104 111 106) 2) +((105 112 107) 2) +((108 112 105) 2) +((109 108 102) 2) +((109 106 111) 2) +((113 110 107) 2) +((114 107 112) 2) +((115 112 108) 2) +((116 108 109) 2) +((111 117 109) 2) +((107 114 113) 2) +((112 115 114) 2) +((108 116 115) 2) +((109 118 116) 2) +((109 117 119) 2) +((113 114 120) 2) +((120 114 115) 2) +((115 116 121) 2) +((116 118 122) 2) +((119 118 109) 2) +((120 123 113) 2) +((115 124 120) 2) +((121 124 115) 2) +((122 121 116) 2) +((122 118 119) 2) +((125 123 120) 2) +((126 120 124) 2) +((127 124 121) 2) +((128 121 122) 2) +((119 129 122) 2) +((120 126 125) 2) +((124 127 126) 2) +((121 128 127) 2) +((122 130 128) 2) +((130 122 129) 2) +((129 131 130) 2) +((65 132 133) 3) +((134 133 132) 3) +((133 61 65) 3) +((132 135 134) 3) +((133 134 136) 3) +((61 133 137) 3) +((138 134 135) 3) +((139 136 134) 3) +((136 137 133) 3) +((137 60 61) 3) +((135 140 138) 3) +((134 138 139) 3) +((136 139 141) 3) +((137 136 142) 3) +((60 137 143) 3) +((144 138 140) 3) +((145 139 138) 3) +((146 141 139) 3) +((141 142 136) 3) +((142 143 137) 3) +((143 64 60) 3) +((140 147 144) 3) +((138 144 145) 3) +((139 145 146) 3) +((141 146 148) 3) +((142 141 149) 3) +((143 142 150) 3) +((64 143 151) 3) +((152 144 147) 3) +((153 145 144) 3) +((154 146 145) 3) +((155 148 146) 3) +((148 149 141) 3) +((149 150 142) 3) +((150 151 143) 3) +((151 62 64) 3) +((147 156 152) 3) +((144 152 153) 3) +((145 153 154) 3) +((146 154 155) 3) +((148 155 157) 3) +((149 148 158) 3) +((150 149 159) 3) +((151 150 160) 3) +((62 151 161) 3) +((162 152 156) 3) +((163 153 152) 3) +((154 153 163) 3) +((164 155 154) 3) +((157 155 164) 3) +((157 158 148) 3) +((158 159 149) 3) +((159 160 150) 3) +((160 161 151) 3) +((161 63 62) 3) +((156 165 162) 3) +((152 162 163) 3) +((163 166 154) 3) +((154 166 164) 3) +((164 167 157) 3) +((168 162 165) 3) +((169 163 162) 3) +((166 163 169) 3) +((170 164 166) 3) +((171 167 164) 3) +((165 172 168) 3) +((162 168 169) 3) +((169 173 166) 3) +((166 173 170) 3) +((164 170 171) 3) +((174 168 172) 3) +((175 169 168) 3) +((176 173 169) 3) +((177 170 173) 3) +((178 171 170) 3) +((172 179 174) 3) +((168 174 175) 3) +((169 175 176) 3) +((173 176 177) 3) +((170 177 178) 3) +((174 179 180) 3) +((175 174 181) 3) +((182 176 175) 3) +((177 176 182) 3) +((178 177 183) 3) +((180 181 174) 3) +((181 184 175) 3) +((175 184 182) 3) +((182 183 177) 3) +((183 185 178) 3) +((181 180 186) 3) +((184 181 187) 3) +((188 182 184) 3) +((183 182 188) 3) +((189 185 183) 3) +((186 187 181) 3) +((187 190 184) 3) +((184 190 188) 3) +((188 191 183) 3) +((183 191 189) 3) +((187 186 192) 3) +((190 187 193) 3) +((194 188 190) 3) +((191 188 194) 3) +((195 189 191) 3) +((192 193 187) 3) +((193 196 190) 3) +((190 196 194) 3) +((194 197 191) 3) +((191 197 195) 3) +((193 192 198) 3) +((199 196 193) 3) +((194 196 199) 3) +((200 197 194) 3) +((195 197 200) 3) +((198 201 193) 3) +((193 201 199) 3) +((199 202 194) 3) +((194 202 200) 3) +((200 203 195) 3) +((204 201 198) 3) +((199 201 204) 3) +((202 199 205) 3) +((206 200 202) 3) +((207 203 200) 3) +((198 208 204) 3) +((204 205 199) 3) +((205 209 202) 3) +((200 206 207) 3) +((202 209 206) 3) +((204 208 210) 3) +((205 204 211) 3) +((212 209 205) 3) +((207 206 213) 3) +((213 206 209) 3) +((210 211 204) 3) +((211 214 205) 3) +((209 212 213) 3) +((205 214 212) 3) +((213 215 207) 3) +((211 210 216) 3) +((214 211 217) 3) +((213 212 218) 3) +((218 212 214) 3) +((215 213 219) 3) +((216 217 211) 3) +((217 220 214) 3) +((218 219 213) 3) +((214 220 218) 3) +((219 221 215) 3) +((222 217 216) 3) +((223 220 217) 3) +((224 219 218) 3) +((225 218 220) 3) +((226 221 219) 3) +((216 227 222) 3) +((217 222 223) 3) +((220 223 225) 3) +((218 225 224) 3) +((219 224 226) 3) +((228 222 227) 3) +((229 223 222) 3) +((230 225 223) 3) +((231 224 225) 3) +((232 226 224) 3) +((227 233 228) 3) +((222 228 229) 3) +((223 229 230) 3) +((225 230 231) 3) +((224 231 232) 3) +((234 228 233) 3) +((235 229 228) 3) +((236 230 229) 3) +((237 231 230) 3) +((238 232 231) 3) +((233 239 234) 3) +((228 234 235) 3) +((229 235 236) 3) +((230 236 237) 3) +((231 237 238) 3) +((240 234 239) 3) +((241 235 234) 3) +((242 236 235) 3) +((243 237 236) 3) +((244 238 237) 3) +((239 245 240) 3) +((234 240 241) 3) +((235 241 242) 3) +((236 242 243) 3) +((237 243 244) 3) +((246 240 245) 3) +((247 241 240) 3) +((248 242 241) 3) +((249 243 242) 3) +((250 244 243) 3) +((245 251 246) 3) +((240 246 247) 3) +((241 247 248) 3) +((242 248 249) 3) +((243 249 250) 3) +((252 246 251) 3) +((253 247 246) 3) +((254 248 247) 3) +((255 249 248) 3) +((256 250 249) 3) +((251 257 252) 3) +((246 252 253) 3) +((247 253 254) 3) +((248 254 255) 3) +((249 255 256) 3) +((258 252 257) 3) +((259 253 252) 3) +((260 254 253) 3) +((261 255 254) 3) +((262 256 255) 3) +((257 263 258) 3) +((252 258 259) 3) +((253 259 260) 3) +((254 260 261) 3) +((255 261 262) 3) +((264 258 263) 3) +((265 259 258) 3) +((266 260 259) 3) +((267 261 260) 3) +((268 262 261) 3) +((263 269 264) 3) +((258 264 265) 3) +((259 265 266) 3) +((260 266 267) 3) +((261 267 268) 3) +((270 264 269) 3) +((271 265 264) 3) +((272 266 265) 3) +((273 267 266) 3) +((274 268 267) 3) +((269 275 270) 3) +((264 270 271) 3) +((265 271 272) 3) +((266 272 273) 3) +((267 273 274) 3) +((126 270 275) 3) +((127 271 270) 3) +((128 272 271) 3) +((130 273 272) 3) +((131 274 273) 3) +((275 125 126) 3) +((270 126 127) 3) +((271 127 128) 3) +((272 128 130) 3) +((273 130 131) 3) +((2 1 276) 3) +((277 276 1) 3) +((276 278 2) 3) +((1 5 277) 3) +((276 277 279) 3) +((278 276 280) 3) +((281 277 5) 3) +((282 279 277) 3) +((279 280 276) 3) +((280 283 278) 3) +((5 10 281) 3) +((277 281 282) 3) +((279 282 284) 3) +((280 279 285) 3) +((283 280 286) 3) +((287 281 10) 3) +((288 282 281) 3) +((289 284 282) 3) +((284 285 279) 3) +((285 286 280) 3) +((286 290 283) 3) +((10 17 287) 3) +((281 287 288) 3) +((282 288 289) 3) +((284 289 291) 3) +((285 284 292) 3) +((286 285 293) 3) +((290 286 294) 3) +((295 287 17) 3) +((296 288 287) 3) +((297 289 288) 3) +((298 291 289) 3) +((291 292 284) 3) +((292 293 285) 3) +((293 294 286) 3) +((294 299 290) 3) +((17 26 295) 3) +((287 295 296) 3) +((288 296 297) 3) +((289 297 298) 3) +((291 298 300) 3) +((292 291 301) 3) +((293 292 302) 3) +((294 293 303) 3) +((299 294 304) 3) +((300 301 291) 3) +((301 302 292) 3) +((302 303 293) 3) +((303 304 294) 3) +((304 305 299) 3) +((301 300 306) 3) +((302 301 307) 3) +((303 302 308) 3) +((304 303 309) 3) +((310 305 304) 3) +((306 307 301) 3) +((307 308 302) 3) +((308 309 303) 3) +((309 311 304) 3) +((304 311 310) 3) +((312 307 306) 3) +((313 308 307) 3) +((309 308 313) 3) +((314 311 309) 3) +((315 310 311) 3) +((307 312 313) 3) +((306 316 312) 3) +((313 317 309) 3) +((311 314 315) 3) +((309 317 314) 3) +((318 313 312) 3) +((319 312 316) 3) +((320 317 313) 3) +((321 315 314) 3) +((322 314 317) 3) +((313 318 320) 3) +((312 319 318) 3) +((316 323 319) 3) +((317 320 322) 3) +((314 322 321) 3) +((324 320 318) 3) +((318 319 325) 3) +((319 323 326) 3) +((322 320 324) 3) +((321 322 327) 3) +((318 328 324) 3) +((325 328 318) 3) +((326 325 319) 3) +((324 327 322) 3) +((327 329 321) 3) +((330 324 328) 3) +((331 328 325) 3) +((332 325 326) 3) +((333 327 324) 3) +((329 327 333) 3) +((324 330 333) 3) +((328 331 330) 3) +((325 332 331) 3) +((326 334 332) 3) +((333 335 329) 3) +((336 333 330) 3) +((337 330 331) 3) +((338 331 332) 3) +((339 332 334) 3) +((340 335 333) 3) +((333 336 340) 3) +((330 337 336) 3) +((331 338 337) 3) +((332 339 338) 3) +((334 341 339) 3) +((340 336 342) 3) +((342 336 337) 3) +((337 338 343) 3) +((343 338 339) 3) +((339 341 344) 3) +((342 345 340) 3) +((337 346 342) 3) +((343 346 337) 3) +((339 347 343) 3) +((344 347 339) 3) +((345 342 348) 3) +((342 346 349) 3) +((349 346 343) 3) +((350 343 347) 3) +((351 347 344) 3) +((349 348 342) 3) +((348 352 345) 3) +((343 350 349) 3) +((347 351 350) 3) +((344 353 351) 3) +((354 348 349) 3) +((352 348 354) 3) +((349 350 355) 3) +((355 350 351) 3) +((351 353 356) 3) +((349 357 354) 3) +((354 358 352) 3) +((355 357 349) 3) +((351 359 355) 3) +((356 359 351) 3) +((360 354 357) 3) +((358 354 360) 3) +((357 355 361) 3) +((361 355 359) 3) +((359 356 362) 3) +((357 363 360) 3) +((360 364 358) 3) +((361 363 357) 3) +((359 365 361) 3) +((362 365 359) 3) +((360 363 366) 3) +((364 360 367) 3) +((363 361 368) 3) +((361 365 369) 3) +((365 362 370) 3) +((368 366 363) 3) +((366 367 360) 3) +((367 371 364) 3) +((369 368 361) 3) +((370 369 365) 3) +((366 368 372) 3) +((367 366 373) 3) +((371 367 374) 3) +((368 369 375) 3) +((369 370 376) 3) +((375 372 368) 3) +((372 373 366) 3) +((373 374 367) 3) +((374 377 371) 3) +((376 375 369) 3) +((372 375 378) 3) +((373 372 379) 3) +((374 373 380) 3) +((377 374 381) 3) +((375 376 382) 3) +((382 378 375) 3) +((378 379 372) 3) +((379 380 373) 3) +((380 381 374) 3) +((381 383 377) 3) +((378 382 384) 3) +((379 378 385) 3) +((380 379 386) 3) +((381 380 387) 3) +((383 381 388) 3) +((384 385 378) 3) +((385 386 379) 3) +((386 387 380) 3) +((387 388 381) 3) +((388 389 383) 3) +((385 384 390) 3) +((386 385 391) 3) +((387 386 392) 3) +((388 387 393) 3) +((389 388 394) 3) +((390 391 385) 3) +((391 392 386) 3) +((392 393 387) 3) +((393 394 388) 3) +((394 395 389) 3) +((391 390 396) 3) +((392 391 397) 3) +((393 392 398) 3) +((394 393 399) 3) +((395 394 400) 3) +((396 397 391) 3) +((397 398 392) 3) +((398 399 393) 3) +((399 400 394) 3) +((400 401 395) 3) +((397 396 402) 3) +((398 397 403) 3) +((399 398 404) 3) +((400 399 405) 3) +((401 400 406) 3) +((402 403 397) 3) +((403 404 398) 3) +((404 405 399) 3) +((405 406 400) 3) +((406 407 401) 3) +((403 402 408) 3) +((404 403 409) 3) +((405 404 410) 3) +((406 405 411) 3) +((407 406 412) 3) +((408 409 403) 3) +((409 410 404) 3) +((410 411 405) 3) +((411 412 406) 3) +((412 413 407) 3) +((409 408 414) 3) +((410 409 415) 3) +((411 410 416) 3) +((412 411 417) 3) +((413 412 418) 3) +((414 415 409) 3) +((415 416 410) 3) +((416 417 411) 3) +((417 418 412) 3) +((418 419 413) 3) +((415 414 90) 3) +((416 415 81) 3) +((417 416 77) 3) +((418 417 72) 3) +((419 418 66) 3) +((90 81 415) 3) +((81 77 416) 3) +((77 72 417) 3) +((72 66 418) 3) +((66 71 419) 3) +((63 161 420) 4) +((421 420 161) 4) +((420 57 63) 4) +((161 160 421) 4) +((420 421 422) 4) +((57 420 423) 4) +((424 421 160) 4) +((425 422 421) 4) +((422 423 420) 4) +((423 53 57) 4) +((160 159 424) 4) +((421 424 425) 4) +((422 425 426) 4) +((423 422 427) 4) +((53 423 428) 4) +((429 424 159) 4) +((430 425 424) 4) +((431 426 425) 4) +((426 427 422) 4) +((427 428 423) 4) +((428 47 53) 4) +((159 158 429) 4) +((424 429 430) 4) +((425 430 431) 4) +((426 431 432) 4) +((427 426 433) 4) +((428 427 434) 4) +((47 428 435) 4) +((436 429 158) 4) +((437 430 429) 4) +((438 431 430) 4) +((439 432 431) 4) +((432 433 426) 4) +((433 434 427) 4) +((434 435 428) 4) +((435 44 47) 4) +((158 157 436) 4) +((429 436 437) 4) +((430 437 438) 4) +((431 438 439) 4) +((432 439 440) 4) +((433 432 441) 4) +((434 433 442) 4) +((435 434 443) 4) +((44 435 444) 4) +((436 157 167) 4) +((437 436 445) 4) +((438 437 446) 4) +((447 439 438) 4) +((448 440 439) 4) +((440 441 432) 4) +((441 442 433) 4) +((442 443 434) 4) +((443 444 435) 4) +((444 35 44) 4) +((167 445 436) 4) +((445 446 437) 4) +((446 449 438) 4) +((438 449 447) 4) +((439 447 448) 4) +((440 448 450) 4) +((451 441 440) 4) +((452 442 441) 4) +((453 443 442) 4) +((454 444 443) 4) +((32 35 444) 4) +((445 167 171) 4) +((446 445 455) 4) +((449 446 456) 4) +((457 447 449) 4) +((458 448 447) 4) +((459 450 448) 4) +((450 460 440) 4) +((441 451 452) 4) +((440 460 451) 4) +((442 452 453) 4) +((443 453 454) 4) +((444 454 32) 4) +((171 455 445) 4) +((455 456 446) 4) +((456 461 449) 4) +((449 461 457) 4) +((447 457 458) 4) +((448 458 459) 4) +((450 459 462) 4) +((460 450 463) 4) +((464 452 451) 4) +((465 451 460) 4) +((466 453 452) 4) +((467 454 453) 4) +((30 32 454) 4) +((468 455 171) 4) +((469 456 455) 4) +((470 461 456) 4) +((471 457 461) 4) +((472 458 457) 4) +((473 459 458) 4) +((474 462 459) 4) +((462 463 450) 4) +((463 475 460) 4) +((452 464 466) 4) +((451 465 464) 4) +((460 475 465) 4) +((453 466 467) 4) +((454 467 30) 4) +((171 178 468) 4) +((455 468 469) 4) +((456 469 470) 4) +((461 470 471) 4) +((457 471 472) 4) +((458 472 473) 4) +((459 473 474) 4) +((462 474 476) 4) +((463 462 477) 4) +((475 463 478) 4) +((479 466 464) 4) +((480 464 465) 4) +((481 465 475) 4) +((482 467 466) 4) +((24 30 467) 4) +((483 468 178) 4) +((484 469 468) 4) +((485 470 469) 4) +((471 470 485) 4) +((472 471 486) 4) +((473 472 487) 4) +((474 473 488) 4) +((476 474 489) 4) +((476 477 462) 4) +((477 478 463) 4) +((478 490 475) 4) +((466 479 482) 4) +((464 480 479) 4) +((465 481 480) 4) +((475 490 481) 4) +((467 482 24) 4) +((178 185 483) 4) +((468 483 484) 4) +((469 484 485) 4) +((485 486 471) 4) +((486 487 472) 4) +((487 488 473) 4) +((488 489 474) 4) +((489 491 476) 4) +((477 476 492) 4) +((493 478 477) 4) +((494 490 478) 4) +((495 482 479) 4) +((496 479 480) 4) +((497 480 481) 4) +((498 481 490) 4) +((22 24 482) 4) +((499 483 185) 4) +((500 484 483) 4) +((501 485 484) 4) +((486 485 501) 4) +((487 486 502) 4) +((488 487 503) 4) +((489 488 504) 4) +((476 491 505) 4) +((491 489 506) 4) +((505 492 476) 4) +((492 507 477) 4) +((478 493 494) 4) +((477 507 493) 4) +((490 494 498) 4) +((482 495 22) 4) +((479 496 495) 4) +((480 497 496) 4) +((481 498 497) 4) +((185 189 499) 4) +((483 499 500) 4) +((484 500 501) 4) +((501 502 486) 4) +((502 503 487) 4) +((503 504 488) 4) +((504 506 489) 4) +((508 505 491) 4) +((506 509 491) 4) +((492 505 326) 4) +((507 492 323) 4) +((300 494 493) 4) +((306 493 507) 4) +((298 498 494) 4) +((26 22 495) 4) +((295 495 496) 4) +((296 496 497) 4) +((297 497 498) 4) +((510 499 189) 4) +((511 500 499) 4) +((501 500 511) 4) +((502 501 512) 4) +((503 502 513) 4) +((504 503 514) 4) +((506 504 515) 4) +((505 508 334) 4) +((491 509 508) 4) +((516 509 506) 4) +((334 326 505) 4) +((326 323 492) 4) +((323 316 507) 4) +((494 300 298) 4) +((493 306 300) 4) +((507 316 306) 4) +((498 298 297) 4) +((495 295 26) 4) +((496 296 295) 4) +((497 297 296) 4) +((499 510 511) 4) +((189 195 510) 4) +((511 512 501) 4) +((512 513 502) 4) +((513 514 503) 4) +((514 515 504) 4) +((515 517 506) 4) +((341 334 508) 4) +((518 508 509) 4) +((509 516 518) 4) +((506 517 516) 4) +((519 511 510) 4) +((520 510 195) 4) +((512 511 519) 4) +((513 512 521) 4) +((514 513 522) 4) +((515 514 523) 4) +((517 515 524) 4) +((508 518 341) 4) +((525 518 516) 4) +((526 516 517) 4) +((510 520 519) 4) +((195 203 520) 4) +((519 521 512) 4) +((521 522 513) 4) +((522 523 514) 4) +((523 524 515) 4) +((524 527 517) 4) +((344 341 518) 4) +((518 525 344) 4) +((516 526 525) 4) +((517 527 526) 4) +((528 519 520) 4) +((529 520 203) 4) +((521 519 528) 4) +((522 521 530) 4) +((531 523 522) 4) +((524 523 531) 4) +((527 524 532) 4) +((344 525 533) 4) +((533 525 526) 4) +((526 527 534) 4) +((520 529 528) 4) +((203 207 529) 4) +((528 530 521) 4) +((530 535 522) 4) +((522 535 531) 4) +((531 532 524) 4) +((532 534 527) 4) +((533 353 344) 4) +((526 536 533) 4) +((534 536 526) 4) +((528 529 537) 4) +((529 207 215) 4) +((538 530 528) 4) +((539 535 530) 4) +((540 531 535) 4) +((541 532 531) 4) +((542 534 532) 4) +((353 533 543) 4) +((533 536 544) 4) +((536 534 542) 4) +((215 537 529) 4) +((537 545 528) 4) +((530 538 539) 4) +((528 545 538) 4) +((535 539 540) 4) +((531 540 541) 4) +((532 541 542) 4) +((544 543 533) 4) +((543 356 353) 4) +((542 544 536) 4) +((537 215 221) 4) +((545 537 546) 4) +((547 539 538) 4) +((548 538 545) 4) +((549 540 539) 4) +((550 541 540) 4) +((551 542 541) 4) +((543 544 552) 4) +((356 543 553) 4) +((544 542 551) 4) +((221 546 537) 4) +((546 554 545) 4) +((539 547 549) 4) +((538 548 547) 4) +((545 554 548) 4) +((540 549 550) 4) +((541 550 551) 4) +((551 552 544) 4) +((552 553 543) 4) +((553 362 356) 4) +((555 546 221) 4) +((556 554 546) 4) +((557 549 547) 4) +((558 547 548) 4) +((559 548 554) 4) +((550 549 557) 4) +((551 550 560) 4) +((552 551 561) 4) +((553 552 562) 4) +((362 553 563) 4) +((221 226 555) 4) +((546 555 556) 4) +((554 556 559) 4) +((547 558 557) 4) +((548 559 558) 4) +((557 560 550) 4) +((560 561 551) 4) +((561 562 552) 4) +((562 563 553) 4) +((563 370 362) 4) +((564 555 226) 4) +((565 556 555) 4) +((566 559 556) 4) +((567 557 558) 4) +((568 558 559) 4) +((560 557 567) 4) +((561 560 569) 4) +((562 561 570) 4) +((563 562 571) 4) +((370 563 572) 4) +((226 232 564) 4) +((555 564 565) 4) +((556 565 566) 4) +((559 566 568) 4) +((558 568 567) 4) +((567 569 560) 4) +((569 570 561) 4) +((570 571 562) 4) +((571 572 563) 4) +((572 376 370) 4) +((573 564 232) 4) +((574 565 564) 4) +((575 566 565) 4) +((576 568 566) 4) +((577 567 568) 4) +((569 567 577) 4) +((570 569 578) 4) +((571 570 579) 4) +((572 571 580) 4) +((376 572 581) 4) +((232 238 573) 4) +((564 573 574) 4) +((565 574 575) 4) +((566 575 576) 4) +((568 576 577) 4) +((577 578 569) 4) +((578 579 570) 4) +((579 580 571) 4) +((580 581 572) 4) +((581 382 376) 4) +((582 573 238) 4) +((583 574 573) 4) +((584 575 574) 4) +((585 576 575) 4) +((586 577 576) 4) +((578 577 586) 4) +((579 578 587) 4) +((580 579 588) 4) +((581 580 589) 4) +((382 581 590) 4) +((238 244 582) 4) +((573 582 583) 4) +((574 583 584) 4) +((575 584 585) 4) +((576 585 586) 4) +((586 587 578) 4) +((587 588 579) 4) +((588 589 580) 4) +((589 590 581) 4) +((590 384 382) 4) +((591 582 244) 4) +((592 583 582) 4) +((593 584 583) 4) +((594 585 584) 4) +((595 586 585) 4) +((587 586 595) 4) +((588 587 596) 4) +((589 588 597) 4) +((590 589 598) 4) +((384 590 599) 4) +((244 250 591) 4) +((582 591 592) 4) +((583 592 593) 4) +((584 593 594) 4) +((585 594 595) 4) +((595 596 587) 4) +((596 597 588) 4) +((597 598 589) 4) +((598 599 590) 4) +((599 390 384) 4) +((600 591 250) 4) +((601 592 591) 4) +((602 593 592) 4) +((603 594 593) 4) +((604 595 594) 4) +((596 595 604) 4) +((597 596 605) 4) +((598 597 606) 4) +((599 598 607) 4) +((390 599 608) 4) +((250 256 600) 4) +((591 600 601) 4) +((592 601 602) 4) +((593 602 603) 4) +((594 603 604) 4) +((604 605 596) 4) +((605 606 597) 4) +((606 607 598) 4) +((607 608 599) 4) +((608 396 390) 4) +((609 600 256) 4) +((610 601 600) 4) +((611 602 601) 4) +((612 603 602) 4) +((613 604 603) 4) +((605 604 613) 4) +((606 605 614) 4) +((607 606 615) 4) +((608 607 616) 4) +((396 608 617) 4) +((256 262 609) 4) +((600 609 610) 4) +((601 610 611) 4) +((602 611 612) 4) +((603 612 613) 4) +((613 614 605) 4) +((614 615 606) 4) +((615 616 607) 4) +((616 617 608) 4) +((617 402 396) 4) +((618 609 262) 4) +((619 610 609) 4) +((620 611 610) 4) +((621 612 611) 4) +((622 613 612) 4) +((614 613 622) 4) +((615 614 623) 4) +((616 615 624) 4) +((617 616 625) 4) +((402 617 626) 4) +((262 268 618) 4) +((609 618 619) 4) +((610 619 620) 4) +((611 620 621) 4) +((612 621 622) 4) +((622 623 614) 4) +((623 624 615) 4) +((624 625 616) 4) +((625 626 617) 4) +((626 408 402) 4) +((627 618 268) 4) +((628 619 618) 4) +((629 620 619) 4) +((630 621 620) 4) +((631 622 621) 4) +((623 622 631) 4) +((624 623 632) 4) +((625 624 633) 4) +((626 625 634) 4) +((408 626 635) 4) +((268 274 627) 4) +((618 627 628) 4) +((619 628 629) 4) +((620 629 630) 4) +((621 630 631) 4) +((631 632 623) 4) +((632 633 624) 4) +((633 634 625) 4) +((634 635 626) 4) +((635 414 408) 4) +((129 627 274) 4) +((119 628 627) 4) +((117 629 628) 4) +((111 630 629) 4) +((104 631 630) 4) +((632 631 104) 4) +((633 632 100) 4) +((634 633 92) 4) +((635 634 97) 4) +((414 635 93) 4) +((274 131 129) 4) +((627 129 119) 4) +((628 119 117) 4) +((629 117 111) 4) +((630 111 104) 4) +((104 100 632) 4) +((100 92 633) 4) +((92 97 634) 4) +((97 93 635) 4) +((93 90 414) 4) +((2 278 636) 4) +((637 636 278) 4) +((636 4 2) 4) +((278 283 637) 4) +((636 637 638) 4) +((4 636 639) 4) +((640 637 283) 4) +((641 638 637) 4) +((638 639 636) 4) +((639 7 4) 4) +((283 290 640) 4) +((637 640 641) 4) +((638 641 642) 4) +((639 638 643) 4) +((7 639 644) 4) +((645 640 290) 4) +((646 641 640) 4) +((647 642 641) 4) +((642 643 638) 4) +((643 644 639) 4) +((644 16 7) 4) +((290 299 645) 4) +((640 645 646) 4) +((641 646 647) 4) +((642 647 648) 4) +((643 642 649) 4) +((644 643 650) 4) +((16 644 651) 4) +((652 645 299) 4) +((653 646 645) 4) +((654 647 646) 4) +((655 648 647) 4) +((648 649 642) 4) +((649 650 643) 4) +((650 651 644) 4) +((651 21 16) 4) +((299 305 652) 4) +((645 652 653) 4) +((646 653 654) 4) +((647 654 655) 4) +((648 655 656) 4) +((649 648 657) 4) +((650 649 658) 4) +((651 650 659) 4) +((21 651 660) 4) +((661 652 305) 4) +((653 652 661) 4) +((654 653 662) 4) +((655 654 663) 4) +((656 655 664) 4) +((656 657 648) 4) +((657 658 649) 4) +((658 659 650) 4) +((659 660 651) 4) +((660 29 21) 4) +((305 310 661) 4) +((661 662 653) 4) +((662 663 654) 4) +((663 664 655) 4) +((664 665 656) 4) +((666 657 656) 4) +((667 658 657) 4) +((668 659 658) 4) +((669 660 659) 4) +((38 29 660) 4) +((670 661 310) 4) +((662 661 670) 4) +((663 662 671) 4) +((664 663 672) 4) +((665 664 673) 4) +((656 665 674) 4) +((657 666 667) 4) +((656 675 666) 4) +((658 667 668) 4) +((659 668 669) 4) +((660 669 38) 4) +((310 315 670) 4) +((670 671 662) 4) +((671 672 663) 4) +((672 673 664) 4) +((673 676 665) 4) +((674 675 656) 4) +((677 674 665) 4) +((678 667 666) 4) +((679 666 675) 4) +((680 668 667) 4) +((681 669 668) 4) +((46 38 669) 4) +((682 670 315) 4) +((683 671 670) 4) +((684 672 671) 4) +((685 673 672) 4) +((686 676 673) 4) +((665 676 677) 4) +((675 674 687) 4) +((674 677 688) 4) +((667 678 680) 4) +((666 679 678) 4) +((675 689 679) 4) +((668 680 681) 4) +((669 681 46) 4) +((670 682 683) 4) +((315 321 682) 4) +((671 683 684) 4) +((672 684 685) 4) +((673 685 686) 4) +((677 676 686) 4) +((687 689 675) 4) +((688 687 674) 4) +((688 677 690) 4) +((691 680 678) 4) +((692 678 679) 4) +((693 679 689) 4) +((694 681 680) 4) +((49 46 681) 4) +((695 683 682) 4) +((682 321 329) 4) +((696 684 683) 4) +((697 685 684) 4) +((698 686 685) 4) +((686 690 677) 4) +((689 687 699) 4) +((687 688 700) 4) +((690 701 688) 4) +((680 691 694) 4) +((678 692 691) 4) +((679 693 692) 4) +((689 702 693) 4) +((681 694 49) 4) +((683 695 696) 4) +((682 703 695) 4) +((329 703 682) 4) +((684 696 697) 4) +((685 697 698) 4) +((690 686 698) 4) +((699 702 689) 4) +((700 699 687) 4) +((700 688 701) 4) +((701 690 704) 4) +((705 694 691) 4) +((706 691 692) 4) +((707 692 693) 4) +((708 693 702) 4) +((56 49 694) 4) +((709 696 695) 4) +((710 695 703) 4) +((703 329 335) 4) +((711 697 696) 4) +((712 698 697) 4) +((698 704 690) 4) +((702 699 713) 4) +((699 700 714) 4) +((701 715 700) 4) +((704 716 701) 4) +((694 705 56) 4) +((691 706 705) 4) +((692 707 706) 4) +((693 708 707) 4) +((702 717 708) 4) +((696 709 711) 4) +((695 710 709) 4) +((703 718 710) 4) +((335 718 703) 4) +((697 711 712) 4) +((704 698 712) 4) +((713 717 702) 4) +((714 713 699) 4) +((714 700 715) 4) +((715 701 716) 4) +((716 704 719) 4) +((65 56 705) 4) +((132 705 706) 4) +((135 706 707) 4) +((140 707 708) 4) +((147 708 717) 4) +((711 709 720) 4) +((709 710 721) 4) +((710 718 722) 4) +((718 335 340) 4) +((712 711 723) 4) +((712 719 704) 4) +((717 713 165) 4) +((713 714 172) 4) +((715 724 714) 4) +((716 725 715) 4) +((719 726 716) 4) +((705 132 65) 4) +((706 135 132) 4) +((707 140 135) 4) +((708 147 140) 4) +((717 156 147) 4) +((721 720 709) 4) +((720 723 711) 4) +((722 721 710) 4) +((340 722 718) 4) +((723 727 712) 4) +((728 719 712) 4) +((165 156 717) 4) +((172 165 713) 4) +((172 714 724) 4) +((724 715 725) 4) +((725 716 726) 4) +((729 726 719) 4) +((720 721 730) 4) +((723 720 731) 4) +((721 722 732) 4) +((722 340 345) 4) +((727 723 733) 4) +((712 727 728) 4) +((719 728 729) 4) +((724 179 172) 4) +((725 734 724) 4) +((726 735 725) 4) +((726 729 736) 4) +((732 730 721) 4) +((730 731 720) 4) +((731 733 723) 4) +((345 732 722) 4) +((733 737 727) 4) +((738 728 727) 4) +((739 729 728) 4) +((179 724 734) 4) +((734 725 735) 4) +((736 735 726) 4) +((740 736 729) 4) +((741 730 732) 4) +((731 730 741) 4) +((733 731 742) 4) +((743 732 345) 4) +((744 737 733) 4) +((727 737 738) 4) +((728 738 739) 4) +((729 739 740) 4) +((734 180 179) 4) +((735 745 734) 4) +((735 736 746) 4) +((736 740 747) 4) +((732 743 741) 4) +((741 742 731) 4) +((742 748 733) 4) +((345 352 743) 4) +((733 748 744) 4) +((738 737 744) 4) +((739 738 749) 4) +((740 739 750) 4) +((180 734 745) 4) +((746 745 735) 4) +((747 746 736) 4) +((751 747 740) 4) +((752 741 743) 4) +((753 742 741) 4) +((754 748 742) 4) +((755 743 352) 4) +((756 744 748) 4) +((744 749 738) 4) +((749 750 739) 4) +((750 757 740) 4) +((745 186 180) 4) +((186 745 746) 4) +((192 746 747) 4) +((198 747 751) 4) +((740 757 751) 4) +((743 755 752) 4) +((741 752 753) 4) +((742 753 754) 4) +((748 754 756) 4) +((352 358 755) 4) +((749 744 756) 4) +((750 749 758) 4) +((757 750 759) 4) +((746 192 186) 4) +((747 198 192) 4) +((751 208 198) 4) +((751 757 760) 4) +((761 752 755) 4) +((762 753 752) 4) +((763 754 753) 4) +((764 756 754) 4) +((765 755 358) 4) +((756 758 749) 4) +((758 759 750) 4) +((759 760 757) 4) +((210 208 751) 4) +((760 766 751) 4) +((755 765 761) 4) +((752 761 762) 4) +((753 762 763) 4) +((754 763 764) 4) +((758 756 764) 4) +((358 364 765) 4) +((759 758 767) 4) +((760 759 768) 4) +((751 766 210) 4) +((766 760 769) 4) +((770 761 765) 4) +((771 762 761) 4) +((772 763 762) 4) +((773 764 763) 4) +((764 767 758) 4) +((774 765 364) 4) +((767 768 759) 4) +((768 769 760) 4) +((216 210 766) 4) +((769 775 766) 4) +((765 774 770) 4) +((761 770 771) 4) +((762 771 772) 4) +((763 772 773) 4) +((767 764 773) 4) +((364 371 774) 4) +((768 767 776) 4) +((769 768 777) 4) +((766 775 216) 4) +((775 769 778) 4) +((779 770 774) 4) +((780 771 770) 4) +((781 772 771) 4) +((782 773 772) 4) +((773 776 767) 4) +((783 774 371) 4) +((776 777 768) 4) +((777 778 769) 4) +((216 775 784) 4) +((778 784 775) 4) +((774 783 779) 4) +((770 779 780) 4) +((771 780 781) 4) +((772 781 782) 4) +((776 773 782) 4) +((371 377 783) 4) +((777 776 785) 4) +((778 777 786) 4) +((784 227 216) 4) +((784 778 787) 4) +((788 779 783) 4) +((789 780 779) 4) +((790 781 780) 4) +((791 782 781) 4) +((782 785 776) 4) +((792 783 377) 4) +((785 786 777) 4) +((786 787 778) 4) +((227 784 793) 4) +((787 793 784) 4) +((783 792 788) 4) +((779 788 789) 4) +((780 789 790) 4) +((781 790 791) 4) +((785 782 791) 4) +((377 383 792) 4) +((786 785 794) 4) +((787 786 795) 4) +((793 233 227) 4) +((793 787 796) 4) +((797 788 792) 4) +((798 789 788) 4) +((799 790 789) 4) +((800 791 790) 4) +((791 794 785) 4) +((801 792 383) 4) +((794 795 786) 4) +((795 796 787) 4) +((233 793 802) 4) +((796 802 793) 4) +((792 801 797) 4) +((788 797 798) 4) +((789 798 799) 4) +((790 799 800) 4) +((794 791 800) 4) +((383 389 801) 4) +((795 794 803) 4) +((796 795 804) 4) +((802 239 233) 4) +((802 796 805) 4) +((806 797 801) 4) +((807 798 797) 4) +((808 799 798) 4) +((809 800 799) 4) +((800 803 794) 4) +((810 801 389) 4) +((803 804 795) 4) +((804 805 796) 4) +((239 802 811) 4) +((805 811 802) 4) +((801 810 806) 4) +((797 806 807) 4) +((798 807 808) 4) +((799 808 809) 4) +((803 800 809) 4) +((389 395 810) 4) +((804 803 812) 4) +((805 804 813) 4) +((811 245 239) 4) +((811 805 814) 4) +((815 806 810) 4) +((816 807 806) 4) +((817 808 807) 4) +((818 809 808) 4) +((809 812 803) 4) +((819 810 395) 4) +((812 813 804) 4) +((813 814 805) 4) +((245 811 820) 4) +((814 820 811) 4) +((810 819 815) 4) +((806 815 816) 4) +((807 816 817) 4) +((808 817 818) 4) +((812 809 818) 4) +((395 401 819) 4) +((813 812 821) 4) +((814 813 822) 4) +((820 251 245) 4) +((820 814 823) 4) +((824 815 819) 4) +((825 816 815) 4) +((826 817 816) 4) +((827 818 817) 4) +((818 821 812) 4) +((828 819 401) 4) +((821 822 813) 4) +((822 823 814) 4) +((251 820 829) 4) +((823 829 820) 4) +((819 828 824) 4) +((815 824 825) 4) +((816 825 826) 4) +((817 826 827) 4) +((821 818 827) 4) +((401 407 828) 4) +((822 821 830) 4) +((823 822 831) 4) +((829 257 251) 4) +((829 823 832) 4) +((833 824 828) 4) +((834 825 824) 4) +((835 826 825) 4) +((836 827 826) 4) +((827 830 821) 4) +((837 828 407) 4) +((830 831 822) 4) +((831 832 823) 4) +((257 829 838) 4) +((832 838 829) 4) +((828 837 833) 4) +((824 833 834) 4) +((825 834 835) 4) +((826 835 836) 4) +((830 827 836) 4) +((407 413 837) 4) +((831 830 839) 4) +((832 831 840) 4) +((838 263 257) 4) +((838 832 841) 4) +((842 833 837) 4) +((843 834 833) 4) +((844 835 834) 4) +((845 836 835) 4) +((836 839 830) 4) +((846 837 413) 4) +((839 840 831) 4) +((840 841 832) 4) +((263 838 847) 4) +((841 847 838) 4) +((837 846 842) 4) +((833 842 843) 4) +((834 843 844) 4) +((835 844 845) 4) +((839 836 845) 4) +((413 419 846) 4) +((840 839 848) 4) +((841 840 849) 4) +((847 269 263) 4) +((847 841 850) 4) +((73 842 846) 4) +((78 843 842) 4) +((82 844 843) 4) +((95 845 844) 4) +((845 848 839) 4) +((68 846 419) 4) +((848 849 840) 4) +((849 850 841) 4) +((269 847 851) 4) +((850 851 847) 4) +((846 68 73) 4) +((842 73 78) 4) +((843 78 82) 4) +((844 82 95) 4) +((848 845 95) 4) +((419 71 68) 4) +((849 848 103) 4) +((850 849 110) 4) +((851 275 269) 4) +((851 850 113) 4) +((95 103 848) 4) +((103 110 849) 4) +((110 113 850) 4) +((275 851 123) 4) +((113 123 851) 4) +((123 125 275) 4) +) +160 +( +(389 383) +(384 390) +(1 2) +(2 4) +(203 195) +(5 1) +(4 7) +(299 290) +(26 295) +(110 103) +(207 203) +(295 296) +(395 389) +(104 111) +(296 297) +(390 396) +(198 208) +(297 298) +(298 300) +(10 5) +(113 110) +(208 210) +(111 117) +(401 395) +(396 402) +(305 299) +(7 16) +(300 306) +(17 10) +(117 119) +(215 207) +(210 216) +(310 305) +(16 21) +(407 401) +(402 408) +(123 113) +(221 215) +(125 123) +(315 310) +(22 26) +(26 17) +(306 316) +(24 22) +(119 129) +(413 407) +(226 221) +(408 414) +(126 125) +(216 227) +(127 126) +(128 127) +(21 29) +(130 128) +(30 24) +(129 131) +(321 315) +(131 130) +(65 132) +(316 323) +(132 135) +(32 30) +(419 413) +(232 226) +(414 90) +(227 233) +(35 32) +(323 326) +(29 38) +(71 419) +(135 140) +(238 232) +(329 321) +(233 239) +(44 35) +(140 147) +(326 334) +(38 46) +(244 238) +(335 329) +(239 245) +(47 44) +(46 49) +(340 335) +(334 341) +(250 244) +(245 251) +(53 47) +(147 156) +(341 344) +(49 56) +(345 340) +(57 53) +(256 250) +(251 257) +(157 158) +(63 57) +(352 345) +(158 159) +(159 160) +(61 60) +(160 161) +(60 64) +(344 353) +(262 256) +(161 63) +(156 165) +(56 65) +(257 263) +(65 61) +(62 63) +(64 62) +(353 356) +(167 157) +(68 71) +(358 352) +(71 66) +(66 72) +(268 262) +(171 167) +(263 269) +(165 172) +(73 68) +(356 362) +(72 77) +(364 358) +(78 73) +(274 268) +(178 171) +(269 275) +(172 179) +(77 81) +(82 78) +(179 180) +(362 370) +(371 364) +(131 274) +(275 125) +(278 2) +(185 178) +(180 186) +(370 376) +(81 90) +(377 371) +(189 185) +(283 278) +(90 93) +(95 82) +(186 192) +(376 382) +(97 92) +(93 97) +(195 189) +(383 377) +(382 384) +(92 100) +(290 283) +(192 198) +(103 95) +(100 104) +)0() +1(refFine +2 +500 +( +1042 +1043 +1044 +1045 +1046 +1047 +1048 +1049 +1050 +1051 +1052 +1053 +1054 +1055 +1056 +1057 +1058 +1059 +1060 +1061 +1062 +1063 +1064 +1065 +1066 +1067 +1068 +1069 +1070 +1071 +1072 +1073 +1074 +1075 +1076 +1077 +1078 +1079 +1080 +1081 +1082 +1083 +1084 +1085 +1086 +1087 +1088 +1089 +1090 +1091 +1092 +1093 +1094 +1095 +1096 +1097 +1098 +1099 +1100 +1101 +1102 +1103 +1104 +1105 +1106 +1107 +1108 +1109 +1110 +1111 +1112 +1113 +1114 +1115 +1116 +1117 +1118 +1119 +1120 +1121 +1122 +1123 +1124 +1125 +1126 +1127 +1128 +1129 +1130 +1131 +1132 +1133 +1134 +1135 +1136 +1137 +1138 +1139 +1140 +1141 +1142 +1143 +1144 +1145 +1146 +1147 +1148 +1149 +1150 +1151 +1152 +1153 +1154 +1155 +1156 +1157 +1158 +1159 +1160 +1161 +1162 +1163 +1164 +1165 +1166 +1167 +1168 +1169 +1170 +1171 +1172 +1173 +1174 +1175 +1176 +1177 +1178 +1179 +1180 +1181 +1182 +1183 +1184 +1185 +1186 +1187 +1188 +1189 +1190 +1191 +1192 +1193 +1194 +1195 +1196 +1197 +1198 +1199 +700 +701 +702 +703 +704 +705 +706 +707 +708 +709 +710 +711 +712 +713 +714 +715 +716 +717 +718 +719 +720 +721 +722 +723 +724 +725 +726 +727 +728 +729 +730 +731 +732 +733 +734 +735 +736 +737 +738 +739 +740 +741 +742 +743 +744 +745 +746 +747 +748 +749 +750 +751 +752 +753 +754 +755 +756 +757 +758 +759 +760 +761 +762 +763 +764 +765 +766 +767 +768 +769 +770 +771 +772 +773 +774 +775 +776 +777 +778 +779 +780 +781 +782 +783 +784 +785 +786 +787 +788 +789 +790 +791 +792 +793 +794 +795 +796 +797 +798 +799 +800 +801 +802 +803 +804 +805 +806 +807 +808 +809 +810 +811 +812 +813 +814 +815 +816 +817 +818 +819 +820 +821 +822 +823 +824 +825 +826 +827 +828 +829 +830 +831 +832 +833 +834 +835 +836 +837 +838 +839 +840 +841 +842 +843 +844 +845 +846 +847 +848 +849 +850 +851 +852 +853 +854 +855 +856 +857 +858 +859 +860 +861 +862 +863 +864 +865 +866 +867 +868 +869 +870 +871 +872 +873 +874 +875 +876 +877 +878 +879 +880 +881 +882 +883 +884 +885 +886 +887 +888 +889 +890 +891 +892 +893 +894 +895 +896 +897 +898 +899 +900 +901 +902 +903 +904 +905 +906 +907 +908 +909 +910 +911 +912 +913 +914 +915 +916 +917 +918 +919 +920 +921 +922 +923 +924 +925 +926 +927 +928 +929 +930 +931 +932 +933 +934 +935 +936 +937 +938 +939 +940 +941 +942 +943 +944 +945 +946 +947 +948 +949 +950 +951 +952 +953 +954 +955 +956 +957 +958 +959 +960 +961 +962 +963 +964 +965 +966 +967 +968 +969 +970 +971 +972 +973 +974 +975 +976 +977 +978 +979 +980 +981 +982 +983 +984 +985 +986 +987 +988 +989 +990 +991 +992 +993 +994 +995 +996 +997 +998 +999 +1000 +1001 +1002 +1003 +1004 +1005 +1006 +1007 +1008 +1009 +1010 +1011 +1012 +1013 +1014 +1015 +1016 +1017 +1018 +1019 +1020 +1021 +1022 +1023 +1024 +1025 +1026 +1027 +1028 +1029 +1030 +1031 +1032 +1033 +1034 +1035 +1036 +1037 +1038 +1039 +1040 +1041 +))0() \ No newline at end of file diff --git a/tutorials/cartesianMesh/sBendOctree/system/controlDict b/tutorials/cartesianMesh/sBendOctree/system/controlDict new file mode 100644 index 0000000000000000000000000000000000000000..236cab7abf84f8bbec6d25cc7748f25afa8cd0a5 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/system/controlDict @@ -0,0 +1,36 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +application ; +deltaT 0.001; +endTime 2; +graphFormat raw; +purgeWrite 0; +runTimeModifiable yes; +startFrom latestTime; +startTime 0; +stopAt endTime; +timeFormat general; +timePrecision 6; +writeCompression compressed; +writeControl timeStep; +writeFormat binary; +writeInterval 100; +writePrecision 6; + +// ************************************************************************* // \ No newline at end of file diff --git a/tutorials/cartesianMesh/sBendOctree/system/fvSchemes b/tutorials/cartesianMesh/sBendOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sBendOctree/system/fvSolution b/tutorials/cartesianMesh/sBendOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sBendOctree/system/meshDict b/tutorials/cartesianMesh/sBendOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..37536f6dd142f08fc8ba559a02a772b247538d0b --- /dev/null +++ b/tutorials/cartesianMesh/sBendOctree/system/meshDict @@ -0,0 +1,53 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +maxCellSize 0.1; + +surfaceFile "sBend.fms"; + +boundaryLayers +{ + nLayers 1; + + patchBoundaryLayers + { + + walls + { + nLayers 3; + thicknessRatio 1.2; + } + } +} + +localRefinement +{ + + refFine + { + cellSize 0.025; + } + + walls + { + cellSize 0.05; + } +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sawOctree/0/.gitignore b/tutorials/cartesianMesh/sawOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cartesianMesh/sawOctree/Allclean b/tutorials/cartesianMesh/sawOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..d1ab657facfa3e8154c5c61ec37e9f522128f438 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/Allclean @@ -0,0 +1,14 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh +rm -r 0/polyMesh +rm -r processor* diff --git a/tutorials/cartesianMesh/sawOctree/Allrun b/tutorials/cartesianMesh/sawOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..7cf19bbb1b950f6ef528e6635ab15557d3c49bc2 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/Allrun @@ -0,0 +1,8 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication preparePar +runParallel cartesianMesh 4 +runParallel checkMesh 4 +runApplication reconstructParMesh -zeroTime diff --git a/tutorials/cartesianMesh/sawOctree/README b/tutorials/cartesianMesh/sawOctree/README new file mode 100644 index 0000000000000000000000000000000000000000..44510a92c1b83585bc21b166a5710214d1e6c9be --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/README @@ -0,0 +1 @@ +Please run cartesianMesh to generate the mesh. diff --git a/tutorials/cartesianMesh/sawOctree/constant/.gitignore b/tutorials/cartesianMesh/sawOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/sawOctree/sav.smesh b/tutorials/cartesianMesh/sawOctree/sav.smesh similarity index 100% rename from tutorials/sawOctree/sav.smesh rename to tutorials/cartesianMesh/sawOctree/sav.smesh diff --git a/tutorials/sawOctree/sav.stl b/tutorials/cartesianMesh/sawOctree/sav.stl similarity index 100% rename from tutorials/sawOctree/sav.stl rename to tutorials/cartesianMesh/sawOctree/sav.stl diff --git a/tutorials/sawOctree/sav1.stl b/tutorials/cartesianMesh/sawOctree/sav1.stl similarity index 100% rename from tutorials/sawOctree/sav1.stl rename to tutorials/cartesianMesh/sawOctree/sav1.stl diff --git a/tutorials/cartesianMesh/sawOctree/system/controlDict b/tutorials/cartesianMesh/sawOctree/system/controlDict new file mode 100644 index 0000000000000000000000000000000000000000..de6110208c22b21e0360f5c51bdfa4e80a65e393 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/system/controlDict @@ -0,0 +1,53 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// ************************************************************************* // + +applicationClass ; + +startFrom latestTime; + +startTime 0; + +stopAt endTime; + +endTime 500; + +deltaT 1; + +writeControl timeStep; + +writeInterval 100; + +cycleWrite 0; + +writeFormat binary; + +writeCompression compressed; + +timeFormat general; + +timePrecision 6; + +runTimeModifiable yes; + +nCorrectors 2; + +nNonOrthogonalCorrectors 0; + + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sawOctree/system/decomposeParDict b/tutorials/cartesianMesh/sawOctree/system/decomposeParDict new file mode 100644 index 0000000000000000000000000000000000000000..cdb3ad7e896e967804ce626e350093e40c76c971 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/system/decomposeParDict @@ -0,0 +1,23 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + note "mesh decomposition control dictionary"; + location "system"; + object decomposeParDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +numberOfSubdomains 4; + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sawOctree/system/fvSchemes b/tutorials/cartesianMesh/sawOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sawOctree/system/fvSolution b/tutorials/cartesianMesh/sawOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/cartesianMesh/sawOctree/system/meshDict b/tutorials/cartesianMesh/sawOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..5bcf3b848d235769583f1ab881ca940d5bc4fee0 --- /dev/null +++ b/tutorials/cartesianMesh/sawOctree/system/meshDict @@ -0,0 +1,26 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +surfaceFile "sav1.stl"; + +maxCellSize 0.25; + +boundaryCellSize 0.125; + +// ************************************************************************* // diff --git a/tutorials/cutCubeOctree/system/controlDict b/tutorials/cutCubeOctree/system/controlDict deleted file mode 100755 index dee4075f5a0b118368d06622ffb46c63d5e84b48..0000000000000000000000000000000000000000 --- a/tutorials/cutCubeOctree/system/controlDict +++ /dev/null @@ -1,49 +0,0 @@ -// ************************************************************************* // -// FoamX Case Dictionary. - -version 1.0; -format ascii; -root "/home/franjo/foam/franjo2.0/run"; -case "jetAdaptive"; -instance "system"; -local ""; -class dictionary; -form dictionary; -object controlDict; - -// ************************************************************************* // - -applicationClass icoFoam; - -startFrom latestTime; - -startTime 0; - -stopAt endTime; - -endTime 500; - -deltaT 1; - -writeControl timeStep; - -writeInterval 100; - -cycleWrite 0; - -writeFormat ascii; - -writeCompression compressed; - -timeFormat general; - -timePrecision 6; - -runTimeModifiable yes; - -nCorrectors 2; - -nNonOrthogonalCorrectors 0; - - -// ************************************************************************* // diff --git a/tutorials/cutCubeOctree/system/meshDict b/tutorials/cutCubeOctree/system/meshDict deleted file mode 100755 index b5a561361de15ee6e64e33f20e73b0b96fef0b42..0000000000000000000000000000000000000000 --- a/tutorials/cutCubeOctree/system/meshDict +++ /dev/null @@ -1,48 +0,0 @@ -// The FOAM Project // File: adaptiveProperties -/* -------------------------------------------------------------------------------- - ========= | dictionary - \\ / | - \\ / | Name: adaptiveProperties - \\ / | Family: Data file - \\/ | - F ield | FOAM version: 1.9.6 - O peration | Product of Nabla Ltd. - A and | - M anipulation | Email: Enquiries@Nabla.co.uk -------------------------------------------------------------------------------- -*/ - -version 0.5; -format ascii; - -root "/home/larson/franjo/foam/run"; -case "thetaTest"; -instance "system"; -local ""; - -note "fvSchemes for Foam"; - -class dictionary; -object adaptiveProperties; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -surfaceFile "geom1.stl"; - -maxCellSize 0.2; - -boundaryCellSize 0.1; - -minCellSize 0.1; - -patchCellSize -2 -( -patch0000 0.05 -patch0007 0.05 -); - -internalVertex (0.05 0.05 0.05); - -// ************************************************************************* // diff --git a/tutorials/intakePortOctree/system/controlDict b/tutorials/intakePortOctree/system/controlDict deleted file mode 100755 index 4de2815d76b74597ec74f10129e1c1fdc179673a..0000000000000000000000000000000000000000 --- a/tutorials/intakePortOctree/system/controlDict +++ /dev/null @@ -1,49 +0,0 @@ -// ************************************************************************* // -// FoamX Case Dictionary. - -version 1.0; -format ascii; -root "/home/franjo/foam/franjo2.0/run"; -case "jetAdaptive"; -instance "system"; -local ""; -class dictionary; -form dictionary; -object controlDict; - -// ************************************************************************* // - -applicationClass icoFoam; - -startFrom latestTime; - -startTime 0; - -stopAt endTime; - -endTime 500; - -deltaT 1; - -writeControl timeStep; - -writeInterval 100; - -cycleWrite 0; - -writeFormat ascii; - -writeCompression uncompressed; - -timeFormat general; - -timePrecision 6; - -runTimeModifiable yes; - -nCorrectors 2; - -nNonOrthogonalCorrectors 0; - - -// ************************************************************************* // diff --git a/tutorials/intakePortOctree/system/meshDict b/tutorials/intakePortOctree/system/meshDict deleted file mode 100755 index b54a67d8c522e72a8646006e10cf445032597fb8..0000000000000000000000000000000000000000 --- a/tutorials/intakePortOctree/system/meshDict +++ /dev/null @@ -1,54 +0,0 @@ -// The FOAM Project // File: adaptiveProperties -/* -------------------------------------------------------------------------------- - ========= | dictionary - \\ / | - \\ / | Name: adaptiveProperties - \\ / | Family: Data file - \\/ | - F ield | FOAM version: 1.9.6 - O peration | Product of Nabla Ltd. - A and | - M anipulation | Email: Enquiries@Nabla.co.uk -------------------------------------------------------------------------------- -*/ - -version 0.5; -format ascii; - -root "/home/larson/franjo/foam/run"; -case "thetaTest"; -instance "system"; -local ""; - -note "fvSchemes for Foam"; - -class dictionary; -object adaptiveProperties; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -surfaceFile "geom2.stl"; - -maxCellSize 10; - -boundaryCellSize 1.25; - -minCellSize 2.0; - -internalVertex (20.0 -155.0 54); - -patchCellSize -8 -( - patch001 0.625 - patch002 0.625 - patch003 0.625 - patch004 0.625 - patch005 0.625 - patch006 0.625 - patch007 0.625 - patch008 0.625 -); - -// ************************************************************************* // diff --git a/tutorials/sBendOctree/geom.stl b/tutorials/sBendOctree/geom.stl deleted file mode 100644 index 5541405736b9344fa30ef530a93a1e86f1f96853..0000000000000000000000000000000000000000 --- a/tutorials/sBendOctree/geom.stl +++ /dev/null @@ -1,11912 +0,0 @@ -solid inlet - facet normal -1 0 0 - outer loop - vertex -2 1.39469 -0.128242 - vertex -2 1.415 -3.91402e-17 - vertex -2 1.5 -4.9133e-17 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.415 -3.91402e-17 - vertex -2 1.39469 -0.128242 - vertex -2 1.31385 -0.101976 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.5 -4.9133e-17 - vertex -2 1.47553 -0.154509 - vertex -2 1.39469 -0.128242 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.31385 -0.101976 - vertex -2 1.33 -2.91474e-17 - vertex -2 1.415 -3.91402e-17 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.26698 -0.193969 - vertex -2 1.31385 -0.101976 - vertex -2 1.39469 -0.128242 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.39469 -0.128242 - vertex -2 1.47553 -0.154509 - vertex -2 1.40451 -0.293893 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.33 -2.91474e-17 - vertex -2 1.31385 -0.101976 - vertex -2 1.23301 -0.0757092 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.23301 -0.0757092 - vertex -2 1.31385 -0.101976 - vertex -2 1.26698 -0.193969 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.39469 -0.128242 - vertex -2 1.33574 -0.243931 - vertex -2 1.26698 -0.193969 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.40451 -0.293893 - vertex -2 1.33574 -0.243931 - vertex -2 1.39469 -0.128242 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.23301 -0.0757092 - vertex -2 1.245 -1.91546e-17 - vertex -2 1.33 -2.91474e-17 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.26698 -0.193969 - vertex -2 1.19821 -0.144007 - vertex -2 1.23301 -0.0757092 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.19397 -0.266976 - vertex -2 1.26698 -0.193969 - vertex -2 1.33574 -0.243931 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.24393 -0.335742 - vertex -2 1.33574 -0.243931 - vertex -2 1.40451 -0.293893 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.245 -1.91546e-17 - vertex -2 1.23301 -0.0757092 - vertex -2 1.15217 -0.0494427 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.14401 -0.198209 - vertex -2 1.19821 -0.144007 - vertex -2 1.26698 -0.193969 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.15217 -0.0494427 - vertex -2 1.23301 -0.0757092 - vertex -2 1.19821 -0.144007 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.26698 -0.193969 - vertex -2 1.19397 -0.266976 - vertex -2 1.14401 -0.198209 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.33574 -0.243931 - vertex -2 1.24393 -0.335742 - vertex -2 1.19397 -0.266976 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.40451 -0.293893 - vertex -2 1.29389 -0.404509 - vertex -2 1.24393 -0.335742 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.15217 -0.0494427 - vertex -2 1.16 -9.16178e-18 - vertex -2 1.245 -1.91546e-17 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 1.19821 -0.144007 - vertex -2 1.14401 -0.198209 - vertex -2 1.09405 -0.129443 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.19821 -0.144007 - vertex -2 1.12944 -0.0940456 - vertex -2 1.15217 -0.0494427 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1.14401 -0.198209 - vertex -2 1.19397 -0.266976 - vertex -2 1.10198 -0.313849 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.10198 -0.313849 - vertex -2 1.19397 -0.266976 - vertex -2 1.24393 -0.335742 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1.24393 -0.335742 - vertex -2 1.29389 -0.404509 - vertex -2 1.15451 -0.475528 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.16 -9.16178e-18 - vertex -2 1.15217 -0.0494427 - vertex -2 1.07133 -0.0231763 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.09405 -0.129443 - vertex -2 1.12944 -0.0940456 - vertex -2 1.19821 -0.144007 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1.09405 -0.129443 - vertex -2 1.14401 -0.198209 - vertex -2 1.07571 -0.233009 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 1.15217 -0.0494427 - vertex -2 1.12944 -0.0940456 - vertex -2 1.06068 -0.0440838 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.10198 -0.313849 - vertex -2 1.07571 -0.233009 - vertex -2 1.14401 -0.198209 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 1.24393 -0.335742 - vertex -2 1.12824 -0.394688 - vertex -2 1.10198 -0.313849 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.15451 -0.475528 - vertex -2 1.12824 -0.394688 - vertex -2 1.24393 -0.335742 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.07133 -0.0231763 - vertex -2 1.075 8.31019e-19 - vertex -2 1.16 -9.16178e-18 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.06068 -0.0440838 - vertex -2 1.07133 -0.0231763 - vertex -2 1.15217 -0.0494427 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.06068 -0.0440838 - vertex -2 1.12944 -0.0940456 - vertex -2 1.09405 -0.129443 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.07571 -0.233009 - vertex -2 1.04944 -0.152169 - vertex -2 1.09405 -0.129443 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1.07571 -0.233009 - vertex -2 1.10198 -0.313849 - vertex -2 1 -0.33 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1 -0.33 - vertex -2 1.10198 -0.313849 - vertex -2 1.12824 -0.394688 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1.12824 -0.394688 - vertex -2 1.15451 -0.475528 - vertex -2 1 -0.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.09405 -0.129443 - vertex -2 1.04408 -0.0606762 - vertex -2 1.06068 -0.0440838 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1.04944 -0.152169 - vertex -2 1.07571 -0.233009 - vertex -2 1 -0.245 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 1.09405 -0.129443 - vertex -2 1.04944 -0.152169 - vertex -2 1.02318 -0.0713292 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1 -0.33 - vertex -2 1 -0.245 - vertex -2 1.07571 -0.233009 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 1.12824 -0.394688 - vertex -2 1 -0.415 - vertex -2 1 -0.33 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1 -0.5 - vertex -2 1 -0.415 - vertex -2 1.12824 -0.394688 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1.02318 -0.0713292 - vertex -2 1.04408 -0.0606762 - vertex -2 1.09405 -0.129443 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1 -0.245 - vertex -2 1 -0.16 - vertex -2 1.04944 -0.152169 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1 -0.075 - vertex -2 1.02318 -0.0713292 - vertex -2 1.04944 -0.152169 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.924291 -0.233009 - vertex -2 1 -0.245 - vertex -2 1 -0.33 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.898024 -0.313849 - vertex -2 1 -0.33 - vertex -2 1 -0.415 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1 -0.415 - vertex -2 1 -0.5 - vertex -2 0.845491 -0.475528 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1 -0.16 - vertex -2 1 -0.245 - vertex -2 0.924291 -0.233009 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 1.04944 -0.152169 - vertex -2 1 -0.16 - vertex -2 1 -0.075 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1 -0.33 - vertex -2 0.898024 -0.313849 - vertex -2 0.924291 -0.233009 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 1 -0.415 - vertex -2 0.871758 -0.394688 - vertex -2 0.898024 -0.313849 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.845491 -0.475528 - vertex -2 0.871758 -0.394688 - vertex -2 1 -0.415 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.924291 -0.233009 - vertex -2 0.950557 -0.152169 - vertex -2 1 -0.16 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 1 -0.075 - vertex -2 1 -0.16 - vertex -2 0.950557 -0.152169 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.924291 -0.233009 - vertex -2 0.898024 -0.313849 - vertex -2 0.806031 -0.266976 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.898024 -0.313849 - vertex -2 0.871758 -0.394688 - vertex -2 0.756069 -0.335742 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.756069 -0.335742 - vertex -2 0.871758 -0.394688 - vertex -2 0.845491 -0.475528 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.905954 -0.129443 - vertex -2 0.950557 -0.152169 - vertex -2 0.924291 -0.233009 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.950557 -0.152169 - vertex -2 0.976824 -0.0713292 - vertex -2 1 -0.075 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.756069 -0.335742 - vertex -2 0.806031 -0.266976 - vertex -2 0.898024 -0.313849 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.806031 -0.266976 - vertex -2 0.855993 -0.198209 - vertex -2 0.924291 -0.233009 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.845491 -0.475528 - vertex -2 0.706107 -0.404509 - vertex -2 0.756069 -0.335742 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.950557 -0.152169 - vertex -2 0.905954 -0.129443 - vertex -2 0.955916 -0.0606763 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.924291 -0.233009 - vertex -2 0.855993 -0.198209 - vertex -2 0.905954 -0.129443 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 0.955916 -0.0606763 - vertex -2 0.976824 -0.0713292 - vertex -2 0.950557 -0.152169 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.733024 -0.193969 - vertex -2 0.806031 -0.266976 - vertex -2 0.756069 -0.335742 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 0.855993 -0.198209 - vertex -2 0.806031 -0.266976 - vertex -2 0.733024 -0.193969 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 0.756069 -0.335742 - vertex -2 0.706107 -0.404509 - vertex -2 0.595491 -0.293893 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.955916 -0.0606763 - vertex -2 0.905954 -0.129443 - vertex -2 0.870557 -0.0940456 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.905954 -0.129443 - vertex -2 0.855993 -0.198209 - vertex -2 0.801791 -0.144007 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.756069 -0.335742 - vertex -2 0.664258 -0.243931 - vertex -2 0.733024 -0.193969 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.733024 -0.193969 - vertex -2 0.801791 -0.144007 - vertex -2 0.855993 -0.198209 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.595491 -0.293893 - vertex -2 0.664258 -0.243931 - vertex -2 0.756069 -0.335742 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.801791 -0.144007 - vertex -2 0.870557 -0.0940456 - vertex -2 0.905954 -0.129443 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.870557 -0.0940456 - vertex -2 0.939324 -0.0440839 - vertex -2 0.955916 -0.0606763 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 0.686151 -0.101976 - vertex -2 0.733024 -0.193969 - vertex -2 0.664258 -0.243931 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 0.766991 -0.0757092 - vertex -2 0.801791 -0.144007 - vertex -2 0.733024 -0.193969 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 0.664258 -0.243931 - vertex -2 0.595491 -0.293893 - vertex -2 0.524472 -0.154509 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 0.870557 -0.0940456 - vertex -2 0.801791 -0.144007 - vertex -2 0.766991 -0.0757092 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 0.928671 -0.0231763 - vertex -2 0.939324 -0.0440839 - vertex -2 0.870557 -0.0940456 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.733024 -0.193969 - vertex -2 0.686151 -0.101976 - vertex -2 0.766991 -0.0757092 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.664258 -0.243931 - vertex -2 0.605312 -0.128242 - vertex -2 0.686151 -0.101976 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.524472 -0.154509 - vertex -2 0.605312 -0.128242 - vertex -2 0.664258 -0.243931 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.766991 -0.0757092 - vertex -2 0.847831 -0.0494427 - vertex -2 0.870557 -0.0940456 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.870557 -0.0940456 - vertex -2 0.847831 -0.0494427 - vertex -2 0.928671 -0.0231763 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 0.766991 -0.0757092 - vertex -2 0.686151 -0.101976 - vertex -2 0.67 -3.3749e-23 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -2 0.686151 -0.101976 - vertex -2 0.605312 -0.128242 - vertex -2 0.585 -4.33443e-23 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 0.585 -4.33443e-23 - vertex -2 0.605312 -0.128242 - vertex -2 0.524472 -0.154509 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 0.84 -1.45584e-23 - vertex -2 0.847831 -0.0494427 - vertex -2 0.766991 -0.0757092 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -2 0.925 -4.96308e-24 - vertex -2 0.928671 -0.0231763 - vertex -2 0.847831 -0.0494427 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.585 -4.33443e-23 - vertex -2 0.67 -3.3749e-23 - vertex -2 0.686151 -0.101976 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.67 -3.3749e-23 - vertex -2 0.755 -2.41537e-23 - vertex -2 0.766991 -0.0757092 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.524472 -0.154509 - vertex -2 0.5 -5.29396e-23 - vertex -2 0.585 -4.33443e-23 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.847831 -0.0494427 - vertex -2 0.84 -1.45584e-23 - vertex -2 0.925 -4.96308e-24 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -2 0.766991 -0.0757092 - vertex -2 0.755 -2.41537e-23 - vertex -2 0.84 -1.45584e-23 - endloop - endfacet -endsolid inlet -solid outlet - facet normal 1 0 0 - outer loop - vertex 6 -0.585 4.32569e-18 - vertex 6 -0.605312 -0.128242 - vertex 6 -0.524472 -0.154509 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -0.686151 -0.101976 - vertex 6 -0.605312 -0.128242 - vertex 6 -0.585 4.32569e-18 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.524472 -0.154509 - vertex 6 -0.605312 -0.128242 - vertex 6 -0.664258 -0.243931 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -0.524472 -0.154509 - vertex 6 -0.5 6.21687e-18 - vertex 6 -0.585 4.32569e-18 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -0.664258 -0.243931 - vertex 6 -0.605312 -0.128242 - vertex 6 -0.686151 -0.101976 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.585 4.32569e-18 - vertex 6 -0.67 2.43451e-18 - vertex 6 -0.686151 -0.101976 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -0.664258 -0.243931 - vertex 6 -0.595491 -0.293893 - vertex 6 -0.524472 -0.154509 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.686151 -0.101976 - vertex 6 -0.733024 -0.193969 - vertex 6 -0.664258 -0.243931 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -0.766991 -0.0757092 - vertex 6 -0.686151 -0.101976 - vertex 6 -0.67 2.43451e-18 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.595491 -0.293893 - vertex 6 -0.664258 -0.243931 - vertex 6 -0.756069 -0.335742 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -0.733024 -0.193969 - vertex 6 -0.686151 -0.101976 - vertex 6 -0.766991 -0.0757092 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.756069 -0.335742 - vertex 6 -0.664258 -0.243931 - vertex 6 -0.733024 -0.193969 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.67 2.43451e-18 - vertex 6 -0.755 5.43323e-19 - vertex 6 -0.766991 -0.0757092 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -0.756069 -0.335742 - vertex 6 -0.706107 -0.404509 - vertex 6 -0.595491 -0.293893 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.766991 -0.0757092 - vertex 6 -0.801791 -0.144007 - vertex 6 -0.733024 -0.193969 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.733024 -0.193969 - vertex 6 -0.806031 -0.266976 - vertex 6 -0.756069 -0.335742 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -0.766991 -0.0757092 - vertex 6 -0.755 5.43323e-19 - vertex 6 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.845491 -0.475528 - vertex 6 -0.706107 -0.404509 - vertex 6 -0.756069 -0.335742 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -0.870557 -0.0940456 - vertex 6 -0.801791 -0.144007 - vertex 6 -0.766991 -0.0757092 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.733024 -0.193969 - vertex 6 -0.801791 -0.144007 - vertex 6 -0.855993 -0.198209 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -0.855993 -0.198209 - vertex 6 -0.806031 -0.266976 - vertex 6 -0.733024 -0.193969 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.756069 -0.335742 - vertex 6 -0.806031 -0.266976 - vertex 6 -0.898024 -0.313849 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.84 -1.34786e-18 - vertex 6 -0.847831 -0.0494427 - vertex 6 -0.766991 -0.0757092 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.756069 -0.335742 - vertex 6 -0.871758 -0.394688 - vertex 6 -0.845491 -0.475528 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.801791 -0.144007 - vertex 6 -0.870557 -0.0940456 - vertex 6 -0.905954 -0.129443 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.766991 -0.0757092 - vertex 6 -0.847831 -0.0494427 - vertex 6 -0.870557 -0.0940456 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.905954 -0.129443 - vertex 6 -0.855993 -0.198209 - vertex 6 -0.801791 -0.144007 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.806031 -0.266976 - vertex 6 -0.855993 -0.198209 - vertex 6 -0.924291 -0.233009 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.898024 -0.313849 - vertex 6 -0.871758 -0.394688 - vertex 6 -0.756069 -0.335742 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.924291 -0.233009 - vertex 6 -0.898024 -0.313849 - vertex 6 -0.806031 -0.266976 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -0.847831 -0.0494427 - vertex 6 -0.84 -1.34786e-18 - vertex 6 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.845491 -0.475528 - vertex 6 -0.871758 -0.394688 - vertex 6 -1 -0.415 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.955916 -0.0606763 - vertex 6 -0.905954 -0.129443 - vertex 6 -0.870557 -0.0940456 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -0.870557 -0.0940456 - vertex 6 -0.847831 -0.0494427 - vertex 6 -0.928671 -0.0231763 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.924291 -0.233009 - vertex 6 -0.855993 -0.198209 - vertex 6 -0.905954 -0.129443 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1 -0.415 - vertex 6 -0.871758 -0.394688 - vertex 6 -0.898024 -0.313849 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1 -0.33 - vertex 6 -0.898024 -0.313849 - vertex 6 -0.924291 -0.233009 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.925 -3.23904e-18 - vertex 6 -0.928671 -0.0231763 - vertex 6 -0.847831 -0.0494427 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1 -0.415 - vertex 6 -1 -0.5 - vertex 6 -0.845491 -0.475528 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -0.950557 -0.152169 - vertex 6 -0.905954 -0.129443 - vertex 6 -0.955916 -0.0606763 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.870557 -0.0940456 - vertex 6 -0.939324 -0.0440839 - vertex 6 -0.955916 -0.0606763 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.928671 -0.0231763 - vertex 6 -0.939324 -0.0440839 - vertex 6 -0.870557 -0.0940456 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.905954 -0.129443 - vertex 6 -0.950557 -0.152169 - vertex 6 -0.924291 -0.233009 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.898024 -0.313849 - vertex 6 -1 -0.33 - vertex 6 -1 -0.415 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.924291 -0.233009 - vertex 6 -1 -0.245 - vertex 6 -1 -0.33 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -1 -0.5 - vertex 6 -1 -0.415 - vertex 6 -1.12824 -0.394689 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.955916 -0.0606763 - vertex 6 -0.976824 -0.0713292 - vertex 6 -0.950557 -0.152169 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.924291 -0.233009 - vertex 6 -0.950557 -0.152169 - vertex 6 -1 -0.16 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -1.12824 -0.394689 - vertex 6 -1 -0.415 - vertex 6 -1 -0.33 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1 -0.16 - vertex 6 -1 -0.245 - vertex 6 -0.924291 -0.233009 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -1 -0.33 - vertex 6 -1 -0.245 - vertex 6 -1.07571 -0.233009 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.12824 -0.394689 - vertex 6 -1.15451 -0.475528 - vertex 6 -1 -0.5 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -0.950557 -0.152169 - vertex 6 -0.976824 -0.0713292 - vertex 6 -1 -0.075 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1 -0.075 - vertex 6 -1 -0.16 - vertex 6 -0.950557 -0.152169 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1 -0.33 - vertex 6 -1.10198 -0.313849 - vertex 6 -1.12824 -0.394689 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -1 -0.245 - vertex 6 -1 -0.16 - vertex 6 -1.04944 -0.152169 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.07571 -0.233009 - vertex 6 -1.10198 -0.313849 - vertex 6 -1 -0.33 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.04944 -0.152169 - vertex 6 -1.07571 -0.233009 - vertex 6 -1 -0.245 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -1.15451 -0.475528 - vertex 6 -1.12824 -0.394689 - vertex 6 -1.24393 -0.335742 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -1.04944 -0.152169 - vertex 6 -1 -0.16 - vertex 6 -1 -0.075 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -1.24393 -0.335742 - vertex 6 -1.12824 -0.394689 - vertex 6 -1.10198 -0.313849 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -1.10198 -0.313849 - vertex 6 -1.07571 -0.233009 - vertex 6 -1.14401 -0.198209 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 6 -1.07571 -0.233009 - vertex 6 -1.04944 -0.152169 - vertex 6 -1.09405 -0.129443 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.24393 -0.335742 - vertex 6 -1.29389 -0.404509 - vertex 6 -1.15451 -0.475528 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1 -0.075 - vertex 6 -1.02318 -0.0713293 - vertex 6 -1.04944 -0.152169 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.10198 -0.313849 - vertex 6 -1.19397 -0.266976 - vertex 6 -1.24393 -0.335742 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.14401 -0.198209 - vertex 6 -1.19397 -0.266976 - vertex 6 -1.10198 -0.313849 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.09405 -0.129443 - vertex 6 -1.14401 -0.198209 - vertex 6 -1.07571 -0.233009 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -1.09405 -0.129443 - vertex 6 -1.04944 -0.152169 - vertex 6 -1.02318 -0.0713293 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.40451 -0.293893 - vertex 6 -1.29389 -0.404509 - vertex 6 -1.24393 -0.335742 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.33574 -0.243931 - vertex 6 -1.24393 -0.335742 - vertex 6 -1.19397 -0.266976 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.26698 -0.193969 - vertex 6 -1.19397 -0.266976 - vertex 6 -1.14401 -0.198209 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -1.19821 -0.144007 - vertex 6 -1.14401 -0.198209 - vertex 6 -1.09405 -0.129443 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.02318 -0.0713293 - vertex 6 -1.04408 -0.0606763 - vertex 6 -1.09405 -0.129443 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.24393 -0.335742 - vertex 6 -1.33574 -0.243931 - vertex 6 -1.40451 -0.293893 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.19397 -0.266976 - vertex 6 -1.26698 -0.193969 - vertex 6 -1.33574 -0.243931 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.14401 -0.198209 - vertex 6 -1.19821 -0.144007 - vertex 6 -1.26698 -0.193969 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.09405 -0.129443 - vertex 6 -1.12944 -0.0940457 - vertex 6 -1.19821 -0.144007 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.09405 -0.129443 - vertex 6 -1.04408 -0.0606763 - vertex 6 -1.06068 -0.0440839 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.40451 -0.293893 - vertex 6 -1.33574 -0.243931 - vertex 6 -1.39469 -0.128242 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.39469 -0.128242 - vertex 6 -1.33574 -0.243931 - vertex 6 -1.26698 -0.193969 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.26698 -0.193969 - vertex 6 -1.19821 -0.144007 - vertex 6 -1.23301 -0.0757092 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.19821 -0.144007 - vertex 6 -1.12944 -0.0940457 - vertex 6 -1.15217 -0.0494427 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.06068 -0.0440839 - vertex 6 -1.12944 -0.0940457 - vertex 6 -1.09405 -0.129443 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.39469 -0.128242 - vertex 6 -1.47553 -0.154509 - vertex 6 -1.40451 -0.293893 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.26698 -0.193969 - vertex 6 -1.31385 -0.101976 - vertex 6 -1.39469 -0.128242 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.23301 -0.0757092 - vertex 6 -1.31385 -0.101976 - vertex 6 -1.26698 -0.193969 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.15217 -0.0494427 - vertex 6 -1.23301 -0.0757092 - vertex 6 -1.19821 -0.144007 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 6 -1.15217 -0.0494427 - vertex 6 -1.12944 -0.0940457 - vertex 6 -1.06068 -0.0440839 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.5 1.05879e-22 - vertex 6 -1.47553 -0.154509 - vertex 6 -1.39469 -0.128242 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.415 1.11173e-22 - vertex 6 -1.39469 -0.128242 - vertex 6 -1.31385 -0.101976 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.33 1.16467e-22 - vertex 6 -1.31385 -0.101976 - vertex 6 -1.23301 -0.0757092 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.245 1.21761e-22 - vertex 6 -1.23301 -0.0757092 - vertex 6 -1.15217 -0.0494427 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.06068 -0.0440839 - vertex 6 -1.07133 -0.0231763 - vertex 6 -1.15217 -0.0494427 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.39469 -0.128242 - vertex 6 -1.415 1.11173e-22 - vertex 6 -1.5 1.05879e-22 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.31385 -0.101976 - vertex 6 -1.33 1.16467e-22 - vertex 6 -1.415 1.11173e-22 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.23301 -0.0757092 - vertex 6 -1.245 1.21761e-22 - vertex 6 -1.33 1.16467e-22 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.15217 -0.0494427 - vertex 6 -1.16 1.27055e-22 - vertex 6 -1.245 1.21761e-22 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.16 1.27055e-22 - vertex 6 -1.15217 -0.0494427 - vertex 6 -1.07133 -0.0231763 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 6 -1.07133 -0.0231763 - vertex 6 -1.075 1.32349e-22 - vertex 6 -1.16 1.27055e-22 - endloop - endfacet -endsolid outlet -solid symm - facet normal 0 -1.12886e-22 1 - outer loop - vertex -2 0.5 -5.29396e-23 - vertex -1.6 0.5 -5.29396e-23 - vertex -1.6 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.585 -4.33443e-23 - vertex -1.6 0.585 -4.33443e-23 - vertex -1.6 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.585 -4.33443e-23 - vertex -2 0.585 -4.33443e-23 - vertex -2 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.5 -5.29396e-23 - vertex -1.2 0.5 -5.29396e-23 - vertex -1.2 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.585 -4.33443e-23 - vertex -1.2 0.585 -4.33443e-23 - vertex -1.2 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -2 0.585 -4.33443e-23 - vertex -1.6 0.585 -4.33443e-23 - vertex -1.6 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.585 -4.33443e-23 - vertex -1.2 0.585 -4.33443e-23 - vertex -1.2 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.67 -3.3749e-23 - vertex -1.2 0.67 -3.3749e-23 - vertex -1.2 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.67 -3.3749e-23 - vertex -1.6 0.67 -3.3749e-23 - vertex -1.6 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.67 -3.3749e-23 - vertex -2 0.67 -3.3749e-23 - vertex -2 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.5 -5.29396e-23 - vertex -0.8 0.5 -5.29396e-23 - vertex -0.8 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.585 -4.33443e-23 - vertex -0.8 0.585 -4.33443e-23 - vertex -0.8 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.67 -3.3749e-23 - vertex -0.8 0.67 -3.3749e-23 - vertex -0.8 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.67 -3.3749e-23 - vertex -1.2 0.67 -3.3749e-23 - vertex -1.2 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -2 0.67 -3.3749e-23 - vertex -1.6 0.67 -3.3749e-23 - vertex -1.6 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.585 -4.33443e-23 - vertex -0.8 0.585 -4.33443e-23 - vertex -0.8 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.67 -3.3749e-23 - vertex -0.8 0.67 -3.3749e-23 - vertex -0.8 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.755 -2.41537e-23 - vertex -0.8 0.755 -2.41537e-23 - vertex -0.8 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.755 -2.41537e-23 - vertex -1.2 0.755 -2.41537e-23 - vertex -1.2 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.755 -2.41537e-23 - vertex -1.6 0.755 -2.41537e-23 - vertex -1.6 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.755 -2.41537e-23 - vertex -2 0.755 -2.41537e-23 - vertex -2 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.5 -5.29396e-23 - vertex -0.4 0.5 -5.29396e-23 - vertex -0.4 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.585 -4.33443e-23 - vertex -0.4 0.585 -4.33443e-23 - vertex -0.4 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.67 -3.3749e-23 - vertex -0.4 0.67 -3.3749e-23 - vertex -0.4 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.755 -2.41537e-23 - vertex -0.4 0.755 -2.41537e-23 - vertex -0.4 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.755 -2.41537e-23 - vertex -0.8 0.755 -2.41537e-23 - vertex -0.8 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.755 -2.41537e-23 - vertex -1.2 0.755 -2.41537e-23 - vertex -1.2 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -2 0.755 -2.41537e-23 - vertex -1.6 0.755 -2.41537e-23 - vertex -1.6 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex 2.38228e-23 0.585 -4.33443e-23 - vertex -0.4 0.585 -4.33443e-23 - vertex -0.4 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex 2.11758e-23 0.67 -3.3749e-23 - vertex -0.4 0.67 -3.3749e-23 - vertex -0.4 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex 1.85288e-23 0.755 -2.41537e-23 - vertex -0.4 0.755 -2.41537e-23 - vertex -0.4 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex 1.58819e-23 0.84 -1.45584e-23 - vertex -0.4 0.84 -1.45584e-23 - vertex -0.4 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.84 -1.45584e-23 - vertex -0.8 0.84 -1.45584e-23 - vertex -0.8 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.84 -1.45584e-23 - vertex -1.2 0.84 -1.45584e-23 - vertex -1.2 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.84 -1.45584e-23 - vertex -1.6 0.84 -1.45584e-23 - vertex -1.6 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.84 -1.45584e-23 - vertex -2 0.84 -1.45584e-23 - vertex -2 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.5 -5.29396e-23 - vertex 2.64698e-23 0.5 -5.29396e-23 - vertex 2.38228e-23 0.585 -4.33443e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.585 -4.33443e-23 - vertex 2.38228e-23 0.585 -4.33443e-23 - vertex 2.11758e-23 0.67 -3.3749e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.67 -3.3749e-23 - vertex 2.11758e-23 0.67 -3.3749e-23 - vertex 1.85288e-23 0.755 -2.41537e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.755 -2.41537e-23 - vertex 1.85288e-23 0.755 -2.41537e-23 - vertex 1.58819e-23 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.84 -1.45584e-23 - vertex 1.58819e-23 0.84 -1.45584e-23 - vertex 1.32349e-23 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.84 -1.45584e-23 - vertex -0.4 0.84 -1.45584e-23 - vertex -0.4 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.84 -1.45584e-23 - vertex -0.8 0.84 -1.45584e-23 - vertex -0.8 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.84 -1.45584e-23 - vertex -1.2 0.84 -1.45584e-23 - vertex -1.2 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -2 0.84 -1.45584e-23 - vertex -1.6 0.84 -1.45584e-23 - vertex -1.6 0.925 -4.96308e-24 - endloop - endfacet - facet normal -6.94938e-23 -1.12886e-22 1 - outer loop - vertex 0.180775 0.556368 -3.40137e-23 - vertex 2.38228e-23 0.585 -4.33443e-23 - vertex 2.64698e-23 0.5 -5.29396e-23 - endloop - endfacet - facet normal -5.04806e-23 -1.12886e-22 1 - outer loop - vertex 0.207041 0.637208 -2.69992e-23 - vertex 2.11758e-23 0.67 -3.3749e-23 - vertex 2.38228e-23 0.585 -4.33443e-23 - endloop - endfacet - facet normal -5.04806e-23 -1.12886e-22 1 - outer loop - vertex 1.85288e-23 0.755 -2.41537e-23 - vertex 2.11758e-23 0.67 -3.3749e-23 - vertex 0.207041 0.637208 -2.69992e-23 - endloop - endfacet - facet normal -2.39976e-23 -1.12886e-22 1 - outer loop - vertex 0.259574 0.798888 -1.29702e-23 - vertex 1.58819e-23 0.84 -1.45584e-23 - vertex 1.85288e-23 0.755 -2.41537e-23 - endloop - endfacet - facet normal -2.39976e-23 -1.12886e-22 1 - outer loop - vertex 1.32349e-23 0.925 -4.96308e-24 - vertex 1.58819e-23 0.84 -1.45584e-23 - vertex 0.259574 0.798888 -1.29702e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex 1.32349e-23 0.925 -4.96308e-24 - vertex -0.4 0.925 -4.96308e-24 - vertex -0.4 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.4 0.925 -4.96308e-24 - vertex -0.8 0.925 -4.96308e-24 - vertex -0.8 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -0.8 0.925 -4.96308e-24 - vertex -1.2 0.925 -4.96308e-24 - vertex -1.2 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.2 0.925 -4.96308e-24 - vertex -1.6 0.925 -4.96308e-24 - vertex -1.6 0.84 -1.45584e-23 - endloop - endfacet - facet normal 0 -1.12886e-22 1 - outer loop - vertex -1.6 0.925 -4.96308e-24 - vertex -2 0.925 -4.96308e-24 - vertex -2 0.84 -1.45584e-23 - endloop - endfacet - facet normal -8.63893e-23 -5.87011e-23 1 - outer loop - vertex 2.64698e-23 0.5 -5.29396e-23 - vertex 0.154509 0.475528 -4.10282e-23 - vertex 0.180775 0.556368 -3.40137e-23 - endloop - endfacet - facet normal -6.21587e-23 -6.6574e-23 1 - outer loop - vertex 2.38228e-23 0.585 -4.33443e-23 - vertex 0.180775 0.556368 -3.40137e-23 - vertex 0.207041 0.637208 -2.69992e-23 - endloop - endfacet - facet normal -3.00648e-23 -7.70014e-23 1 - outer loop - vertex 0.207041 0.637208 -2.69992e-23 - vertex 0.233308 0.718048 -1.99847e-23 - vertex 1.85288e-23 0.755 -2.41537e-23 - endloop - endfacet - facet normal -3.00648e-23 -7.70016e-23 1 - outer loop - vertex 1.85288e-23 0.755 -2.41537e-23 - vertex 0.233308 0.718048 -1.99847e-23 - vertex 0.259574 0.798888 -1.29702e-23 - endloop - endfacet - facet normal -9.76796e-24 -8.35974e-23 1 - outer loop - vertex 0.259574 0.798888 -1.29702e-23 - vertex 0.285841 0.879727 -5.9557e-24 - vertex 1.32349e-23 0.925 -4.96308e-24 - endloop - endfacet - facet normal -8.70205e-23 -5.8496e-23 1 - outer loop - vertex 0.343854 0.473275 -2.46831e-23 - vertex 0.180775 0.556368 -3.40137e-23 - vertex 0.154509 0.475528 -4.10282e-23 - endloop - endfacet - facet normal -6.89377e-23 -6.43714e-23 1 - outer loop - vertex 0.393816 0.542041 -2.02494e-23 - vertex 0.207041 0.637208 -2.69992e-23 - vertex 0.180775 0.556368 -3.40137e-23 - endloop - endfacet - facet normal -6.89373e-23 -6.43707e-23 1 - outer loop - vertex 0.233308 0.718048 -1.99847e-23 - vertex 0.207041 0.637208 -2.69992e-23 - vertex 0.393816 0.542041 -2.02494e-23 - endloop - endfacet - facet normal -4.3751e-23 -7.25548e-23 1 - outer loop - vertex 0.49374 0.679574 -1.1382e-23 - vertex 0.259574 0.798888 -1.29702e-23 - vertex 0.233308 0.718048 -1.99847e-23 - endloop - endfacet - facet normal -3.46294e-23 -7.55191e-23 1 - outer loop - vertex 0.543701 0.748341 -6.94832e-24 - vertex 0.285841 0.879727 -5.9557e-24 - vertex 0.259574 0.798888 -1.29702e-23 - endloop - endfacet - facet normal -8.63452e-23 -1.74227e-24 1 - outer loop - vertex 0.154509 0.475528 -4.10282e-23 - vertex 0.293893 0.404509 -2.91168e-23 - vertex 0.343854 0.473275 -2.46831e-23 - endloop - endfacet - facet normal -6.57329e-23 -1.67169e-23 1 - outer loop - vertex 0.180775 0.556368 -3.40137e-23 - vertex 0.343854 0.473275 -2.46831e-23 - vertex 0.393816 0.542041 -2.02494e-23 - endloop - endfacet - facet normal -3.84321e-23 -3.65517e-23 1 - outer loop - vertex 0.393816 0.542041 -2.02494e-23 - vertex 0.443778 0.610808 -1.58157e-23 - vertex 0.233308 0.718048 -1.99847e-23 - endloop - endfacet - facet normal -3.84323e-23 -3.65522e-23 1 - outer loop - vertex 0.233308 0.718048 -1.99847e-23 - vertex 0.443778 0.610808 -1.58157e-23 - vertex 0.49374 0.679574 -1.1382e-23 - endloop - endfacet - facet normal -2.89257e-23 -4.34586e-23 1 - outer loop - vertex 0.259574 0.798888 -1.29702e-23 - vertex 0.49374 0.679574 -1.1382e-23 - vertex 0.543701 0.748341 -6.94832e-24 - endloop - endfacet - facet normal -7.91006e-23 -7.00569e-24 1 - outer loop - vertex 0.473275 0.343854 -1.53525e-23 - vertex 0.343854 0.473275 -2.46831e-23 - vertex 0.293893 0.404509 -2.91168e-23 - endloop - endfacet - facet normal -6.37182e-23 -1.81807e-23 1 - outer loop - vertex 0.542041 0.393816 -1.34996e-23 - vertex 0.393816 0.542041 -2.02494e-23 - vertex 0.343854 0.473275 -2.46831e-23 - endloop - endfacet - facet normal -5.17994e-23 -2.68398e-23 1 - outer loop - vertex 0.610808 0.443778 -1.16467e-23 - vertex 0.443778 0.610808 -1.58157e-23 - vertex 0.393816 0.542041 -2.02494e-23 - endloop - endfacet - facet normal -4.22932e-23 -3.3747e-23 1 - outer loop - vertex 0.679574 0.49374 -9.79382e-24 - vertex 0.49374 0.679574 -1.1382e-23 - vertex 0.443778 0.610808 -1.58157e-23 - endloop - endfacet - facet normal -3.45338e-23 -3.93843e-23 1 - outer loop - vertex 0.748341 0.543701 -7.94093e-24 - vertex 0.543701 0.748341 -6.94832e-24 - vertex 0.49374 0.679574 -1.1382e-23 - endloop - endfacet - facet normal -6.09198e-23 4.67627e-23 1 - outer loop - vertex 0.293893 0.404509 -2.91168e-23 - vertex 0.404509 0.293893 -1.72054e-23 - vertex 0.473275 0.343854 -1.53525e-23 - endloop - endfacet - facet normal -4.59446e-23 2.61504e-23 1 - outer loop - vertex 0.343854 0.473275 -2.46831e-23 - vertex 0.473275 0.343854 -1.53525e-23 - vertex 0.542041 0.393816 -1.34996e-23 - endloop - endfacet - facet normal -3.47686e-23 1.07689e-23 1 - outer loop - vertex 0.393816 0.542041 -2.02494e-23 - vertex 0.542041 0.393816 -1.34996e-23 - vertex 0.610808 0.443778 -1.16467e-23 - endloop - endfacet - facet normal -2.61093e-23 -1.14976e-24 1 - outer loop - vertex 0.443778 0.610808 -1.58157e-23 - vertex 0.610808 0.443778 -1.16467e-23 - vertex 0.679574 0.49374 -9.79382e-24 - endloop - endfacet - facet normal -1.92024e-23 -1.06562e-23 1 - outer loop - vertex 0.49374 0.679574 -1.1382e-23 - vertex 0.679574 0.49374 -9.79382e-24 - vertex 0.748341 0.543701 -7.94093e-24 - endloop - endfacet - facet normal -6.49789e-23 5.23496e-23 1 - outer loop - vertex 0.473275 0.343854 -1.53525e-23 - vertex 0.404509 0.293893 -1.72054e-23 - vertex 0.475528 0.154509 -5.29396e-24 - endloop - endfacet - facet normal -5.00037e-23 3.17372e-23 1 - outer loop - vertex 0.542041 0.393816 -1.34996e-23 - vertex 0.473275 0.343854 -1.53525e-23 - vertex 0.556368 0.180775 -6.02187e-24 - endloop - endfacet - facet normal -3.0168e-23 4.43662e-24 1 - outer loop - vertex 0.718048 0.233308 -7.47771e-24 - vertex 0.610808 0.443778 -1.16467e-23 - vertex 0.542041 0.393816 -1.34996e-23 - endloop - endfacet - facet normal -3.01681e-23 4.43657e-24 1 - outer loop - vertex 0.679574 0.49374 -9.79382e-24 - vertex 0.610808 0.443778 -1.16467e-23 - vertex 0.718048 0.233308 -7.47771e-24 - endloop - endfacet - facet normal -2.32611e-23 -5.06984e-24 1 - outer loop - vertex 0.748341 0.543701 -7.94093e-24 - vertex 0.679574 0.49374 -9.79382e-24 - vertex 0.798888 0.259574 -8.20563e-24 - endloop - endfacet - facet normal -8.2242e-24 5.3025e-23 1 - outer loop - vertex 0.475528 0.154509 -5.29396e-24 - vertex 0.556368 0.180775 -6.02187e-24 - vertex 0.473275 0.343854 -1.53525e-23 - endloop - endfacet - facet normal -2.34867e-24 3.4942e-23 1 - outer loop - vertex 0.556368 0.180775 -6.02187e-24 - vertex 0.637208 0.207041 -6.74979e-24 - vertex 0.542041 0.393816 -1.34996e-23 - endloop - endfacet - facet normal -2.34904e-24 3.49418e-23 1 - outer loop - vertex 0.542041 0.393816 -1.34996e-23 - vertex 0.637208 0.207041 -6.74979e-24 - vertex 0.718048 0.233308 -7.47771e-24 - endloop - endfacet - facet normal 5.83481e-24 9.75532e-24 1 - outer loop - vertex 0.718048 0.233308 -7.47771e-24 - vertex 0.798888 0.259574 -8.20563e-24 - vertex 0.679574 0.49374 -9.79382e-24 - endloop - endfacet - facet normal 8.79866e-24 6.33682e-25 1 - outer loop - vertex 0.798888 0.259574 -8.20563e-24 - vertex 0.879727 0.285841 -8.93355e-24 - vertex 0.748341 0.543701 -7.94093e-24 - endloop - endfacet - facet normal -1.52587e-23 7.46752e-23 1 - outer loop - vertex 0.556368 0.180775 -6.02187e-24 - vertex 0.475528 0.154509 -5.29396e-24 - vertex 0.5 -1.32349e-23 6.61744e-24 - endloop - endfacet - facet normal -7.38567e-24 5.04446e-23 1 - outer loop - vertex 0.637208 0.207041 -6.74979e-24 - vertex 0.556368 0.180775 -6.02187e-24 - vertex 0.585 1.05879e-23 3.30872e-24 - endloop - endfacet - facet normal 3.04181e-24 1.83508e-23 1 - outer loop - vertex 0.755 5.82335e-23 -3.30872e-24 - vertex 0.718048 0.233308 -7.47771e-24 - vertex 0.637208 0.207041 -6.74979e-24 - endloop - endfacet - facet normal 3.04202e-24 1.83508e-23 1 - outer loop - vertex 0.798888 0.259574 -8.20563e-24 - vertex 0.718048 0.233308 -7.47771e-24 - vertex 0.755 5.82335e-23 -3.30872e-24 - endloop - endfacet - facet normal 9.63697e-24 -1.94628e-24 1 - outer loop - vertex 0.925 1.05879e-22 -9.92617e-24 - vertex 0.879727 0.285841 -8.93355e-24 - vertex 0.798888 0.259574 -8.20563e-24 - endloop - endfacet - facet normal 3.89261e-23 5.77797e-23 1 - outer loop - vertex 0.5 -1.32349e-23 6.61744e-24 - vertex 0.585 1.05879e-23 3.30872e-24 - vertex 0.556368 0.180775 -6.02187e-24 - endloop - endfacet - facet normal 3.89261e-23 3.87665e-23 1 - outer loop - vertex 0.585 1.05879e-23 3.30872e-24 - vertex 0.67 3.44107e-23 -7.34684e-40 - vertex 0.637208 0.207041 -6.74979e-24 - endloop - endfacet - facet normal 3.89261e-23 3.87665e-23 1 - outer loop - vertex 0.637208 0.207041 -6.74979e-24 - vertex 0.67 3.44107e-23 -7.34684e-40 - vertex 0.755 5.82335e-23 -3.30872e-24 - endloop - endfacet - facet normal 3.89261e-23 1.22837e-23 1 - outer loop - vertex 0.755 5.82335e-23 -3.30872e-24 - vertex 0.84 8.20563e-23 -6.61744e-24 - vertex 0.798888 0.259574 -8.20563e-24 - endloop - endfacet - facet normal 3.89262e-23 1.22837e-23 1 - outer loop - vertex 0.798888 0.259574 -8.20563e-24 - vertex 0.84 8.20563e-23 -6.61744e-24 - vertex 0.925 1.05879e-22 -9.92617e-24 - endloop - endfacet - facet normal 3.89261e-23 4.89944e-23 1 - outer loop - vertex 0.585 1.05879e-23 3.30872e-24 - vertex 0.5 -1.32349e-23 6.61744e-24 - vertex 0.573415 -0.463525 2.64698e-23 - endloop - endfacet - facet normal 3.89261e-23 5.55019e-23 1 - outer loop - vertex 0.67 3.44107e-23 -7.34684e-40 - vertex 0.585 1.05879e-23 3.30872e-24 - vertex 0.654255 -0.437259 2.48816e-23 - endloop - endfacet - facet normal 3.89261e-23 7.11828e-23 1 - outer loop - vertex 0.815935 -0.384726 2.17052e-23 - vertex 0.755 5.82335e-23 -3.30872e-24 - vertex 0.67 3.44107e-23 -7.34684e-40 - endloop - endfacet - facet normal 3.89261e-23 7.11828e-23 1 - outer loop - vertex 0.84 8.20563e-23 -6.61744e-24 - vertex 0.755 5.82335e-23 -3.30872e-24 - vertex 0.815935 -0.384726 2.17052e-23 - endloop - endfacet - facet normal 3.89262e-23 9.18232e-23 1 - outer loop - vertex 0.977614 -0.332193 1.85288e-23 - vertex 0.925 1.05879e-22 -9.92617e-24 - vertex 0.84 8.20563e-23 -6.61744e-24 - endloop - endfacet - facet normal 3.43908e-24 4.98813e-23 1 - outer loop - vertex 0.573415 -0.463525 2.64698e-23 - vertex 0.654255 -0.437259 2.48816e-23 - vertex 0.585 1.05879e-23 3.30872e-24 - endloop - endfacet - facet normal 1.17121e-24 5.68614e-23 1 - outer loop - vertex 0.654255 -0.437259 2.48816e-23 - vertex 0.735095 -0.410993 2.32934e-23 - vertex 0.67 3.44107e-23 -7.34684e-40 - endloop - endfacet - facet normal 1.17049e-24 5.68613e-23 1 - outer loop - vertex 0.67 3.44107e-23 -7.34684e-40 - vertex 0.735095 -0.410993 2.32934e-23 - vertex 0.815935 -0.384726 2.17052e-23 - endloop - endfacet - facet normal -4.3618e-24 7.38905e-23 1 - outer loop - vertex 0.815935 -0.384726 2.17052e-23 - vertex 0.896775 -0.35846 2.0117e-23 - vertex 0.84 8.20563e-23 -6.61744e-24 - endloop - endfacet - facet normal -4.36274e-24 7.38904e-23 1 - outer loop - vertex 0.84 8.20563e-23 -6.61744e-24 - vertex 0.896775 -0.35846 2.0117e-23 - vertex 0.977614 -0.332193 1.85288e-23 - endloop - endfacet - facet normal 3.62107e-24 4.93212e-23 1 - outer loop - vertex 0.654255 -0.437259 2.48816e-23 - vertex 0.573415 -0.463525 2.64698e-23 - vertex 0.786475 -0.881678 4.63221e-23 - endloop - endfacet - facet normal -6.57833e-25 6.24907e-23 1 - outer loop - vertex 0.924007 -0.781754 4.65868e-23 - vertex 0.735095 -0.410993 2.32934e-23 - vertex 0.654255 -0.437259 2.48816e-23 - endloop - endfacet - facet normal -6.58542e-25 6.24904e-23 1 - outer loop - vertex 0.815935 -0.384726 2.17052e-23 - vertex 0.735095 -0.410993 2.32934e-23 - vertex 0.924007 -0.781754 4.65868e-23 - endloop - endfacet - facet normal -6.19088e-24 7.952e-23 1 - outer loop - vertex 1.06154 -0.681831 4.68515e-23 - vertex 0.896775 -0.35846 2.0117e-23 - vertex 0.815935 -0.384726 2.17052e-23 - endloop - endfacet - facet normal -6.19181e-24 7.95195e-23 1 - outer loop - vertex 0.977614 -0.332193 1.85288e-23 - vertex 0.896775 -0.35846 2.0117e-23 - vertex 1.06154 -0.681831 4.68515e-23 - endloop - endfacet - facet normal -3.04048e-23 3.91981e-23 1 - outer loop - vertex 0.786475 -0.881678 4.63221e-23 - vertex 0.855241 -0.831716 4.64545e-23 - vertex 0.654255 -0.437259 2.48816e-23 - endloop - endfacet - facet normal -3.04037e-23 3.91986e-23 1 - outer loop - vertex 0.654255 -0.437259 2.48816e-23 - vertex 0.855241 -0.831716 4.64545e-23 - vertex 0.924007 -0.781754 4.65868e-23 - endloop - endfacet - facet normal -3.96209e-23 5.18847e-23 1 - outer loop - vertex 0.924007 -0.781754 4.65868e-23 - vertex 0.992774 -0.731793 4.67192e-23 - vertex 0.815935 -0.384726 2.17052e-23 - endloop - endfacet - facet normal -3.96208e-23 5.18848e-23 1 - outer loop - vertex 0.815935 -0.384726 2.17052e-23 - vertex 0.992774 -0.731793 4.67192e-23 - vertex 1.06154 -0.681831 4.68515e-23 - endloop - endfacet - facet normal -5.17517e-23 6.85835e-23 1 - outer loop - vertex 1.06154 -0.681831 4.68515e-23 - vertex 1.13031 -0.631869 4.69839e-23 - vertex 0.977614 -0.332193 1.85288e-23 - endloop - endfacet - facet normal -3.01147e-23 3.87988e-23 1 - outer loop - vertex 1.16828 -1.14476 6.80273e-23 - vertex 0.855241 -0.831716 4.64545e-23 - vertex 0.786475 -0.881678 4.63221e-23 - endloop - endfacet - facet normal -3.01138e-23 3.87997e-23 1 - outer loop - vertex 0.924007 -0.781754 4.65868e-23 - vertex 0.855241 -0.831716 4.64545e-23 - vertex 1.16828 -1.14476 6.80273e-23 - endloop - endfacet - facet normal -3.44279e-23 4.4737e-23 1 - outer loop - vertex 0.992774 -0.731793 4.67192e-23 - vertex 0.924007 -0.781754 4.65868e-23 - vertex 1.21825 -1.07599 6.98802e-23 - endloop - endfacet - facet normal -4.49525e-23 5.9223e-23 1 - outer loop - vertex 1.31817 -0.93846 7.3586e-23 - vertex 1.06154 -0.681831 4.68515e-23 - vertex 0.992774 -0.731793 4.67192e-23 - endloop - endfacet - facet normal -5.14626e-23 6.81856e-23 1 - outer loop - vertex 1.36813 -0.869693 7.54389e-23 - vertex 1.13031 -0.631869 4.69839e-23 - vertex 1.06154 -0.681831 4.68515e-23 - endloop - endfacet - facet normal -5.02568e-23 9.56706e-24 1 - outer loop - vertex 0.786475 -0.881678 4.63221e-23 - vertex 1.11832 -1.21353 6.61744e-23 - vertex 1.16828 -1.14476 6.80273e-23 - endloop - endfacet - facet normal -6.14538e-23 1.77104e-23 1 - outer loop - vertex 1.16828 -1.14476 6.80273e-23 - vertex 1.21825 -1.07599 6.98802e-23 - vertex 0.924007 -0.781754 4.65868e-23 - endloop - endfacet - facet normal -6.82056e-23 2.26099e-23 1 - outer loop - vertex 1.21825 -1.07599 6.98802e-23 - vertex 1.26821 -1.00723 7.17331e-23 - vertex 0.992774 -0.731793 4.67192e-23 - endloop - endfacet - facet normal -7.59451e-23 2.82303e-23 1 - outer loop - vertex 1.06154 -0.681831 4.68515e-23 - vertex 1.31817 -0.93846 7.3586e-23 - vertex 1.36813 -0.869693 7.54389e-23 - endloop - endfacet - facet normal -6.82077e-23 2.26079e-23 1 - outer loop - vertex 0.992774 -0.731793 4.67192e-23 - vertex 1.26821 -1.00723 7.17331e-23 - vertex 1.31817 -0.93846 7.3586e-23 - endloop - endfacet - facet normal -4.46701e-23 5.5085e-24 1 - outer loop - vertex 1.16828 -1.14476 6.80273e-23 - vertex 1.11832 -1.21353 6.61744e-23 - vertex 1.53647 -1.42658 8.60268e-23 - endloop - endfacet - facet normal -4.99318e-23 9.33825e-24 1 - outer loop - vertex 1.21825 -1.07599 6.98802e-23 - vertex 1.16828 -1.14476 6.80273e-23 - vertex 1.56274 -1.34574 8.96002e-23 - endloop - endfacet - facet normal -6.26208e-23 1.85521e-23 1 - outer loop - vertex 1.61527 -1.18407 9.6747e-23 - vertex 1.26821 -1.00723 7.17331e-23 - vertex 1.21825 -1.07599 6.98802e-23 - endloop - endfacet - facet normal -7.03572e-23 2.41707e-23 1 - outer loop - vertex 1.36813 -0.869693 7.54389e-23 - vertex 1.31817 -0.93846 7.3586e-23 - vertex 1.64154 -1.10323 1.0032e-22 - endloop - endfacet - facet normal -7.03576e-23 2.41698e-23 1 - outer loop - vertex 1.64154 -1.10323 1.0032e-22 - vertex 1.31817 -0.93846 7.3586e-23 - vertex 1.26821 -1.00723 7.17331e-23 - endloop - endfacet - facet normal -6.62436e-23 -2.26767e-23 1 - outer loop - vertex 1.53647 -1.42658 8.60268e-23 - vertex 1.56274 -1.34574 8.96002e-23 - vertex 1.16828 -1.14476 6.80273e-23 - endloop - endfacet - facet normal -7.3226e-23 -2.04101e-23 1 - outer loop - vertex 1.56274 -1.34574 8.96002e-23 - vertex 1.58901 -1.26491 9.31736e-23 - vertex 1.21825 -1.07599 6.98802e-23 - endloop - endfacet - facet normal -8.11565e-23 -1.78256e-23 1 - outer loop - vertex 1.26821 -1.00723 7.17331e-23 - vertex 1.61527 -1.18407 9.6747e-23 - vertex 1.64154 -1.10323 1.0032e-22 - endloop - endfacet - facet normal -7.32289e-23 -2.04158e-23 1 - outer loop - vertex 1.21825 -1.07599 6.98802e-23 - vertex 1.58901 -1.26491 9.31736e-23 - vertex 1.61527 -1.18407 9.6747e-23 - endloop - endfacet - facet normal -1.0079e-22 -1.14579e-23 1 - outer loop - vertex 1.64154 -1.10323 1.0032e-22 - vertex 1.66781 -1.02239 1.03894e-22 - vertex 1.36813 -0.869693 7.54389e-23 - endloop - endfacet - facet normal -4.73905e-23 -2.88032e-23 1 - outer loop - vertex 1.56274 -1.34574 8.96002e-23 - vertex 1.53647 -1.42658 8.60268e-23 - vertex 2 -1.5 1.05879e-22 - endloop - endfacet - facet normal -5.35805e-23 -2.6795e-23 1 - outer loop - vertex 1.58901 -1.26491 9.31736e-23 - vertex 1.56274 -1.34574 8.96002e-23 - vertex 2 -1.415 1.11173e-22 - endloop - endfacet - facet normal -6.84919e-23 -2.19411e-23 1 - outer loop - vertex 1.64154 -1.10323 1.0032e-22 - vertex 1.61527 -1.18407 9.6747e-23 - vertex 2 -1.245 1.21761e-22 - endloop - endfacet - facet normal -6.84939e-23 -2.19539e-23 1 - outer loop - vertex 2 -1.245 1.21761e-22 - vertex 1.61527 -1.18407 9.6747e-23 - vertex 1.58901 -1.26491 9.31736e-23 - endloop - endfacet - facet normal -7.75914e-23 -1.89965e-23 1 - outer loop - vertex 1.66781 -1.02239 1.03894e-22 - vertex 1.64154 -1.10323 1.0032e-22 - vertex 2 -1.16 1.27055e-22 - endloop - endfacet - facet normal -5.92016e-23 -6.22824e-23 1 - outer loop - vertex 2 -1.5 1.05879e-22 - vertex 2 -1.415 1.11173e-22 - vertex 1.56274 -1.34574 8.96002e-23 - endloop - endfacet - facet normal -6.65402e-23 -6.22823e-23 1 - outer loop - vertex 2 -1.415 1.11173e-22 - vertex 2 -1.33 1.16467e-22 - vertex 1.58901 -1.26491 9.31736e-23 - endloop - endfacet - facet normal -8.44467e-23 -6.22823e-23 1 - outer loop - vertex 2 -1.245 1.21761e-22 - vertex 2 -1.16 1.27055e-22 - vertex 1.64154 -1.10323 1.0032e-22 - endloop - endfacet - facet normal -6.65402e-23 -6.22823e-23 1 - outer loop - vertex 1.58901 -1.26491 9.31736e-23 - vertex 2 -1.33 1.16467e-22 - vertex 2 -1.245 1.21761e-22 - endloop - endfacet - facet normal -9.55227e-23 -6.22824e-23 1 - outer loop - vertex 2 -1.16 1.27055e-22 - vertex 2 -1.075 1.32349e-22 - vertex 1.66781 -1.02239 1.03894e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.4 -1.415 1.11173e-22 - vertex 2 -1.415 1.11173e-22 - vertex 2 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.4 -1.33 1.16467e-22 - vertex 2 -1.33 1.16467e-22 - vertex 2 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.4 -1.16 1.27055e-22 - vertex 2 -1.16 1.27055e-22 - vertex 2 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.4 -1.245 1.21761e-22 - vertex 2 -1.245 1.21761e-22 - vertex 2 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.4 -1.075 1.32349e-22 - vertex 2 -1.075 1.32349e-22 - vertex 2 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2 -1.5 1.05879e-22 - vertex 2.4 -1.5 1.05879e-22 - vertex 2.4 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2 -1.415 1.11173e-22 - vertex 2.4 -1.415 1.11173e-22 - vertex 2.4 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2 -1.33 1.16467e-22 - vertex 2.4 -1.33 1.16467e-22 - vertex 2.4 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2 -1.245 1.21761e-22 - vertex 2.4 -1.245 1.21761e-22 - vertex 2.4 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2 -1.16 1.27055e-22 - vertex 2.4 -1.16 1.27055e-22 - vertex 2.4 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.8 -1.415 1.11173e-22 - vertex 2.4 -1.415 1.11173e-22 - vertex 2.4 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.8 -1.33 1.16467e-22 - vertex 2.4 -1.33 1.16467e-22 - vertex 2.4 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.8 -1.245 1.21761e-22 - vertex 2.4 -1.245 1.21761e-22 - vertex 2.4 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.8 -1.16 1.27055e-22 - vertex 2.4 -1.16 1.27055e-22 - vertex 2.4 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.8 -1.075 1.32349e-22 - vertex 2.4 -1.075 1.32349e-22 - vertex 2.4 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.4 -1.5 1.05879e-22 - vertex 2.8 -1.5 1.05879e-22 - vertex 2.8 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.4 -1.415 1.11173e-22 - vertex 2.8 -1.415 1.11173e-22 - vertex 2.8 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.4 -1.33 1.16467e-22 - vertex 2.8 -1.33 1.16467e-22 - vertex 2.8 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.4 -1.245 1.21761e-22 - vertex 2.8 -1.245 1.21761e-22 - vertex 2.8 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.4 -1.16 1.27055e-22 - vertex 2.8 -1.16 1.27055e-22 - vertex 2.8 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.2 -1.415 1.11173e-22 - vertex 2.8 -1.415 1.11173e-22 - vertex 2.8 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.2 -1.33 1.16467e-22 - vertex 2.8 -1.33 1.16467e-22 - vertex 2.8 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.2 -1.245 1.21761e-22 - vertex 2.8 -1.245 1.21761e-22 - vertex 2.8 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.2 -1.16 1.27055e-22 - vertex 2.8 -1.16 1.27055e-22 - vertex 2.8 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.2 -1.075 1.32349e-22 - vertex 2.8 -1.075 1.32349e-22 - vertex 2.8 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.8 -1.5 1.05879e-22 - vertex 3.2 -1.5 1.05879e-22 - vertex 3.2 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.8 -1.415 1.11173e-22 - vertex 3.2 -1.415 1.11173e-22 - vertex 3.2 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.8 -1.33 1.16467e-22 - vertex 3.2 -1.33 1.16467e-22 - vertex 3.2 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 2.8 -1.245 1.21761e-22 - vertex 3.2 -1.245 1.21761e-22 - vertex 3.2 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 2.8 -1.16 1.27055e-22 - vertex 3.2 -1.16 1.27055e-22 - vertex 3.2 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.6 -1.415 1.11173e-22 - vertex 3.2 -1.415 1.11173e-22 - vertex 3.2 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.6 -1.33 1.16467e-22 - vertex 3.2 -1.33 1.16467e-22 - vertex 3.2 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.6 -1.245 1.21761e-22 - vertex 3.2 -1.245 1.21761e-22 - vertex 3.2 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.6 -1.16 1.27055e-22 - vertex 3.2 -1.16 1.27055e-22 - vertex 3.2 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.6 -1.075 1.32349e-22 - vertex 3.2 -1.075 1.32349e-22 - vertex 3.2 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.2 -1.5 1.05879e-22 - vertex 3.6 -1.5 1.05879e-22 - vertex 3.6 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.2 -1.415 1.11173e-22 - vertex 3.6 -1.415 1.11173e-22 - vertex 3.6 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.2 -1.33 1.16467e-22 - vertex 3.6 -1.33 1.16467e-22 - vertex 3.6 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.2 -1.245 1.21761e-22 - vertex 3.6 -1.245 1.21761e-22 - vertex 3.6 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.2 -1.16 1.27055e-22 - vertex 3.6 -1.16 1.27055e-22 - vertex 3.6 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4 -1.415 1.11173e-22 - vertex 3.6 -1.415 1.11173e-22 - vertex 3.6 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4 -1.33 1.16467e-22 - vertex 3.6 -1.33 1.16467e-22 - vertex 3.6 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4 -1.245 1.21761e-22 - vertex 3.6 -1.245 1.21761e-22 - vertex 3.6 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4 -1.16 1.27055e-22 - vertex 3.6 -1.16 1.27055e-22 - vertex 3.6 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4 -1.075 1.32349e-22 - vertex 3.6 -1.075 1.32349e-22 - vertex 3.6 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.6 -1.5 1.05879e-22 - vertex 4 -1.5 1.05879e-22 - vertex 4 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.6 -1.415 1.11173e-22 - vertex 4 -1.415 1.11173e-22 - vertex 4 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.6 -1.33 1.16467e-22 - vertex 4 -1.33 1.16467e-22 - vertex 4 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 3.6 -1.245 1.21761e-22 - vertex 4 -1.245 1.21761e-22 - vertex 4 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 3.6 -1.16 1.27055e-22 - vertex 4 -1.16 1.27055e-22 - vertex 4 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.4 -1.415 1.11173e-22 - vertex 4 -1.415 1.11173e-22 - vertex 4 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.4 -1.33 1.16467e-22 - vertex 4 -1.33 1.16467e-22 - vertex 4 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.4 -1.245 1.21761e-22 - vertex 4 -1.245 1.21761e-22 - vertex 4 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.4 -1.16 1.27055e-22 - vertex 4 -1.16 1.27055e-22 - vertex 4 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.4 -1.075 1.32349e-22 - vertex 4 -1.075 1.32349e-22 - vertex 4 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4 -1.5 1.05879e-22 - vertex 4.4 -1.5 1.05879e-22 - vertex 4.4 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4 -1.415 1.11173e-22 - vertex 4.4 -1.415 1.11173e-22 - vertex 4.4 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4 -1.33 1.16467e-22 - vertex 4.4 -1.33 1.16467e-22 - vertex 4.4 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4 -1.245 1.21761e-22 - vertex 4.4 -1.245 1.21761e-22 - vertex 4.4 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4 -1.16 1.27055e-22 - vertex 4.4 -1.16 1.27055e-22 - vertex 4.4 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.8 -1.415 1.11173e-22 - vertex 4.4 -1.415 1.11173e-22 - vertex 4.4 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.8 -1.33 1.16467e-22 - vertex 4.4 -1.33 1.16467e-22 - vertex 4.4 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.8 -1.245 1.21761e-22 - vertex 4.4 -1.245 1.21761e-22 - vertex 4.4 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.8 -1.16 1.27055e-22 - vertex 4.4 -1.16 1.27055e-22 - vertex 4.4 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.8 -1.075 1.32349e-22 - vertex 4.4 -1.075 1.32349e-22 - vertex 4.4 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.4 -1.5 1.05879e-22 - vertex 4.8 -1.5 1.05879e-22 - vertex 4.8 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.4 -1.415 1.11173e-22 - vertex 4.8 -1.415 1.11173e-22 - vertex 4.8 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.4 -1.33 1.16467e-22 - vertex 4.8 -1.33 1.16467e-22 - vertex 4.8 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.4 -1.245 1.21761e-22 - vertex 4.8 -1.245 1.21761e-22 - vertex 4.8 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.4 -1.16 1.27055e-22 - vertex 4.8 -1.16 1.27055e-22 - vertex 4.8 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.2 -1.415 1.11173e-22 - vertex 4.8 -1.415 1.11173e-22 - vertex 4.8 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.2 -1.33 1.16467e-22 - vertex 4.8 -1.33 1.16467e-22 - vertex 4.8 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.2 -1.245 1.21761e-22 - vertex 4.8 -1.245 1.21761e-22 - vertex 4.8 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.2 -1.16 1.27055e-22 - vertex 4.8 -1.16 1.27055e-22 - vertex 4.8 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.2 -1.075 1.32349e-22 - vertex 4.8 -1.075 1.32349e-22 - vertex 4.8 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.8 -1.5 1.05879e-22 - vertex 5.2 -1.5 1.05879e-22 - vertex 5.2 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.8 -1.415 1.11173e-22 - vertex 5.2 -1.415 1.11173e-22 - vertex 5.2 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.8 -1.33 1.16467e-22 - vertex 5.2 -1.33 1.16467e-22 - vertex 5.2 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 4.8 -1.245 1.21761e-22 - vertex 5.2 -1.245 1.21761e-22 - vertex 5.2 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 4.8 -1.16 1.27055e-22 - vertex 5.2 -1.16 1.27055e-22 - vertex 5.2 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.6 -1.415 1.11173e-22 - vertex 5.2 -1.415 1.11173e-22 - vertex 5.2 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.6 -1.33 1.16467e-22 - vertex 5.2 -1.33 1.16467e-22 - vertex 5.2 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.6 -1.245 1.21761e-22 - vertex 5.2 -1.245 1.21761e-22 - vertex 5.2 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.6 -1.16 1.27055e-22 - vertex 5.2 -1.16 1.27055e-22 - vertex 5.2 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.6 -1.075 1.32349e-22 - vertex 5.2 -1.075 1.32349e-22 - vertex 5.2 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.2 -1.5 1.05879e-22 - vertex 5.6 -1.5 1.05879e-22 - vertex 5.6 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.2 -1.415 1.11173e-22 - vertex 5.6 -1.415 1.11173e-22 - vertex 5.6 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.2 -1.33 1.16467e-22 - vertex 5.6 -1.33 1.16467e-22 - vertex 5.6 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.2 -1.245 1.21761e-22 - vertex 5.6 -1.245 1.21761e-22 - vertex 5.6 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.2 -1.16 1.27055e-22 - vertex 5.6 -1.16 1.27055e-22 - vertex 5.6 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 6 -1.415 1.11173e-22 - vertex 5.6 -1.415 1.11173e-22 - vertex 5.6 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 6 -1.33 1.16467e-22 - vertex 5.6 -1.33 1.16467e-22 - vertex 5.6 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 6 -1.245 1.21761e-22 - vertex 5.6 -1.245 1.21761e-22 - vertex 5.6 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 6 -1.16 1.27055e-22 - vertex 5.6 -1.16 1.27055e-22 - vertex 5.6 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 6 -1.075 1.32349e-22 - vertex 5.6 -1.075 1.32349e-22 - vertex 5.6 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.6 -1.5 1.05879e-22 - vertex 6 -1.5 1.05879e-22 - vertex 6 -1.415 1.11173e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.6 -1.415 1.11173e-22 - vertex 6 -1.415 1.11173e-22 - vertex 6 -1.33 1.16467e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.6 -1.33 1.16467e-22 - vertex 6 -1.33 1.16467e-22 - vertex 6 -1.245 1.21761e-22 - endloop - endfacet - facet normal 0 -6.22823e-23 1 - outer loop - vertex 5.6 -1.245 1.21761e-22 - vertex 6 -1.245 1.21761e-22 - vertex 6 -1.16 1.27055e-22 - endloop - endfacet - facet normal 0 -6.22824e-23 1 - outer loop - vertex 5.6 -1.16 1.27055e-22 - vertex 6 -1.16 1.27055e-22 - vertex 6 -1.075 1.32349e-22 - endloop - endfacet -endsolid symm -solid symm1 - facet normal 0 1.17562e-16 1 - outer loop - vertex -2 1.5 -4.9133e-17 - vertex -2 1.415 -3.91402e-17 - vertex -1.6 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.33 -2.91474e-17 - vertex -1.6 1.415 -3.91402e-17 - vertex -2 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.415 -3.91402e-17 - vertex -1.6 1.5 -4.9133e-17 - vertex -2 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -2 1.415 -3.91402e-17 - vertex -2 1.33 -2.91474e-17 - vertex -1.6 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.415 -3.91402e-17 - vertex -1.6 1.33 -2.91474e-17 - vertex -1.2 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.5 -4.9133e-17 - vertex -1.6 1.415 -3.91402e-17 - vertex -1.2 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.245 -1.91546e-17 - vertex -1.6 1.33 -2.91474e-17 - vertex -2 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.245 -1.91546e-17 - vertex -1.2 1.33 -2.91474e-17 - vertex -1.6 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.33 -2.91474e-17 - vertex -1.2 1.415 -3.91402e-17 - vertex -1.6 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.415 -3.91402e-17 - vertex -1.2 1.5 -4.9133e-17 - vertex -1.6 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -2 1.33 -2.91474e-17 - vertex -2 1.245 -1.91546e-17 - vertex -1.6 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.33 -2.91474e-17 - vertex -1.6 1.245 -1.91546e-17 - vertex -1.2 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.33 -2.91474e-17 - vertex -1.2 1.245 -1.91546e-17 - vertex -0.8 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.415 -3.91402e-17 - vertex -1.2 1.33 -2.91474e-17 - vertex -0.8 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.5 -4.9133e-17 - vertex -1.2 1.415 -3.91402e-17 - vertex -0.8 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -1.6 1.16 -9.16178e-18 - vertex -1.6 1.245 -1.91546e-17 - vertex -2 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -1.2 1.16 -9.16178e-18 - vertex -1.2 1.245 -1.91546e-17 - vertex -1.6 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -0.8 1.16 -9.16178e-18 - vertex -0.8 1.245 -1.91546e-17 - vertex -1.2 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.245 -1.91546e-17 - vertex -0.8 1.33 -2.91474e-17 - vertex -1.2 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.33 -2.91474e-17 - vertex -0.8 1.415 -3.91402e-17 - vertex -1.2 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.415 -3.91402e-17 - vertex -0.8 1.5 -4.9133e-17 - vertex -1.2 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -2 1.245 -1.91546e-17 - vertex -2 1.16 -9.16178e-18 - vertex -1.6 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -1.6 1.245 -1.91546e-17 - vertex -1.6 1.16 -9.16178e-18 - vertex -1.2 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -1.2 1.245 -1.91546e-17 - vertex -1.2 1.16 -9.16178e-18 - vertex -0.8 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -0.8 1.245 -1.91546e-17 - vertex -0.8 1.16 -9.16178e-18 - vertex -0.4 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.33 -2.91474e-17 - vertex -0.8 1.245 -1.91546e-17 - vertex -0.4 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.415 -3.91402e-17 - vertex -0.8 1.33 -2.91474e-17 - vertex -0.4 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.5 -4.9133e-17 - vertex -0.8 1.415 -3.91402e-17 - vertex -0.4 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.075 8.31019e-19 - vertex -1.6 1.16 -9.16178e-18 - vertex -2 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.075 8.31019e-19 - vertex -1.2 1.16 -9.16178e-18 - vertex -1.6 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.075 8.31019e-19 - vertex -0.8 1.16 -9.16178e-18 - vertex -1.2 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.075 8.31019e-19 - vertex -0.4 1.16 -9.16178e-18 - vertex -0.8 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -0.4 1.16 -9.16178e-18 - vertex -0.4 1.245 -1.91546e-17 - vertex -0.8 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.245 -1.91546e-17 - vertex -0.4 1.33 -2.91474e-17 - vertex -0.8 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.33 -2.91474e-17 - vertex -0.4 1.415 -3.91402e-17 - vertex -0.8 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.415 -3.91402e-17 - vertex -0.4 1.5 -4.9133e-17 - vertex -0.8 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -2 1.16 -9.16178e-18 - vertex -2 1.075 8.31019e-19 - vertex -1.6 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.6 1.16 -9.16178e-18 - vertex -1.6 1.075 8.31019e-19 - vertex -1.2 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -1.2 1.16 -9.16178e-18 - vertex -1.2 1.075 8.31019e-19 - vertex -0.8 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.8 1.16 -9.16178e-18 - vertex -0.8 1.075 8.31019e-19 - vertex -0.4 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.16 -9.16178e-18 - vertex -0.4 1.075 8.31019e-19 - vertex -6.61744e-24 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -0.4 1.245 -1.91546e-17 - vertex -0.4 1.16 -9.16178e-18 - vertex -2.64698e-23 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.33 -2.91474e-17 - vertex -0.4 1.245 -1.91546e-17 - vertex -4.63221e-23 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.415 -3.91402e-17 - vertex -0.4 1.33 -2.91474e-17 - vertex -6.61744e-23 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -0.4 1.5 -4.9133e-17 - vertex -0.4 1.415 -3.91402e-17 - vertex -8.60268e-23 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -6.61744e-24 1.075 8.31019e-19 - vertex -2.64698e-23 1.16 -9.16178e-18 - vertex -0.4 1.16 -9.16178e-18 - endloop - endfacet - facet normal 0 1.17563e-16 1 - outer loop - vertex -2.64698e-23 1.16 -9.16178e-18 - vertex -4.63221e-23 1.245 -1.91546e-17 - vertex -0.4 1.245 -1.91546e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -4.63221e-23 1.245 -1.91546e-17 - vertex -6.61744e-23 1.33 -2.91474e-17 - vertex -0.4 1.33 -2.91474e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -6.61744e-23 1.33 -2.91474e-17 - vertex -8.60268e-23 1.415 -3.91402e-17 - vertex -0.4 1.415 -3.91402e-17 - endloop - endfacet - facet normal 0 1.17562e-16 1 - outer loop - vertex -8.60268e-23 1.415 -3.91402e-17 - vertex -1.05879e-22 1.5 -4.9133e-17 - vertex -0.4 1.5 -4.9133e-17 - endloop - endfacet - facet normal 2.23413e-17 1.17562e-16 1 - outer loop - vertex -2.64698e-23 1.16 -9.16178e-18 - vertex -6.61744e-24 1.075 8.31019e-19 - vertex 0.332193 1.02239 -4.05649e-19 - endloop - endfacet - facet normal 1.31487e-17 1.17563e-16 1 - outer loop - vertex -4.63221e-23 1.245 -1.91546e-17 - vertex -2.64698e-23 1.16 -9.16178e-18 - vertex 0.35846 1.10323 -7.20103e-18 - endloop - endfacet - facet normal 5.21117e-18 1.17562e-16 1 - outer loop - vertex -6.61744e-23 1.33 -2.91474e-17 - vertex -4.63221e-23 1.245 -1.91546e-17 - vertex 0.384726 1.18407 -1.39964e-17 - endloop - endfacet - facet normal -1.71159e-18 1.17562e-16 1 - outer loop - vertex -8.60268e-23 1.415 -3.91402e-17 - vertex -6.61744e-23 1.33 -2.91474e-17 - vertex 0.410993 1.26491 -2.07918e-17 - endloop - endfacet - facet normal -1.32012e-17 1.17562e-16 1 - outer loop - vertex 0.463525 1.42658 -3.43825e-17 - vertex -1.05879e-22 1.5 -4.9133e-17 - vertex -8.60268e-23 1.415 -3.91402e-17 - endloop - endfacet - facet normal 7.45892e-18 8.1636e-17 1 - outer loop - vertex 0.332193 1.02239 -4.05649e-19 - vertex 0.35846 1.10323 -7.20103e-18 - vertex -2.64698e-23 1.16 -9.16178e-18 - endloop - endfacet - facet normal -9.01099e-20 8.40888e-17 1 - outer loop - vertex 0.35846 1.10323 -7.20103e-18 - vertex 0.384726 1.18407 -1.39964e-17 - vertex -4.63221e-23 1.245 -1.91546e-17 - endloop - endfacet - facet normal -6.67404e-18 8.62284e-17 1 - outer loop - vertex 0.384726 1.18407 -1.39964e-17 - vertex 0.410993 1.26491 -2.07918e-17 - vertex -6.61744e-23 1.33 -2.91474e-17 - endloop - endfacet - facet normal -1.24635e-17 8.81204e-17 1 - outer loop - vertex 0.410993 1.26491 -2.07918e-17 - vertex 0.437259 1.34574 -2.75872e-17 - vertex -8.60268e-23 1.415 -3.91402e-17 - endloop - endfacet - facet normal -1.24653e-17 8.81088e-17 1 - outer loop - vertex -8.60268e-23 1.415 -3.91402e-17 - vertex 0.437259 1.34574 -2.75872e-17 - vertex 0.463525 1.42658 -3.43825e-17 - endloop - endfacet - facet normal 3.15454e-17 7.38097e-17 1 - outer loop - vertex 0.681831 0.93846 -5.24027e-18 - vertex 0.35846 1.10323 -7.20103e-18 - vertex 0.332193 1.02239 -4.05649e-19 - endloop - endfacet - facet normal 2.39958e-17 7.6263e-17 1 - outer loop - vertex 0.731793 1.00723 -8.83823e-18 - vertex 0.384726 1.18407 -1.39964e-17 - vertex 0.35846 1.10323 -7.20103e-18 - endloop - endfacet - facet normal 2.39959e-17 7.6263e-17 1 - outer loop - vertex 0.410993 1.26491 -2.07918e-17 - vertex 0.384726 1.18407 -1.39964e-17 - vertex 0.731793 1.00723 -8.83823e-18 - endloop - endfacet - facet normal 1.16219e-17 8.02937e-17 1 - outer loop - vertex 0.831716 1.14476 -1.60341e-17 - vertex 0.437259 1.34574 -2.75872e-17 - vertex 0.410993 1.26491 -2.07918e-17 - endloop - endfacet - facet normal 6.4802e-18 8.19531e-17 1 - outer loop - vertex 0.881678 1.21353 -1.96321e-17 - vertex 0.463525 1.42658 -3.43825e-17 - vertex 0.437259 1.34574 -2.75872e-17 - endloop - endfacet - facet normal 1.50308e-17 4.13987e-17 1 - outer loop - vertex 0.35846 1.10323 -7.20103e-18 - vertex 0.681831 0.93846 -5.24027e-18 - vertex 0.731793 1.00723 -8.83823e-18 - endloop - endfacet - facet normal 2.24684e-17 3.59967e-17 1 - outer loop - vertex 0.332193 1.02239 -4.05649e-19 - vertex 0.631869 0.869693 -1.64232e-18 - vertex 0.681831 0.93846 -5.24027e-18 - endloop - endfacet - facet normal 3.0115e-18 5.01384e-17 1 - outer loop - vertex 0.731793 1.00723 -8.83823e-18 - vertex 0.781754 1.07599 -1.24362e-17 - vertex 0.410993 1.26491 -2.07918e-17 - endloop - endfacet - facet normal -1.92047e-18 5.37146e-17 1 - outer loop - vertex 0.437259 1.34574 -2.75872e-17 - vertex 0.831716 1.14476 -1.60341e-17 - vertex 0.881678 1.21353 -1.96321e-17 - endloop - endfacet - facet normal 3.00836e-18 5.01322e-17 1 - outer loop - vertex 0.410993 1.26491 -2.07918e-17 - vertex 0.781754 1.07599 -1.24362e-17 - vertex 0.831716 1.14476 -1.60341e-17 - endloop - endfacet - facet normal 1.94563e-17 3.81835e-17 1 - outer loop - vertex 1.00723 0.731793 -3.68005e-18 - vertex 0.731793 1.00723 -8.83823e-18 - vertex 0.681831 0.93846 -5.24027e-18 - endloop - endfacet - facet normal 2.58786e-17 3.3519e-17 1 - outer loop - vertex 0.93846 0.681831 -3.27952e-18 - vertex 0.681831 0.93846 -5.24027e-18 - vertex 0.631869 0.869693 -1.64232e-18 - endloop - endfacet - facet normal 1.3859e-17 4.22566e-17 1 - outer loop - vertex 1.07599 0.781754 -4.08059e-18 - vertex 0.781754 1.07599 -1.24362e-17 - vertex 0.731793 1.00723 -8.83823e-18 - endloop - endfacet - facet normal 4.55861e-18 4.90075e-17 1 - outer loop - vertex 1.21353 0.881678 -4.88165e-18 - vertex 0.881678 1.21353 -1.96321e-17 - vertex 0.831716 1.14476 -1.60341e-17 - endloop - endfacet - facet normal 8.92701e-18 4.58323e-17 1 - outer loop - vertex 1.14476 0.831716 -4.48112e-18 - vertex 0.831716 1.14476 -1.60341e-17 - vertex 0.781754 1.07599 -1.24362e-17 - endloop - endfacet - facet normal -4.50715e-18 1.42201e-17 1 - outer loop - vertex 0.731793 1.00723 -8.83823e-18 - vertex 1.00723 0.731793 -3.68005e-18 - vertex 1.07599 0.781754 -4.08059e-18 - endloop - endfacet - facet normal 1.58341e-19 7.79875e-18 1 - outer loop - vertex 0.681831 0.93846 -5.24027e-18 - vertex 0.93846 0.681831 -3.27952e-18 - vertex 1.00723 0.731793 -3.68005e-18 - endloop - endfacet - facet normal 5.56165e-18 3.61714e-19 1 - outer loop - vertex 0.631869 0.869693 -1.64232e-18 - vertex 0.869693 0.631869 -2.87899e-18 - vertex 0.93846 0.681831 -3.27952e-18 - endloop - endfacet - facet normal -8.57623e-18 1.98214e-17 1 - outer loop - vertex 0.781754 1.07599 -1.24362e-17 - vertex 1.07599 0.781754 -4.08059e-18 - vertex 1.14476 0.831716 -4.48112e-18 - endloop - endfacet - facet normal -1.21562e-17 2.47491e-17 1 - outer loop - vertex 0.831716 1.14476 -1.60341e-17 - vertex 1.14476 0.831716 -4.48112e-18 - vertex 1.21353 0.881678 -4.88165e-18 - endloop - endfacet - facet normal -7.69921e-18 1.86132e-17 1 - outer loop - vertex 1.26491 0.410993 4.27501e-18 - vertex 1.07599 0.781754 -4.08059e-18 - vertex 1.00723 0.731793 -3.68005e-18 - endloop - endfacet - facet normal 1.03565e-18 6.59117e-18 1 - outer loop - vertex 1.00723 0.731793 -3.68005e-18 - vertex 0.93846 0.681831 -3.27952e-18 - vertex 1.10323 0.35846 -1.31877e-18 - endloop - endfacet - facet normal 6.43893e-18 -8.45761e-19 1 - outer loop - vertex 0.93846 0.681831 -3.27952e-18 - vertex 0.869693 0.631869 -2.87899e-18 - vertex 1.02239 0.332193 -4.11565e-18 - endloop - endfacet - facet normal -7.69867e-18 1.86135e-17 1 - outer loop - vertex 1.14476 0.831716 -4.48112e-18 - vertex 1.07599 0.781754 -4.08059e-18 - vertex 1.26491 0.410993 4.27501e-18 - endloop - endfacet - facet normal -1.1279e-17 2.35416e-17 1 - outer loop - vertex 1.21353 0.881678 -4.88165e-18 - vertex 1.14476 0.831716 -4.48112e-18 - vertex 1.34574 0.437259 7.0719e-18 - endloop - endfacet - facet normal -3.38267e-17 -2.37342e-18 1 - outer loop - vertex 1.00723 0.731793 -3.68005e-18 - vertex 1.18407 0.384726 1.47812e-18 - vertex 1.26491 0.410993 4.27501e-18 - endloop - endfacet - facet normal -3.38267e-17 -2.37343e-18 1 - outer loop - vertex 1.10323 0.35846 -1.31877e-18 - vertex 1.18407 0.384726 1.47812e-18 - vertex 1.00723 0.731793 -3.68005e-18 - endloop - endfacet - facet normal -3.13736e-17 -9.9226e-18 1 - outer loop - vertex 1.02239 0.332193 -4.11565e-18 - vertex 1.10323 0.35846 -1.31877e-18 - vertex 0.93846 0.681831 -3.27952e-18 - endloop - endfacet - facet normal -3.78524e-17 1.00022e-17 1 - outer loop - vertex 1.26491 0.410993 4.27501e-18 - vertex 1.34574 0.437259 7.0719e-18 - vertex 1.14476 0.831716 -4.48112e-18 - endloop - endfacet - facet normal -3.95174e-17 1.5141e-17 1 - outer loop - vertex 1.34574 0.437259 7.0719e-18 - vertex 1.42658 0.463525 9.86879e-18 - vertex 1.21353 0.881678 -4.88165e-18 - endloop - endfacet - facet normal -3.91871e-17 1.41241e-17 1 - outer loop - vertex 1.33 1.48231e-22 1.26306e-17 - vertex 1.26491 0.410993 4.27501e-18 - vertex 1.18407 0.384726 1.47812e-18 - endloop - endfacet - facet normal -3.70477e-17 7.54007e-18 1 - outer loop - vertex 1.245 1.69407e-22 6.6363e-18 - vertex 1.18407 0.384726 1.47812e-18 - vertex 1.10323 0.35846 -1.31877e-18 - endloop - endfacet - facet normal -3.45948e-17 -8.90081e-21 1 - outer loop - vertex 1.16 1.90582e-22 6.41987e-19 - vertex 1.10323 0.35846 -1.31877e-18 - vertex 1.02239 0.332193 -4.11565e-18 - endloop - endfacet - facet normal -4.10738e-17 1.99155e-17 1 - outer loop - vertex 1.415 1.27055e-22 1.86249e-17 - vertex 1.34574 0.437259 7.0719e-18 - vertex 1.26491 0.410993 4.27501e-18 - endloop - endfacet - facet normal -4.10689e-17 1.99163e-17 1 - outer loop - vertex 1.42658 0.463525 9.86879e-18 - vertex 1.34574 0.437259 7.0719e-18 - vertex 1.415 1.27055e-22 1.86249e-17 - endloop - endfacet - facet normal -7.05212e-17 9.16161e-18 1 - outer loop - vertex 1.26491 0.410993 4.27501e-18 - vertex 1.33 1.48231e-22 1.26306e-17 - vertex 1.415 1.27055e-22 1.86249e-17 - endloop - endfacet - facet normal -7.05211e-17 2.2388e-18 1 - outer loop - vertex 1.18407 0.384726 1.47812e-18 - vertex 1.245 1.69407e-22 6.6363e-18 - vertex 1.33 1.48231e-22 1.26306e-17 - endloop - endfacet - facet normal -7.05213e-17 -5.69864e-18 1 - outer loop - vertex 1.10323 0.35846 -1.31877e-18 - vertex 1.16 1.90582e-22 6.41987e-19 - vertex 1.245 1.69407e-22 6.6363e-18 - endloop - endfacet - facet normal -7.05213e-17 -1.48913e-17 1 - outer loop - vertex 1.02239 0.332193 -4.11565e-18 - vertex 1.075 2.11758e-22 -5.35232e-18 - vertex 1.16 1.90582e-22 6.41987e-19 - endloop - endfacet - facet normal -7.05211e-17 2.06521e-17 1 - outer loop - vertex 1.415 1.27055e-22 1.86249e-17 - vertex 1.5 1.05879e-22 2.46192e-17 - vertex 1.42658 0.463525 9.86879e-18 - endloop - endfacet - facet normal -7.05212e-17 -2.69884e-17 1 - outer loop - vertex 1.44363 -0.180775 1.57651e-17 - vertex 1.415 1.27055e-22 1.86249e-17 - vertex 1.33 1.48231e-22 1.26306e-17 - endloop - endfacet - facet normal -7.05211e-17 -2.1018e-17 1 - outer loop - vertex 1.36279 -0.207041 1.05914e-17 - vertex 1.33 1.48231e-22 1.26306e-17 - vertex 1.245 1.69407e-22 6.6363e-18 - endloop - endfacet - facet normal -7.05213e-17 -1.63919e-17 1 - outer loop - vertex 1.28195 -0.233308 5.4177e-18 - vertex 1.245 1.69407e-22 6.6363e-18 - vertex 1.16 1.90582e-22 6.41987e-19 - endloop - endfacet - facet normal -7.05213e-17 -1.2702e-17 1 - outer loop - vertex 1.20111 -0.259574 2.44018e-19 - vertex 1.16 1.90582e-22 6.41987e-19 - vertex 1.075 2.11758e-22 -5.35232e-18 - endloop - endfacet - facet normal -7.05211e-17 -3.49886e-17 1 - outer loop - vertex 1.52447 -0.154509 2.09388e-17 - vertex 1.5 1.05879e-22 2.46192e-17 - vertex 1.415 1.27055e-22 1.86249e-17 - endloop - endfacet - facet normal -5.59787e-17 -2.46852e-17 1 - outer loop - vertex 1.415 1.27055e-22 1.86249e-17 - vertex 1.44363 -0.180775 1.57651e-17 - vertex 1.52447 -0.154509 2.09388e-17 - endloop - endfacet - facet normal -5.78236e-17 -1.9007e-17 1 - outer loop - vertex 1.33 1.48231e-22 1.26306e-17 - vertex 1.36279 -0.207041 1.05914e-17 - vertex 1.44363 -0.180775 1.57651e-17 - endloop - endfacet - facet normal -5.9253e-17 -1.46073e-17 1 - outer loop - vertex 1.245 1.69407e-22 6.6363e-18 - vertex 1.28195 -0.233308 5.4177e-18 - vertex 1.36279 -0.207041 1.05914e-17 - endloop - endfacet - facet normal -6.03932e-17 -1.10979e-17 1 - outer loop - vertex 1.16 1.90582e-22 6.41987e-19 - vertex 1.20111 -0.259574 2.44018e-19 - vertex 1.28195 -0.233308 5.4177e-18 - endloop - endfacet - facet normal -6.13238e-17 -8.23352e-18 1 - outer loop - vertex 1.075 2.11758e-22 -5.35232e-18 - vertex 1.12027 -0.285841 -4.92967e-18 - vertex 1.20111 -0.259574 2.44018e-19 - endloop - endfacet - facet normal -5.00207e-17 -4.30226e-17 1 - outer loop - vertex 1.52447 -0.154509 2.09388e-17 - vertex 1.44363 -0.180775 1.57651e-17 - vertex 1.52672 -0.343855 1.29052e-17 - endloop - endfacet - facet normal -5.00207e-17 -4.30226e-17 1 - outer loop - vertex 1.52672 -0.343855 1.29052e-17 - vertex 1.44363 -0.180775 1.57651e-17 - vertex 1.36279 -0.207041 1.05914e-17 - endloop - endfacet - facet normal -5.32946e-17 -3.29449e-17 1 - outer loop - vertex 1.36279 -0.207041 1.05914e-17 - vertex 1.28195 -0.233308 5.4177e-18 - vertex 1.38919 -0.443778 4.19911e-18 - endloop - endfacet - facet normal -5.32948e-17 -3.29449e-17 1 - outer loop - vertex 1.38919 -0.443778 4.19911e-18 - vertex 1.28195 -0.233308 5.4177e-18 - vertex 1.20111 -0.259574 2.44018e-19 - endloop - endfacet - facet normal -5.53653e-17 -2.65716e-17 1 - outer loop - vertex 1.20111 -0.259574 2.44018e-19 - vertex 1.12027 -0.285841 -4.92967e-18 - vertex 1.25166 -0.543702 -4.50701e-18 - endloop - endfacet - facet normal -3.21971e-17 -4.28108e-17 1 - outer loop - vertex 1.52672 -0.343855 1.29052e-17 - vertex 1.59549 -0.293893 1.72583e-17 - vertex 1.52447 -0.154509 2.09388e-17 - endloop - endfacet - facet normal -4.04124e-17 -3.151e-17 1 - outer loop - vertex 1.36279 -0.207041 1.05914e-17 - vertex 1.45796 -0.393816 8.55217e-18 - vertex 1.52672 -0.343855 1.29052e-17 - endloop - endfacet - facet normal -4.04081e-17 -3.15078e-17 1 - outer loop - vertex 1.38919 -0.443778 4.19911e-18 - vertex 1.45796 -0.393816 8.55217e-18 - vertex 1.36279 -0.207041 1.05914e-17 - endloop - endfacet - facet normal -4.53007e-17 -2.47826e-17 1 - outer loop - vertex 1.20111 -0.259574 2.44018e-19 - vertex 1.32043 -0.49374 -1.53951e-19 - vertex 1.38919 -0.443778 4.19911e-18 - endloop - endfacet - facet normal -4.52958e-17 -2.47801e-17 1 - outer loop - vertex 1.25166 -0.543702 -4.50701e-18 - vertex 1.32043 -0.49374 -1.53951e-19 - vertex 1.20111 -0.259574 2.44018e-19 - endloop - endfacet - facet normal -2.7364e-17 -4.94632e-17 1 - outer loop - vertex 1.59549 -0.293893 1.72583e-17 - vertex 1.52672 -0.343855 1.29052e-17 - vertex 1.65615 -0.473275 1.00454e-17 - endloop - endfacet - facet normal -3.0877e-17 -4.46333e-17 1 - outer loop - vertex 1.52672 -0.343855 1.29052e-17 - vertex 1.45796 -0.393816 8.55217e-18 - vertex 1.60618 -0.542042 6.51295e-18 - endloop - endfacet - facet normal -3.08743e-17 -4.46305e-17 1 - outer loop - vertex 1.60618 -0.542042 6.51295e-18 - vertex 1.45796 -0.393816 8.55217e-18 - vertex 1.38919 -0.443778 4.19911e-18 - endloop - endfacet - facet normal -3.35958e-17 -4.08915e-17 1 - outer loop - vertex 1.55622 -0.610808 2.98051e-18 - vertex 1.38919 -0.443778 4.19911e-18 - vertex 1.32043 -0.49374 -1.53951e-19 - endloop - endfacet - facet normal -3.57621e-17 -3.79027e-17 1 - outer loop - vertex 1.50626 -0.679575 -5.51921e-19 - vertex 1.32043 -0.49374 -1.53951e-19 - vertex 1.25166 -0.543702 -4.50701e-18 - endloop - endfacet - facet normal -1.69518e-17 -3.90502e-17 1 - outer loop - vertex 1.60618 -0.542042 6.51295e-18 - vertex 1.65615 -0.473275 1.00454e-17 - vertex 1.52672 -0.343855 1.29052e-17 - endloop - endfacet - facet normal -1.04808e-17 -4.37539e-17 1 - outer loop - vertex 1.65615 -0.473275 1.00454e-17 - vertex 1.70611 -0.404509 1.35778e-17 - vertex 1.59549 -0.293893 1.72583e-17 - endloop - endfacet - facet normal -2.55272e-17 -3.28229e-17 1 - outer loop - vertex 1.38919 -0.443778 4.19911e-18 - vertex 1.55622 -0.610808 2.98051e-18 - vertex 1.60618 -0.542042 6.51295e-18 - endloop - endfacet - facet normal -2.85126e-17 -3.06534e-17 1 - outer loop - vertex 1.32043 -0.49374 -1.53951e-19 - vertex 1.50626 -0.679575 -5.51921e-19 - vertex 1.55622 -0.610808 2.98051e-18 - endloop - endfacet - facet normal -3.0949e-17 -2.88837e-17 1 - outer loop - vertex 1.25166 -0.543702 -4.50701e-18 - vertex 1.4563 -0.748341 -4.08435e-18 - vertex 1.50626 -0.679575 -5.51921e-19 - endloop - endfacet - facet normal -6.30334e-18 -4.6788e-17 1 - outer loop - vertex 1.81922 -0.556368 7.18553e-18 - vertex 1.65615 -0.473275 1.00454e-17 - vertex 1.60618 -0.542042 6.51295e-18 - endloop - endfacet - facet normal -6.30367e-18 -4.67887e-17 1 - outer loop - vertex 1.70611 -0.404509 1.35778e-17 - vertex 1.65615 -0.473275 1.00454e-17 - vertex 1.81922 -0.556368 7.18553e-18 - endloop - endfacet - facet normal -1.48769e-17 -4.05607e-17 1 - outer loop - vertex 1.60618 -0.542042 6.51295e-18 - vertex 1.55622 -0.610808 2.98051e-18 - vertex 1.76669 -0.718048 1.76192e-18 - endloop - endfacet - facet normal -1.48766e-17 -4.05601e-17 1 - outer loop - vertex 1.76669 -0.718048 1.76192e-18 - vertex 1.55622 -0.610808 2.98051e-18 - vertex 1.50626 -0.679575 -5.51921e-19 - endloop - endfacet - facet normal -2.02986e-17 -3.66215e-17 1 - outer loop - vertex 1.50626 -0.679575 -5.51921e-19 - vertex 1.4563 -0.748341 -4.08435e-18 - vertex 1.71416 -0.879727 -3.6617e-18 - endloop - endfacet - facet normal -5.29712e-18 -3.18246e-17 1 - outer loop - vertex 1.60618 -0.542042 6.51295e-18 - vertex 1.79296 -0.637208 4.47373e-18 - vertex 1.81922 -0.556368 7.18553e-18 - endloop - endfacet - facet normal 7.99034e-18 -3.6142e-17 1 - outer loop - vertex 1.81922 -0.556368 7.18553e-18 - vertex 1.84549 -0.475528 9.89734e-18 - vertex 1.70611 -0.404509 1.35778e-17 - endloop - endfacet - facet normal -5.29688e-18 -3.18241e-17 1 - outer loop - vertex 1.76669 -0.718048 1.76192e-18 - vertex 1.79296 -0.637208 4.47373e-18 - vertex 1.60618 -0.542042 6.51295e-18 - endloop - endfacet - facet normal -1.32065e-17 -2.92554e-17 1 - outer loop - vertex 1.50626 -0.679575 -5.51921e-19 - vertex 1.74043 -0.798888 -9.4989e-19 - vertex 1.76669 -0.718048 1.76192e-18 - endloop - endfacet - facet normal -1.3206e-17 -2.92543e-17 1 - outer loop - vertex 1.71416 -0.879727 -3.6617e-18 - vertex 1.74043 -0.798888 -9.4989e-19 - vertex 1.50626 -0.679575 -5.51921e-19 - endloop - endfacet - facet normal 9.99244e-18 -3.67912e-17 1 - outer loop - vertex 2 -0.585 4.32569e-18 - vertex 1.81922 -0.556368 7.18553e-18 - vertex 1.79296 -0.637208 4.47373e-18 - endloop - endfacet - facet normal 9.99224e-18 -3.67925e-17 1 - outer loop - vertex 1.84549 -0.475528 9.89734e-18 - vertex 1.81922 -0.556368 7.18553e-18 - vertex 2 -0.585 4.32569e-18 - endloop - endfacet - facet normal -8.54944e-20 -3.35176e-17 1 - outer loop - vertex 1.79296 -0.637208 4.47373e-18 - vertex 1.76669 -0.718048 1.76192e-18 - vertex 2 -0.755 5.43323e-19 - endloop - endfacet - facet normal -8.54923e-20 -3.35176e-17 1 - outer loop - vertex 2 -0.755 5.43323e-19 - vertex 1.76669 -0.718048 1.76192e-18 - vertex 1.74043 -0.798888 -9.4989e-19 - endloop - endfacet - facet normal -6.45938e-18 -3.14467e-17 1 - outer loop - vertex 1.74043 -0.798888 -9.4989e-19 - vertex 1.71416 -0.879727 -3.6617e-18 - vertex 2 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 6.32547e-18 -2.22492e-17 1 - outer loop - vertex 1.79296 -0.637208 4.47373e-18 - vertex 2 -0.67 2.43451e-18 - vertex 2 -0.585 4.32569e-18 - endloop - endfacet - facet normal 2.02963e-17 -2.22492e-17 1 - outer loop - vertex 2 -0.585 4.32569e-18 - vertex 2 -0.5 6.21687e-18 - vertex 1.84549 -0.475528 9.89734e-18 - endloop - endfacet - facet normal 6.32545e-18 -2.22493e-17 1 - outer loop - vertex 2 -0.755 5.43323e-19 - vertex 2 -0.67 2.43451e-18 - vertex 1.79296 -0.637208 4.47373e-18 - endloop - endfacet - facet normal -1.99075e-18 -2.22492e-17 1 - outer loop - vertex 1.74043 -0.798888 -9.4989e-19 - vertex 2 -0.84 -1.34786e-18 - vertex 2 -0.755 5.43323e-19 - endloop - endfacet - facet normal -1.99074e-18 -2.22492e-17 1 - outer loop - vertex 2 -0.925 -3.23904e-18 - vertex 2 -0.84 -1.34786e-18 - vertex 1.74043 -0.798888 -9.4989e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2 -0.585 4.32569e-18 - vertex 2 -0.67 2.43451e-18 - vertex 2.4 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2 -0.5 6.21687e-18 - vertex 2 -0.585 4.32569e-18 - vertex 2.4 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 2 -0.67 2.43451e-18 - vertex 2 -0.755 5.43323e-19 - vertex 2.4 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2 -0.755 5.43323e-19 - vertex 2 -0.84 -1.34786e-18 - vertex 2.4 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2 -0.84 -1.34786e-18 - vertex 2 -0.925 -3.23904e-18 - vertex 2.4 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 2.4 -0.755 5.43323e-19 - vertex 2.4 -0.67 2.43451e-18 - vertex 2 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.67 2.43451e-18 - vertex 2.4 -0.585 4.32569e-18 - vertex 2 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.585 4.32569e-18 - vertex 2.4 -0.5 6.21687e-18 - vertex 2 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.84 -1.34786e-18 - vertex 2.4 -0.755 5.43323e-19 - vertex 2 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.925 -3.23904e-18 - vertex 2.4 -0.84 -1.34786e-18 - vertex 2 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 2.4 -0.67 2.43451e-18 - vertex 2.4 -0.755 5.43323e-19 - vertex 2.8 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.585 4.32569e-18 - vertex 2.4 -0.67 2.43451e-18 - vertex 2.8 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.5 6.21687e-18 - vertex 2.4 -0.585 4.32569e-18 - vertex 2.8 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.755 5.43323e-19 - vertex 2.4 -0.84 -1.34786e-18 - vertex 2.8 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.4 -0.84 -1.34786e-18 - vertex 2.4 -0.925 -3.23904e-18 - vertex 2.8 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.84 -1.34786e-18 - vertex 2.8 -0.755 5.43323e-19 - vertex 2.4 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 2.8 -0.755 5.43323e-19 - vertex 2.8 -0.67 2.43451e-18 - vertex 2.4 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.67 2.43451e-18 - vertex 2.8 -0.585 4.32569e-18 - vertex 2.4 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.585 4.32569e-18 - vertex 2.8 -0.5 6.21687e-18 - vertex 2.4 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.925 -3.23904e-18 - vertex 2.8 -0.84 -1.34786e-18 - vertex 2.4 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.755 5.43323e-19 - vertex 2.8 -0.84 -1.34786e-18 - vertex 3.2 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 2.8 -0.67 2.43451e-18 - vertex 2.8 -0.755 5.43323e-19 - vertex 3.2 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.585 4.32569e-18 - vertex 2.8 -0.67 2.43451e-18 - vertex 3.2 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.5 6.21687e-18 - vertex 2.8 -0.585 4.32569e-18 - vertex 3.2 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 2.8 -0.84 -1.34786e-18 - vertex 2.8 -0.925 -3.23904e-18 - vertex 3.2 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.925 -3.23904e-18 - vertex 3.2 -0.84 -1.34786e-18 - vertex 2.8 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.84 -1.34786e-18 - vertex 3.2 -0.755 5.43323e-19 - vertex 2.8 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 3.2 -0.755 5.43323e-19 - vertex 3.2 -0.67 2.43451e-18 - vertex 2.8 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.67 2.43451e-18 - vertex 3.2 -0.585 4.32569e-18 - vertex 2.8 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.585 4.32569e-18 - vertex 3.2 -0.5 6.21687e-18 - vertex 2.8 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.84 -1.34786e-18 - vertex 3.2 -0.925 -3.23904e-18 - vertex 3.6 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.755 5.43323e-19 - vertex 3.2 -0.84 -1.34786e-18 - vertex 3.6 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 3.2 -0.67 2.43451e-18 - vertex 3.2 -0.755 5.43323e-19 - vertex 3.6 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.585 4.32569e-18 - vertex 3.2 -0.67 2.43451e-18 - vertex 3.6 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.2 -0.5 6.21687e-18 - vertex 3.2 -0.585 4.32569e-18 - vertex 3.6 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.925 -3.23904e-18 - vertex 3.6 -0.84 -1.34786e-18 - vertex 3.2 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.84 -1.34786e-18 - vertex 3.6 -0.755 5.43323e-19 - vertex 3.2 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 3.6 -0.755 5.43323e-19 - vertex 3.6 -0.67 2.43451e-18 - vertex 3.2 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.67 2.43451e-18 - vertex 3.6 -0.585 4.32569e-18 - vertex 3.2 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.585 4.32569e-18 - vertex 3.6 -0.5 6.21687e-18 - vertex 3.2 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.84 -1.34786e-18 - vertex 3.6 -0.925 -3.23904e-18 - vertex 4 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.755 5.43323e-19 - vertex 3.6 -0.84 -1.34786e-18 - vertex 4 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 3.6 -0.67 2.43451e-18 - vertex 3.6 -0.755 5.43323e-19 - vertex 4 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.585 4.32569e-18 - vertex 3.6 -0.67 2.43451e-18 - vertex 4 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 3.6 -0.5 6.21687e-18 - vertex 3.6 -0.585 4.32569e-18 - vertex 4 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.925 -3.23904e-18 - vertex 4 -0.84 -1.34786e-18 - vertex 3.6 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.84 -1.34786e-18 - vertex 4 -0.755 5.43323e-19 - vertex 3.6 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 4 -0.755 5.43323e-19 - vertex 4 -0.67 2.43451e-18 - vertex 3.6 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.67 2.43451e-18 - vertex 4 -0.585 4.32569e-18 - vertex 3.6 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.585 4.32569e-18 - vertex 4 -0.5 6.21687e-18 - vertex 3.6 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.84 -1.34786e-18 - vertex 4 -0.925 -3.23904e-18 - vertex 4.4 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.755 5.43323e-19 - vertex 4 -0.84 -1.34786e-18 - vertex 4.4 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 4 -0.67 2.43451e-18 - vertex 4 -0.755 5.43323e-19 - vertex 4.4 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.585 4.32569e-18 - vertex 4 -0.67 2.43451e-18 - vertex 4.4 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4 -0.5 6.21687e-18 - vertex 4 -0.585 4.32569e-18 - vertex 4.4 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.925 -3.23904e-18 - vertex 4.4 -0.84 -1.34786e-18 - vertex 4 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.84 -1.34786e-18 - vertex 4.4 -0.755 5.43323e-19 - vertex 4 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 4.4 -0.755 5.43323e-19 - vertex 4.4 -0.67 2.43451e-18 - vertex 4 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.67 2.43451e-18 - vertex 4.4 -0.585 4.32569e-18 - vertex 4 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.585 4.32569e-18 - vertex 4.4 -0.5 6.21687e-18 - vertex 4 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.84 -1.34786e-18 - vertex 4.4 -0.925 -3.23904e-18 - vertex 4.8 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.755 5.43323e-19 - vertex 4.4 -0.84 -1.34786e-18 - vertex 4.8 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 4.4 -0.67 2.43451e-18 - vertex 4.4 -0.755 5.43323e-19 - vertex 4.8 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.585 4.32569e-18 - vertex 4.4 -0.67 2.43451e-18 - vertex 4.8 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.4 -0.5 6.21687e-18 - vertex 4.4 -0.585 4.32569e-18 - vertex 4.8 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.925 -3.23904e-18 - vertex 4.8 -0.84 -1.34786e-18 - vertex 4.4 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.84 -1.34786e-18 - vertex 4.8 -0.755 5.43323e-19 - vertex 4.4 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 4.8 -0.755 5.43323e-19 - vertex 4.8 -0.67 2.43451e-18 - vertex 4.4 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.67 2.43451e-18 - vertex 4.8 -0.585 4.32569e-18 - vertex 4.4 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.585 4.32569e-18 - vertex 4.8 -0.5 6.21687e-18 - vertex 4.4 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.84 -1.34786e-18 - vertex 4.8 -0.925 -3.23904e-18 - vertex 5.2 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.755 5.43323e-19 - vertex 4.8 -0.84 -1.34786e-18 - vertex 5.2 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 4.8 -0.67 2.43451e-18 - vertex 4.8 -0.755 5.43323e-19 - vertex 5.2 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.585 4.32569e-18 - vertex 4.8 -0.67 2.43451e-18 - vertex 5.2 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 4.8 -0.5 6.21687e-18 - vertex 4.8 -0.585 4.32569e-18 - vertex 5.2 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.925 -3.23904e-18 - vertex 5.2 -0.84 -1.34786e-18 - vertex 4.8 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.84 -1.34786e-18 - vertex 5.2 -0.755 5.43323e-19 - vertex 4.8 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 5.2 -0.755 5.43323e-19 - vertex 5.2 -0.67 2.43451e-18 - vertex 4.8 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.67 2.43451e-18 - vertex 5.2 -0.585 4.32569e-18 - vertex 4.8 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.585 4.32569e-18 - vertex 5.2 -0.5 6.21687e-18 - vertex 4.8 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.84 -1.34786e-18 - vertex 5.2 -0.925 -3.23904e-18 - vertex 5.6 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.755 5.43323e-19 - vertex 5.2 -0.84 -1.34786e-18 - vertex 5.6 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 5.2 -0.67 2.43451e-18 - vertex 5.2 -0.755 5.43323e-19 - vertex 5.6 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.585 4.32569e-18 - vertex 5.2 -0.67 2.43451e-18 - vertex 5.6 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.2 -0.5 6.21687e-18 - vertex 5.2 -0.585 4.32569e-18 - vertex 5.6 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.925 -3.23904e-18 - vertex 5.6 -0.84 -1.34786e-18 - vertex 5.2 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.84 -1.34786e-18 - vertex 5.6 -0.755 5.43323e-19 - vertex 5.2 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 5.6 -0.755 5.43323e-19 - vertex 5.6 -0.67 2.43451e-18 - vertex 5.2 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.67 2.43451e-18 - vertex 5.6 -0.585 4.32569e-18 - vertex 5.2 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.585 4.32569e-18 - vertex 5.6 -0.5 6.21687e-18 - vertex 5.2 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.84 -1.34786e-18 - vertex 5.6 -0.925 -3.23904e-18 - vertex 6 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.755 5.43323e-19 - vertex 5.6 -0.84 -1.34786e-18 - vertex 6 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 5.6 -0.67 2.43451e-18 - vertex 5.6 -0.755 5.43323e-19 - vertex 6 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.585 4.32569e-18 - vertex 5.6 -0.67 2.43451e-18 - vertex 6 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 5.6 -0.5 6.21687e-18 - vertex 5.6 -0.585 4.32569e-18 - vertex 6 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 6 -0.925 -3.23904e-18 - vertex 6 -0.84 -1.34786e-18 - vertex 5.6 -0.84 -1.34786e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 6 -0.84 -1.34786e-18 - vertex 6 -0.755 5.43323e-19 - vertex 5.6 -0.755 5.43323e-19 - endloop - endfacet - facet normal 0 -2.22493e-17 1 - outer loop - vertex 6 -0.755 5.43323e-19 - vertex 6 -0.67 2.43451e-18 - vertex 5.6 -0.67 2.43451e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 6 -0.67 2.43451e-18 - vertex 6 -0.585 4.32569e-18 - vertex 5.6 -0.585 4.32569e-18 - endloop - endfacet - facet normal 0 -2.22492e-17 1 - outer loop - vertex 6 -0.585 4.32569e-18 - vertex 6 -0.5 6.21687e-18 - vertex 5.6 -0.5 6.21687e-18 - endloop - endfacet -endsolid symm1 -solid walls - facet normal -0 0.987687 0.156444 - outer loop - vertex -2 0.925 -4.96308e-24 - vertex -1.6 0.925 -4.96308e-24 - vertex -1.6 0.928671 -0.0231763 - endloop - endfacet - facet normal 0 0.987687 0.156444 - outer loop - vertex -1.2 0.928671 -0.0231763 - vertex -1.6 0.928671 -0.0231763 - vertex -1.6 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 0.987687 0.156444 - outer loop - vertex -1.6 0.928671 -0.0231763 - vertex -2 0.928671 -0.0231763 - vertex -2 0.925 -4.96308e-24 - endloop - endfacet - facet normal -0 0.987687 0.156444 - outer loop - vertex -1.6 0.925 -4.96308e-24 - vertex -1.2 0.925 -4.96308e-24 - vertex -1.2 0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.891005 0.453993 - outer loop - vertex -1.6 0.928671 -0.0231763 - vertex -1.2 0.928671 -0.0231763 - vertex -1.2 0.939324 -0.0440839 - endloop - endfacet - facet normal -0 0.891005 0.453993 - outer loop - vertex -2 0.928671 -0.0231763 - vertex -1.6 0.928671 -0.0231763 - vertex -1.6 0.939324 -0.0440839 - endloop - endfacet - facet normal 0 0.987687 0.156444 - outer loop - vertex -0.8 0.928671 -0.0231763 - vertex -1.2 0.928671 -0.0231763 - vertex -1.2 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 0.891005 0.453993 - outer loop - vertex -0.8 0.939324 -0.0440839 - vertex -1.2 0.939324 -0.0440839 - vertex -1.2 0.928671 -0.0231763 - endloop - endfacet - facet normal 0 0.891005 0.453993 - outer loop - vertex -1.2 0.939324 -0.0440839 - vertex -1.6 0.939324 -0.0440839 - vertex -1.6 0.928671 -0.0231763 - endloop - endfacet - facet normal 0 0.891005 0.453993 - outer loop - vertex -1.6 0.939324 -0.0440839 - vertex -2 0.939324 -0.0440839 - vertex -2 0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987687 0.156444 - outer loop - vertex -1.2 0.925 -4.96308e-24 - vertex -0.8 0.925 -4.96308e-24 - vertex -0.8 0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.891005 0.453993 - outer loop - vertex -1.2 0.928671 -0.0231763 - vertex -0.8 0.928671 -0.0231763 - vertex -0.8 0.939324 -0.0440839 - endloop - endfacet - facet normal -0 0.707116 0.707098 - outer loop - vertex -1.2 0.939324 -0.0440839 - vertex -0.8 0.939324 -0.0440839 - vertex -0.8 0.955916 -0.0606763 - endloop - endfacet - facet normal -0 0.707116 0.707098 - outer loop - vertex -1.6 0.939324 -0.0440839 - vertex -1.2 0.939324 -0.0440839 - vertex -1.2 0.955916 -0.0606763 - endloop - endfacet - facet normal -0 0.707116 0.707098 - outer loop - vertex -2 0.939324 -0.0440839 - vertex -1.6 0.939324 -0.0440839 - vertex -1.6 0.955916 -0.0606763 - endloop - endfacet - facet normal 0 0.987687 0.156444 - outer loop - vertex -0.4 0.928671 -0.0231763 - vertex -0.8 0.928671 -0.0231763 - vertex -0.8 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 0.891005 0.453993 - outer loop - vertex -0.4 0.939324 -0.0440839 - vertex -0.8 0.939324 -0.0440839 - vertex -0.8 0.928671 -0.0231763 - endloop - endfacet - facet normal 0 0.707116 0.707098 - outer loop - vertex -0.4 0.955916 -0.0606763 - vertex -0.8 0.955916 -0.0606763 - vertex -0.8 0.939324 -0.0440839 - endloop - endfacet - facet normal 0 0.707116 0.707098 - outer loop - vertex -0.8 0.955916 -0.0606763 - vertex -1.2 0.955916 -0.0606763 - vertex -1.2 0.939324 -0.0440839 - endloop - endfacet - facet normal 0 0.707116 0.707098 - outer loop - vertex -1.2 0.955916 -0.0606763 - vertex -1.6 0.955916 -0.0606763 - vertex -1.6 0.939324 -0.0440839 - endloop - endfacet - facet normal 0 0.707116 0.707098 - outer loop - vertex -1.6 0.955916 -0.0606763 - vertex -2 0.955916 -0.0606763 - vertex -2 0.939324 -0.0440839 - endloop - endfacet - facet normal -0 0.987687 0.156444 - outer loop - vertex -0.8 0.925 -4.96308e-24 - vertex -0.4 0.925 -4.96308e-24 - vertex -0.4 0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.891005 0.453993 - outer loop - vertex -0.8 0.928671 -0.0231763 - vertex -0.4 0.928671 -0.0231763 - vertex -0.4 0.939324 -0.0440839 - endloop - endfacet - facet normal -0 0.707116 0.707098 - outer loop - vertex -0.8 0.939324 -0.0440839 - vertex -0.4 0.939324 -0.0440839 - vertex -0.4 0.955916 -0.0606763 - endloop - endfacet - facet normal -0 0.453982 0.891011 - outer loop - vertex -0.8 0.955916 -0.0606763 - vertex -0.4 0.955916 -0.0606763 - vertex -0.4 0.976824 -0.0713292 - endloop - endfacet - facet normal -0 0.453982 0.891011 - outer loop - vertex -1.2 0.955916 -0.0606763 - vertex -0.8 0.955916 -0.0606763 - vertex -0.8 0.976824 -0.0713292 - endloop - endfacet - facet normal -0 0.453982 0.891011 - outer loop - vertex -1.6 0.955916 -0.0606763 - vertex -1.2 0.955916 -0.0606763 - vertex -1.2 0.976824 -0.0713292 - endloop - endfacet - facet normal -0 0.453982 0.891011 - outer loop - vertex -2 0.955916 -0.0606763 - vertex -1.6 0.955916 -0.0606763 - vertex -1.6 0.976824 -0.0713292 - endloop - endfacet - facet normal 0 0.987687 0.156444 - outer loop - vertex 7.94093e-24 0.928671 -0.0231763 - vertex -0.4 0.928671 -0.0231763 - vertex -0.4 0.925 -4.96308e-24 - endloop - endfacet - facet normal 0 0.891005 0.453993 - outer loop - vertex 2.64698e-24 0.939324 -0.0440839 - vertex -0.4 0.939324 -0.0440839 - vertex -0.4 0.928671 -0.0231763 - endloop - endfacet - facet normal 0 0.707116 0.707098 - outer loop - vertex -2.64698e-24 0.955916 -0.0606763 - vertex -0.4 0.955916 -0.0606763 - vertex -0.4 0.939324 -0.0440839 - endloop - endfacet - facet normal 0 0.453982 0.891011 - outer loop - vertex -7.94093e-24 0.976824 -0.0713292 - vertex -0.4 0.976824 -0.0713292 - vertex -0.4 0.955916 -0.0606763 - endloop - endfacet - facet normal 0 0.453982 0.891011 - outer loop - vertex -0.4 0.976824 -0.0713292 - vertex -0.8 0.976824 -0.0713292 - vertex -0.8 0.955916 -0.0606763 - endloop - endfacet - facet normal 0 0.453982 0.891011 - outer loop - vertex -0.8 0.976824 -0.0713292 - vertex -1.2 0.976824 -0.0713292 - vertex -1.2 0.955916 -0.0606763 - endloop - endfacet - facet normal 0 0.453982 0.891011 - outer loop - vertex -1.2 0.976824 -0.0713292 - vertex -1.6 0.976824 -0.0713292 - vertex -1.6 0.955916 -0.0606763 - endloop - endfacet - facet normal 0 0.453982 0.891011 - outer loop - vertex -1.6 0.976824 -0.0713292 - vertex -2 0.976824 -0.0713292 - vertex -2 0.955916 -0.0606763 - endloop - endfacet - facet normal -0 0.987687 0.156444 - outer loop - vertex -0.4 0.925 -4.96308e-24 - vertex 1.32349e-23 0.925 -4.96308e-24 - vertex 7.94093e-24 0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.891005 0.453993 - outer loop - vertex -0.4 0.928671 -0.0231763 - vertex 7.94093e-24 0.928671 -0.0231763 - vertex 2.64698e-24 0.939324 -0.0440839 - endloop - endfacet - facet normal -0 0.707116 0.707098 - outer loop - vertex -0.4 0.939324 -0.0440839 - vertex 2.64698e-24 0.939324 -0.0440839 - vertex -2.64698e-24 0.955916 -0.0606763 - endloop - endfacet - facet normal -0 0.453982 0.891011 - outer loop - vertex -0.4 0.955916 -0.0606763 - vertex -2.64698e-24 0.955916 -0.0606763 - vertex -7.94093e-24 0.976824 -0.0713292 - endloop - endfacet - facet normal -0 0.156438 0.987688 - outer loop - vertex -0.4 0.976824 -0.0713292 - vertex -7.94093e-24 0.976824 -0.0713292 - vertex -1.32349e-23 1 -0.075 - endloop - endfacet - facet normal -0 0.156438 0.987688 - outer loop - vertex -0.8 0.976824 -0.0713292 - vertex -0.4 0.976824 -0.0713292 - vertex -0.4 1 -0.075 - endloop - endfacet - facet normal -0 0.156438 0.987688 - outer loop - vertex -1.2 0.976824 -0.0713292 - vertex -0.8 0.976824 -0.0713292 - vertex -0.8 1 -0.075 - endloop - endfacet - facet normal -0 0.156438 0.987688 - outer loop - vertex -1.6 0.976824 -0.0713292 - vertex -1.2 0.976824 -0.0713292 - vertex -1.2 1 -0.075 - endloop - endfacet - facet normal -0 0.156438 0.987688 - outer loop - vertex -2 0.976824 -0.0713292 - vertex -1.6 0.976824 -0.0713292 - vertex -1.6 1 -0.075 - endloop - endfacet - facet normal 0.154555 0.975819 0.154564 - outer loop - vertex 7.94093e-24 0.928671 -0.0231763 - vertex 1.32349e-23 0.925 -4.96308e-24 - vertex 0.285841 0.879727 -5.9557e-24 - endloop - endfacet - facet normal 0.134006 0.882969 0.449898 - outer loop - vertex 2.64698e-24 0.939324 -0.0440839 - vertex 7.94093e-24 0.928671 -0.0231763 - vertex 0.28821 0.88493 -0.0231763 - endloop - endfacet - facet normal 0.105022 0.703206 0.703187 - outer loop - vertex -2.64698e-24 0.955916 -0.0606763 - vertex 2.64698e-24 0.939324 -0.0440839 - vertex 0.291976 0.895718 -0.0440839 - endloop - endfacet - facet normal 0.0696702 0.452879 0.888846 - outer loop - vertex 0.302746 0.93025 -0.0713292 - vertex -7.94093e-24 0.976824 -0.0713292 - vertex -2.64698e-24 0.955916 -0.0606763 - endloop - endfacet - facet normal 0.0247695 0.15639 0.987385 - outer loop - vertex 0.309017 0.951057 -0.075 - vertex -1.32349e-23 1 -0.075 - vertex -7.94093e-24 0.976824 -0.0713292 - endloop - endfacet - facet normal 0 0.156438 0.987688 - outer loop - vertex -1.32349e-23 1 -0.075 - vertex -0.4 1 -0.075 - vertex -0.4 0.976824 -0.0713292 - endloop - endfacet - facet normal 0 0.156438 0.987688 - outer loop - vertex -0.4 1 -0.075 - vertex -0.8 1 -0.075 - vertex -0.8 0.976824 -0.0713292 - endloop - endfacet - facet normal 0 0.156438 0.987688 - outer loop - vertex -0.8 1 -0.075 - vertex -1.2 1 -0.075 - vertex -1.2 0.976824 -0.0713292 - endloop - endfacet - facet normal 0 0.156438 0.987688 - outer loop - vertex -1.2 1 -0.075 - vertex -1.6 1 -0.075 - vertex -1.6 0.976824 -0.0713292 - endloop - endfacet - facet normal 0 0.156438 0.987688 - outer loop - vertex -1.6 1 -0.075 - vertex -2 1 -0.075 - vertex -2 0.976824 -0.0713292 - endloop - endfacet - facet normal 0.145995 0.961966 0.230882 - outer loop - vertex 0.285841 0.879727 -5.9557e-24 - vertex 0.28821 0.88493 -0.0231763 - vertex 7.94093e-24 0.928671 -0.0231763 - endloop - endfacet - facet normal 0.130137 0.87137 0.473053 - outer loop - vertex 0.28821 0.88493 -0.0231763 - vertex 0.291976 0.895718 -0.0440839 - vertex 2.64698e-24 0.939324 -0.0440839 - endloop - endfacet - facet normal 0.106725 0.709609 0.696466 - outer loop - vertex 0.291976 0.895718 -0.0440839 - vertex 0.29693 0.911258 -0.0606763 - vertex -2.64698e-24 0.955916 -0.0606763 - endloop - endfacet - facet normal 0.0708947 0.471377 0.879078 - outer loop - vertex -2.64698e-24 0.955916 -0.0606763 - vertex 0.29693 0.911258 -0.0606763 - vertex 0.302746 0.93025 -0.0713292 - endloop - endfacet - facet normal 0.0255684 0.166203 0.98576 - outer loop - vertex -7.94093e-24 0.976824 -0.0713292 - vertex 0.302746 0.93025 -0.0713292 - vertex 0.309017 0.951057 -0.075 - endloop - endfacet - facet normal -0.026291 -0.165997 0.985776 - outer loop - vertex -1.32349e-23 1 -0.075 - vertex 0.309017 0.951057 -0.075 - vertex 0.315288 0.971863 -0.0713292 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -0.4 1.02318 -0.0713292 - vertex -0.4 1 -0.075 - vertex -1.32349e-23 1 -0.075 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -0.8 1.02318 -0.0713292 - vertex -0.8 1 -0.075 - vertex -0.4 1 -0.075 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -1.2 1.02318 -0.0713292 - vertex -1.2 1 -0.075 - vertex -0.8 1 -0.075 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -1.6 1.02318 -0.0713292 - vertex -1.6 1 -0.075 - vertex -1.2 1 -0.075 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -2 1.02318 -0.0713292 - vertex -2 1 -0.075 - vertex -1.6 1 -0.075 - endloop - endfacet - facet normal 0.440802 0.865125 0.239275 - outer loop - vertex 0.28821 0.88493 -0.0231763 - vertex 0.285841 0.879727 -5.9557e-24 - vertex 0.543701 0.748341 -6.94832e-24 - endloop - endfacet - facet normal 0.396508 0.784774 0.476351 - outer loop - vertex 0.291976 0.895718 -0.0440839 - vertex 0.28821 0.88493 -0.0231763 - vertex 0.547986 0.753678 -0.0231763 - endloop - endfacet - facet normal 0.322769 0.640818 0.696543 - outer loop - vertex 0.29693 0.911258 -0.0606763 - vertex 0.291976 0.895718 -0.0440839 - vertex 0.555064 0.763205 -0.0440839 - endloop - endfacet - facet normal 0.216056 0.426492 0.878308 - outer loop - vertex 0.575698 0.791976 -0.0713292 - vertex 0.302746 0.93025 -0.0713292 - vertex 0.29693 0.911258 -0.0606763 - endloop - endfacet - facet normal 0.0768018 0.150731 0.985587 - outer loop - vertex 0.587785 0.809017 -0.075 - vertex 0.309017 0.951057 -0.075 - vertex 0.302746 0.93025 -0.0713292 - endloop - endfacet - facet normal -0.0771718 -0.150625 0.985574 - outer loop - vertex 0.599873 0.826058 -0.0713292 - vertex 0.315288 0.971863 -0.0713292 - vertex 0.309017 0.951057 -0.075 - endloop - endfacet - facet normal -0.0254497 -0.156361 0.987372 - outer loop - vertex 0.315288 0.971863 -0.0713292 - vertex -1.19114e-23 1.02318 -0.0713292 - vertex -1.32349e-23 1 -0.075 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -0.4 1 -0.075 - vertex -0.4 1.02318 -0.0713292 - vertex -0.8 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -1.32349e-23 1 -0.075 - vertex -1.19114e-23 1.02318 -0.0713292 - vertex -0.4 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -0.8 1 -0.075 - vertex -0.8 1.02318 -0.0713292 - vertex -1.2 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -1.2 1 -0.075 - vertex -1.2 1.02318 -0.0713292 - vertex -1.6 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.156412 0.987692 - outer loop - vertex -1.6 1 -0.075 - vertex -1.6 1.02318 -0.0713292 - vertex -2 1.02318 -0.0713292 - endloop - endfacet - facet normal 0.43324 0.857476 0.277558 - outer loop - vertex 0.543701 0.748341 -6.94832e-24 - vertex 0.547986 0.753678 -0.0231763 - vertex 0.28821 0.88493 -0.0231763 - endloop - endfacet - facet normal 0.392616 0.77949 0.488106 - outer loop - vertex 0.547986 0.753678 -0.0231763 - vertex 0.555064 0.763205 -0.0440839 - vertex 0.291976 0.895718 -0.0440839 - endloop - endfacet - facet normal 0.324693 0.643767 0.69292 - outer loop - vertex 0.555064 0.763205 -0.0440839 - vertex 0.564518 0.776296 -0.0606763 - vertex 0.29693 0.911258 -0.0606763 - endloop - endfacet - facet normal 0.219929 0.436051 0.872634 - outer loop - vertex 0.29693 0.911258 -0.0606763 - vertex 0.564518 0.776296 -0.0606763 - vertex 0.575698 0.791976 -0.0713292 - endloop - endfacet - facet normal 0.079041 0.156027 0.984585 - outer loop - vertex 0.302746 0.93025 -0.0713292 - vertex 0.575698 0.791976 -0.0713292 - vertex 0.587785 0.809017 -0.075 - endloop - endfacet - facet normal -0.0793774 -0.155786 0.984596 - outer loop - vertex 0.309017 0.951057 -0.075 - vertex 0.587785 0.809017 -0.075 - vertex 0.599873 0.826058 -0.0713292 - endloop - endfacet - facet normal -0.222531 -0.434341 0.872827 - outer loop - vertex 0.315288 0.971863 -0.0713292 - vertex 0.599873 0.826058 -0.0713292 - vertex 0.611052 0.841738 -0.0606763 - endloop - endfacet - facet normal -0.0764763 -0.469865 0.879419 - outer loop - vertex -1.19114e-23 1.02318 -0.0713292 - vertex 0.315288 0.971863 -0.0713292 - vertex 0.321104 0.990855 -0.0606762 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -0.8 1.04408 -0.0606762 - vertex -0.8 1.02318 -0.0713292 - vertex -0.4 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -0.4 1.04408 -0.0606762 - vertex -0.4 1.02318 -0.0713292 - vertex -1.19114e-23 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -1.2 1.04408 -0.0606762 - vertex -1.2 1.02318 -0.0713292 - vertex -0.8 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -1.6 1.04408 -0.0606762 - vertex -1.6 1.02318 -0.0713292 - vertex -1.2 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -2 1.04408 -0.0606762 - vertex -2 1.02318 -0.0713292 - vertex -1.6 1.02318 -0.0713292 - endloop - endfacet - facet normal 0.678475 0.678475 0.281679 - outer loop - vertex 0.753678 0.547986 -0.0231763 - vertex 0.547986 0.753678 -0.0231763 - vertex 0.543701 0.748341 -6.94832e-24 - endloop - endfacet - facet normal 0.616536 0.616536 0.489659 - outer loop - vertex 0.763205 0.555064 -0.0440839 - vertex 0.555064 0.763205 -0.0440839 - vertex 0.547986 0.753678 -0.0231763 - endloop - endfacet - facet normal 0.509898 0.509898 0.692826 - outer loop - vertex 0.776296 0.564518 -0.0606763 - vertex 0.564518 0.776296 -0.0606763 - vertex 0.555064 0.763205 -0.0440839 - endloop - endfacet - facet normal 0.345912 0.345912 0.872175 - outer loop - vertex 0.791976 0.575698 -0.0713292 - vertex 0.575698 0.791976 -0.0713292 - vertex 0.564518 0.776296 -0.0606763 - endloop - endfacet - facet normal 0.124068 0.124068 0.984487 - outer loop - vertex 0.809017 0.587785 -0.075 - vertex 0.587785 0.809017 -0.075 - vertex 0.575698 0.791976 -0.0713292 - endloop - endfacet - facet normal -0.124064 -0.124064 0.984488 - outer loop - vertex 0.826058 0.599873 -0.0713292 - vertex 0.599873 0.826058 -0.0713292 - vertex 0.587785 0.809017 -0.075 - endloop - endfacet - facet normal -0.345922 -0.345922 0.872167 - outer loop - vertex 0.841738 0.611052 -0.0606763 - vertex 0.611052 0.841738 -0.0606763 - vertex 0.599873 0.826058 -0.0713292 - endloop - endfacet - facet normal -0.218841 -0.425522 0.878089 - outer loop - vertex 0.611052 0.841738 -0.0606763 - vertex 0.321104 0.990855 -0.0606762 - vertex 0.315288 0.971863 -0.0713292 - endloop - endfacet - facet normal -0.0750614 -0.452842 0.888426 - outer loop - vertex 0.321104 0.990855 -0.0606762 - vertex -1.05879e-23 1.04408 -0.0606762 - vertex -1.19114e-23 1.02318 -0.0713292 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -0.8 1.02318 -0.0713292 - vertex -0.8 1.04408 -0.0606762 - vertex -1.2 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -0.4 1.02318 -0.0713292 - vertex -0.4 1.04408 -0.0606762 - vertex -0.8 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -1.19114e-23 1.02318 -0.0713292 - vertex -1.05879e-23 1.04408 -0.0606762 - vertex -0.4 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -1.2 1.02318 -0.0713292 - vertex -1.2 1.04408 -0.0606762 - vertex -1.6 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.454123 0.890939 - outer loop - vertex -1.6 1.02318 -0.0713292 - vertex -1.6 1.04408 -0.0606762 - vertex -2 1.04408 -0.0606762 - endloop - endfacet - facet normal 0.678475 0.678475 0.281679 - outer loop - vertex 0.543701 0.748341 -6.94832e-24 - vertex 0.748341 0.543701 -7.94093e-24 - vertex 0.753678 0.547986 -0.0231763 - endloop - endfacet - facet normal 0.616536 0.616536 0.489659 - outer loop - vertex 0.547986 0.753678 -0.0231763 - vertex 0.753678 0.547986 -0.0231763 - vertex 0.763205 0.555064 -0.0440839 - endloop - endfacet - facet normal 0.509898 0.509898 0.692826 - outer loop - vertex 0.555064 0.763205 -0.0440839 - vertex 0.763205 0.555064 -0.0440839 - vertex 0.776296 0.564518 -0.0606763 - endloop - endfacet - facet normal 0.345912 0.345912 0.872175 - outer loop - vertex 0.564518 0.776296 -0.0606763 - vertex 0.776296 0.564518 -0.0606763 - vertex 0.791976 0.575698 -0.0713292 - endloop - endfacet - facet normal 0.124068 0.124068 0.984487 - outer loop - vertex 0.575698 0.791976 -0.0713292 - vertex 0.791976 0.575698 -0.0713292 - vertex 0.809017 0.587785 -0.075 - endloop - endfacet - facet normal -0.124064 -0.124064 0.984488 - outer loop - vertex 0.587785 0.809017 -0.075 - vertex 0.809017 0.587785 -0.075 - vertex 0.826058 0.599873 -0.0713292 - endloop - endfacet - facet normal -0.345922 -0.345922 0.872167 - outer loop - vertex 0.599873 0.826058 -0.0713292 - vertex 0.826058 0.599873 -0.0713292 - vertex 0.841738 0.611052 -0.0606763 - endloop - endfacet - facet normal -0.509898 -0.509898 0.692827 - outer loop - vertex 0.611052 0.841738 -0.0606763 - vertex 0.841738 0.611052 -0.0606763 - vertex 0.854829 0.620506 -0.0440839 - endloop - endfacet - facet normal -0.329561 -0.64081 0.693362 - outer loop - vertex 0.321104 0.990855 -0.0606762 - vertex 0.611052 0.841738 -0.0606763 - vertex 0.620506 0.854829 -0.0440839 - endloop - endfacet - facet normal -0.117196 -0.707035 0.6974 - outer loop - vertex -1.05879e-23 1.04408 -0.0606762 - vertex 0.321104 0.990855 -0.0606762 - vertex 0.326058 1.0064 -0.0440839 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -1.2 1.06068 -0.0440838 - vertex -1.2 1.04408 -0.0606762 - vertex -0.8 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -0.8 1.06068 -0.0440838 - vertex -0.8 1.04408 -0.0606762 - vertex -0.4 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -0.4 1.06068 -0.0440838 - vertex -0.4 1.04408 -0.0606762 - vertex -1.05879e-23 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -1.6 1.06068 -0.0440838 - vertex -1.6 1.04408 -0.0606762 - vertex -1.2 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -2 1.06068 -0.0440838 - vertex -2 1.04408 -0.0606762 - vertex -1.6 1.04408 -0.0606762 - endloop - endfacet - facet normal 0.857476 0.43324 0.277558 - outer loop - vertex 0.88493 0.28821 -0.0231763 - vertex 0.753678 0.547986 -0.0231763 - vertex 0.748341 0.543701 -7.94093e-24 - endloop - endfacet - facet normal 0.77949 0.392616 0.488106 - outer loop - vertex 0.895718 0.291976 -0.0440839 - vertex 0.763205 0.555064 -0.0440839 - vertex 0.753678 0.547986 -0.0231763 - endloop - endfacet - facet normal 0.643767 0.324693 0.69292 - outer loop - vertex 0.911258 0.29693 -0.0606763 - vertex 0.776296 0.564518 -0.0606763 - vertex 0.763205 0.555064 -0.0440839 - endloop - endfacet - facet normal 0.436051 0.219929 0.872634 - outer loop - vertex 0.791976 0.575698 -0.0713292 - vertex 0.776296 0.564518 -0.0606763 - vertex 0.911258 0.29693 -0.0606763 - endloop - endfacet - facet normal 0.156027 0.079041 0.984585 - outer loop - vertex 0.809017 0.587785 -0.075 - vertex 0.791976 0.575698 -0.0713292 - vertex 0.93025 0.302746 -0.0713292 - endloop - endfacet - facet normal -0.155786 -0.0793774 0.984596 - outer loop - vertex 0.826058 0.599873 -0.0713292 - vertex 0.809017 0.587785 -0.075 - vertex 0.951057 0.309017 -0.075 - endloop - endfacet - facet normal -0.434341 -0.222532 0.872827 - outer loop - vertex 0.841738 0.611052 -0.0606763 - vertex 0.826058 0.599873 -0.0713292 - vertex 0.971863 0.315288 -0.0713293 - endloop - endfacet - facet normal -0.64081 -0.329562 0.693362 - outer loop - vertex 0.854829 0.620506 -0.0440839 - vertex 0.841738 0.611052 -0.0606763 - vertex 0.990855 0.321104 -0.0606763 - endloop - endfacet - facet normal -0.509898 -0.509898 0.692827 - outer loop - vertex 0.854829 0.620506 -0.0440839 - vertex 0.620506 0.854829 -0.0440839 - vertex 0.611052 0.841738 -0.0606763 - endloop - endfacet - facet normal -0.328579 -0.638312 0.696127 - outer loop - vertex 0.620506 0.854829 -0.0440839 - vertex 0.326058 1.0064 -0.0440839 - vertex 0.321104 0.990855 -0.0606762 - endloop - endfacet - facet normal -0.116881 -0.702099 0.702421 - outer loop - vertex 0.326058 1.0064 -0.0440839 - vertex -9.26442e-24 1.06068 -0.0440838 - vertex -1.05879e-23 1.04408 -0.0606762 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -1.2 1.04408 -0.0606762 - vertex -1.2 1.06068 -0.0440838 - vertex -1.6 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -0.8 1.04408 -0.0606762 - vertex -0.8 1.06068 -0.0440838 - vertex -1.2 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -0.4 1.04408 -0.0606762 - vertex -0.4 1.06068 -0.0440838 - vertex -0.8 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -1.05879e-23 1.04408 -0.0606762 - vertex -9.26442e-24 1.06068 -0.0440838 - vertex -0.4 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.706945 0.707269 - outer loop - vertex -1.6 1.04408 -0.0606762 - vertex -1.6 1.06068 -0.0440838 - vertex -2 1.06068 -0.0440838 - endloop - endfacet - facet normal 0.865125 0.440802 0.239275 - outer loop - vertex 0.748341 0.543701 -7.94093e-24 - vertex 0.879727 0.285841 -8.93355e-24 - vertex 0.88493 0.28821 -0.0231763 - endloop - endfacet - facet normal 0.784774 0.396508 0.476351 - outer loop - vertex 0.753678 0.547986 -0.0231763 - vertex 0.88493 0.28821 -0.0231763 - vertex 0.895718 0.291976 -0.0440839 - endloop - endfacet - facet normal 0.640818 0.322769 0.696543 - outer loop - vertex 0.763205 0.555064 -0.0440839 - vertex 0.895718 0.291976 -0.0440839 - vertex 0.911258 0.29693 -0.0606763 - endloop - endfacet - facet normal 0.426492 0.216056 0.878308 - outer loop - vertex 0.911258 0.29693 -0.0606763 - vertex 0.93025 0.302746 -0.0713292 - vertex 0.791976 0.575698 -0.0713292 - endloop - endfacet - facet normal 0.150731 0.0768018 0.985587 - outer loop - vertex 0.93025 0.302746 -0.0713292 - vertex 0.951057 0.309017 -0.075 - vertex 0.809017 0.587785 -0.075 - endloop - endfacet - facet normal -0.150621 -0.07717 0.985575 - outer loop - vertex 0.951057 0.309017 -0.075 - vertex 0.971863 0.315288 -0.0713293 - vertex 0.826058 0.599873 -0.0713292 - endloop - endfacet - facet normal -0.425522 -0.218841 0.878089 - outer loop - vertex 0.971863 0.315288 -0.0713293 - vertex 0.990855 0.321104 -0.0606763 - vertex 0.841738 0.611052 -0.0606763 - endloop - endfacet - facet normal -0.638314 -0.32858 0.696125 - outer loop - vertex 0.990855 0.321104 -0.0606763 - vertex 1.0064 0.326058 -0.0440839 - vertex 0.854829 0.620506 -0.0440839 - endloop - endfacet - facet normal -0.616537 -0.616537 0.489658 - outer loop - vertex 0.620506 0.854829 -0.0440839 - vertex 0.854829 0.620506 -0.0440839 - vertex 0.864356 0.627584 -0.0231763 - endloop - endfacet - facet normal -0.402572 -0.782053 0.475741 - outer loop - vertex 0.329824 1.01718 -0.0231763 - vertex 0.326058 1.0064 -0.0440839 - vertex 0.620506 0.854829 -0.0440839 - endloop - endfacet - facet normal -0.146732 -0.881413 0.448977 - outer loop - vertex -7.94093e-24 1.07133 -0.0231763 - vertex -9.26442e-24 1.06068 -0.0440838 - vertex 0.326058 1.0064 -0.0440839 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -1.6 1.07133 -0.0231763 - vertex -1.6 1.06068 -0.0440838 - vertex -1.2 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -1.2 1.07133 -0.0231763 - vertex -1.2 1.06068 -0.0440838 - vertex -0.8 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -0.8 1.07133 -0.0231763 - vertex -0.8 1.06068 -0.0440838 - vertex -0.4 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -0.4 1.07133 -0.0231763 - vertex -0.4 1.06068 -0.0440838 - vertex -9.26442e-24 1.06068 -0.0440838 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -2 1.07133 -0.0231763 - vertex -2 1.06068 -0.0440838 - vertex -1.6 1.06068 -0.0440838 - endloop - endfacet - facet normal 0.961966 0.145995 0.230882 - outer loop - vertex 0.928671 8.47033e-23 -0.0231763 - vertex 0.88493 0.28821 -0.0231763 - vertex 0.879727 0.285841 -8.93355e-24 - endloop - endfacet - facet normal 0.87137 0.130137 0.473053 - outer loop - vertex 0.939324 6.35275e-23 -0.0440839 - vertex 0.895718 0.291976 -0.0440839 - vertex 0.88493 0.28821 -0.0231763 - endloop - endfacet - facet normal 0.709609 0.106725 0.696466 - outer loop - vertex 0.955916 4.23516e-23 -0.0606763 - vertex 0.911258 0.29693 -0.0606763 - vertex 0.895718 0.291976 -0.0440839 - endloop - endfacet - facet normal 0.471377 0.0708947 0.879078 - outer loop - vertex 0.93025 0.302746 -0.0713292 - vertex 0.911258 0.29693 -0.0606763 - vertex 0.955916 4.23516e-23 -0.0606763 - endloop - endfacet - facet normal 0.166203 0.0255684 0.98576 - outer loop - vertex 0.951057 0.309017 -0.075 - vertex 0.93025 0.302746 -0.0713292 - vertex 0.976824 2.11758e-23 -0.0713292 - endloop - endfacet - facet normal -0.165992 -0.0262903 0.985777 - outer loop - vertex 0.971863 0.315288 -0.0713293 - vertex 0.951057 0.309017 -0.075 - vertex 1 0 -0.075 - endloop - endfacet - facet normal -0.469865 -0.0764763 0.879419 - outer loop - vertex 0.990855 0.321104 -0.0606763 - vertex 0.971863 0.315288 -0.0713293 - vertex 1.02318 4.23516e-23 -0.0713293 - endloop - endfacet - facet normal -0.782053 -0.402572 0.475741 - outer loop - vertex 0.854829 0.620506 -0.0440839 - vertex 1.0064 0.326058 -0.0440839 - vertex 1.01718 0.329824 -0.0231763 - endloop - endfacet - facet normal -0.707037 -0.117196 0.697397 - outer loop - vertex 1.0064 0.326058 -0.0440839 - vertex 0.990855 0.321104 -0.0606763 - vertex 1.04408 8.47033e-23 -0.0606763 - endloop - endfacet - facet normal -0.776246 -0.398405 0.488586 - outer loop - vertex 1.01718 0.329824 -0.0231763 - vertex 0.864356 0.627584 -0.0231763 - vertex 0.854829 0.620506 -0.0440839 - endloop - endfacet - facet normal -0.616537 -0.616537 0.489658 - outer loop - vertex 0.864356 0.627584 -0.0231763 - vertex 0.627584 0.864356 -0.0231763 - vertex 0.620506 0.854829 -0.0440839 - endloop - endfacet - facet normal -0.142674 -0.869017 0.473765 - outer loop - vertex 0.326058 1.0064 -0.0440839 - vertex 0.329824 1.01718 -0.0231763 - vertex -7.94093e-24 1.07133 -0.0231763 - endloop - endfacet - facet normal -0.398405 -0.776246 0.488586 - outer loop - vertex 0.620506 0.854829 -0.0440839 - vertex 0.627584 0.864356 -0.0231763 - vertex 0.329824 1.01718 -0.0231763 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -9.26442e-24 1.06068 -0.0440838 - vertex -7.94093e-24 1.07133 -0.0231763 - vertex -0.4 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -1.6 1.06068 -0.0440838 - vertex -1.6 1.07133 -0.0231763 - vertex -2 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -1.2 1.06068 -0.0440838 - vertex -1.2 1.07133 -0.0231763 - vertex -1.6 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -0.8 1.06068 -0.0440838 - vertex -0.8 1.07133 -0.0231763 - vertex -1.2 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.891058 0.45389 - outer loop - vertex -0.4 1.06068 -0.0440838 - vertex -0.4 1.07133 -0.0231763 - vertex -0.8 1.07133 -0.0231763 - endloop - endfacet - facet normal 0.975819 0.154555 0.154564 - outer loop - vertex 0.879727 0.285841 -8.93355e-24 - vertex 0.925 1.05879e-22 -9.92617e-24 - vertex 0.928671 8.47033e-23 -0.0231763 - endloop - endfacet - facet normal 0.882969 0.134006 0.449898 - outer loop - vertex 0.88493 0.28821 -0.0231763 - vertex 0.928671 8.47033e-23 -0.0231763 - vertex 0.939324 6.35275e-23 -0.0440839 - endloop - endfacet - facet normal 0.703206 0.105022 0.703187 - outer loop - vertex 0.895718 0.291976 -0.0440839 - vertex 0.939324 6.35275e-23 -0.0440839 - vertex 0.955916 4.23516e-23 -0.0606763 - endloop - endfacet - facet normal 0.452879 0.0696702 0.888846 - outer loop - vertex 0.955916 4.23516e-23 -0.0606763 - vertex 0.976824 2.11758e-23 -0.0713292 - vertex 0.93025 0.302746 -0.0713292 - endloop - endfacet - facet normal 0.15639 0.0247695 0.987385 - outer loop - vertex 0.976824 2.11758e-23 -0.0713292 - vertex 1 0 -0.075 - vertex 0.951057 0.309017 -0.075 - endloop - endfacet - facet normal -0.156357 -0.025449 0.987373 - outer loop - vertex 1 0 -0.075 - vertex 1.02318 4.23516e-23 -0.0713293 - vertex 0.971863 0.315288 -0.0713293 - endloop - endfacet - facet normal -0.452842 -0.0750614 0.888426 - outer loop - vertex 1.02318 4.23516e-23 -0.0713293 - vertex 1.04408 8.47033e-23 -0.0606763 - vertex 0.990855 0.321104 -0.0606763 - endloop - endfacet - facet normal -0.869017 -0.142674 0.473765 - outer loop - vertex 1.07133 1.69407e-22 -0.0231763 - vertex 1.01718 0.329824 -0.0231763 - vertex 1.0064 0.326058 -0.0440839 - endloop - endfacet - facet normal -0.702099 -0.116881 0.702421 - outer loop - vertex 1.04408 8.47033e-23 -0.0606763 - vertex 1.06068 1.27055e-22 -0.0440839 - vertex 1.0064 0.326058 -0.0440839 - endloop - endfacet - facet normal -0.863773 -0.443328 0.239492 - outer loop - vertex 0.864356 0.627584 -0.0231763 - vertex 1.01718 0.329824 -0.0231763 - vertex 1.02239 0.332193 -4.11565e-18 - endloop - endfacet - facet normal -0.678475 -0.678475 0.28168 - outer loop - vertex 0.627584 0.864356 -0.0231763 - vertex 0.864356 0.627584 -0.0231763 - vertex 0.869693 0.631869 -2.87899e-18 - endloop - endfacet - facet normal -0.160067 -0.974958 0.15439 - outer loop - vertex -6.61744e-24 1.075 8.31019e-19 - vertex -7.94093e-24 1.07133 -0.0231763 - vertex 0.329824 1.01718 -0.0231763 - endloop - endfacet - facet normal -0.443328 -0.863773 0.239492 - outer loop - vertex 0.332193 1.02239 -4.05649e-19 - vertex 0.329824 1.01718 -0.0231763 - vertex 0.627584 0.864356 -0.0231763 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -0.4 1.075 8.31019e-19 - vertex -0.4 1.07133 -0.0231763 - vertex -7.94093e-24 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -2 1.075 8.31019e-19 - vertex -2 1.07133 -0.0231763 - vertex -1.6 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -1.6 1.075 8.31019e-19 - vertex -1.6 1.07133 -0.0231763 - vertex -1.2 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -1.2 1.075 8.31019e-19 - vertex -1.2 1.07133 -0.0231763 - vertex -0.8 1.07133 -0.0231763 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -0.8 1.075 8.31019e-19 - vertex -0.8 1.07133 -0.0231763 - vertex -0.4 1.07133 -0.0231763 - endloop - endfacet - facet normal 0.974954 0.160055 0.154427 - outer loop - vertex 0.982817 -0.329824 -0.0231763 - vertex 0.928671 8.47033e-23 -0.0231763 - vertex 0.925 1.05879e-22 -9.92617e-24 - endloop - endfacet - facet normal 0.881362 0.146726 0.449079 - outer loop - vertex 0.993605 -0.326058 -0.0440839 - vertex 0.939324 6.35275e-23 -0.0440839 - vertex 0.928671 8.47033e-23 -0.0231763 - endloop - endfacet - facet normal 0.702267 0.116911 0.702249 - outer loop - vertex 0.955916 4.23516e-23 -0.0606763 - vertex 0.939324 6.35275e-23 -0.0440839 - vertex 0.993605 -0.326058 -0.0440839 - endloop - endfacet - facet normal 0.452702 0.0750368 0.888499 - outer loop - vertex 0.976824 2.11758e-23 -0.0713292 - vertex 0.955916 4.23516e-23 -0.0606763 - vertex 1.00914 -0.321104 -0.0606763 - endloop - endfacet - facet normal 0.156387 0.0254535 0.987368 - outer loop - vertex 1 0 -0.075 - vertex 0.976824 2.11758e-23 -0.0713292 - vertex 1.02814 -0.315287 -0.0713292 - endloop - endfacet - facet normal -0.156359 -0.0247631 0.98739 - outer loop - vertex 1.02318 4.23516e-23 -0.0713293 - vertex 1 0 -0.075 - vertex 1.04894 -0.309017 -0.075 - endloop - endfacet - facet normal -0.453019 -0.0696857 0.888773 - outer loop - vertex 1.04408 8.47033e-23 -0.0606763 - vertex 1.02318 4.23516e-23 -0.0713293 - vertex 1.06975 -0.302746 -0.0713293 - endloop - endfacet - facet normal -0.974958 -0.160067 0.15439 - outer loop - vertex 1.01718 0.329824 -0.0231763 - vertex 1.07133 1.69407e-22 -0.0231763 - vertex 1.075 2.11758e-22 -5.35232e-18 - endloop - endfacet - facet normal -0.881414 -0.146732 0.448975 - outer loop - vertex 1.0064 0.326058 -0.0440839 - vertex 1.06068 1.27055e-22 -0.0440839 - vertex 1.07133 1.69407e-22 -0.0231763 - endloop - endfacet - facet normal -0.703038 -0.104983 0.703361 - outer loop - vertex 1.10428 -0.291976 -0.0440839 - vertex 1.06068 1.27055e-22 -0.0440839 - vertex 1.04408 8.47033e-23 -0.0606763 - endloop - endfacet - facet normal -0.960847 -0.152171 0.231553 - outer loop - vertex 1.075 2.11758e-22 -5.35232e-18 - vertex 1.02239 0.332193 -4.11565e-18 - vertex 1.01718 0.329824 -0.0231763 - endloop - endfacet - facet normal -0.855945 -0.436139 0.277743 - outer loop - vertex 1.02239 0.332193 -4.11565e-18 - vertex 0.869693 0.631869 -2.87899e-18 - vertex 0.864356 0.627584 -0.0231763 - endloop - endfacet - facet normal -0.678475 -0.678475 0.28168 - outer loop - vertex 0.869693 0.631869 -2.87899e-18 - vertex 0.631869 0.869693 -1.64232e-18 - vertex 0.627584 0.864356 -0.0231763 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -7.94093e-24 1.07133 -0.0231763 - vertex -6.61744e-24 1.075 8.31019e-19 - vertex -0.4 1.075 8.31019e-19 - endloop - endfacet - facet normal -0.152171 -0.960847 0.231553 - outer loop - vertex 0.329824 1.01718 -0.0231763 - vertex 0.332193 1.02239 -4.05649e-19 - vertex -6.61744e-24 1.075 8.31019e-19 - endloop - endfacet - facet normal -0.436139 -0.855945 0.277743 - outer loop - vertex 0.627584 0.864356 -0.0231763 - vertex 0.631869 0.869693 -1.64232e-18 - vertex 0.332193 1.02239 -4.05649e-19 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -0.4 1.07133 -0.0231763 - vertex -0.4 1.075 8.31019e-19 - vertex -0.8 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -1.6 1.07133 -0.0231763 - vertex -1.6 1.075 8.31019e-19 - vertex -2 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -1.2 1.07133 -0.0231763 - vertex -1.2 1.075 8.31019e-19 - vertex -1.6 1.075 8.31019e-19 - endloop - endfacet - facet normal 0 -0.987693 0.156407 - outer loop - vertex -0.8 1.07133 -0.0231763 - vertex -0.8 1.075 8.31019e-19 - vertex -1.2 1.075 8.31019e-19 - endloop - endfacet - facet normal 0.868881 0.142641 0.474024 - outer loop - vertex 0.928671 8.47033e-23 -0.0231763 - vertex 0.982817 -0.329824 -0.0231763 - vertex 0.993605 -0.326058 -0.0440839 - endloop - endfacet - facet normal 0.96091 0.152193 0.231278 - outer loop - vertex 0.925 1.05879e-22 -9.92617e-24 - vertex 0.977614 -0.332193 1.85288e-23 - vertex 0.982817 -0.329824 -0.0231763 - endloop - endfacet - facet normal 0.707248 0.117229 0.697178 - outer loop - vertex 0.993605 -0.326058 -0.0440839 - vertex 1.00914 -0.321104 -0.0606763 - vertex 0.955916 4.23516e-23 -0.0606763 - endloop - endfacet - facet normal 0.469714 0.0764504 0.879502 - outer loop - vertex 1.00914 -0.321104 -0.0606763 - vertex 1.02814 -0.315287 -0.0713292 - vertex 0.976824 2.11758e-23 -0.0713292 - endloop - endfacet - facet normal 0.166042 0.0262966 0.985768 - outer loop - vertex 1.02814 -0.315287 -0.0713292 - vertex 1.04894 -0.309017 -0.075 - vertex 1 0 -0.075 - endloop - endfacet - facet normal -0.166177 -0.0255622 0.985765 - outer loop - vertex 1.04894 -0.309017 -0.075 - vertex 1.06975 -0.302746 -0.0713293 - vertex 1.02318 4.23516e-23 -0.0713293 - endloop - endfacet - facet normal -0.471416 -0.0709037 0.879056 - outer loop - vertex 1.06975 -0.302746 -0.0713293 - vertex 1.08874 -0.29693 -0.0606763 - vertex 1.04408 8.47033e-23 -0.0606763 - endloop - endfacet - facet normal -0.975826 -0.154546 0.154528 - outer loop - vertex 1.12027 -0.285841 -4.92967e-18 - vertex 1.075 2.11758e-22 -5.35232e-18 - vertex 1.07133 1.69407e-22 -0.0231763 - endloop - endfacet - facet normal -0.883021 -0.134011 0.449794 - outer loop - vertex 1.11507 -0.28821 -0.0231763 - vertex 1.07133 1.69407e-22 -0.0231763 - vertex 1.06068 1.27055e-22 -0.0440839 - endloop - endfacet - facet normal -0.871338 -0.130115 0.473117 - outer loop - vertex 1.06068 1.27055e-22 -0.0440839 - vertex 1.10428 -0.291976 -0.0440839 - vertex 1.11507 -0.28821 -0.0231763 - endloop - endfacet - facet normal -0.709608 -0.106729 0.696466 - outer loop - vertex 1.04408 8.47033e-23 -0.0606763 - vertex 1.08874 -0.29693 -0.0606763 - vertex 1.10428 -0.291976 -0.0440839 - endloop - endfacet - facet normal 0.781947 0.402501 0.475974 - outer loop - vertex 1.14517 -0.620506 -0.0440839 - vertex 0.993605 -0.326058 -0.0440839 - vertex 0.982817 -0.329824 -0.0231763 - endloop - endfacet - facet normal 0.863829 0.443353 0.239245 - outer loop - vertex 1.13564 -0.627584 -0.0231763 - vertex 0.982817 -0.329824 -0.0231763 - vertex 0.977614 -0.332193 1.85288e-23 - endloop - endfacet - facet normal 0.63849 0.328658 0.695928 - outer loop - vertex 1.00914 -0.321104 -0.0606763 - vertex 0.993605 -0.326058 -0.0440839 - vertex 1.14517 -0.620506 -0.0440839 - endloop - endfacet - facet normal 0.425391 0.218778 0.878168 - outer loop - vertex 1.02814 -0.315287 -0.0713292 - vertex 1.00914 -0.321104 -0.0606763 - vertex 1.15826 -0.611052 -0.0606763 - endloop - endfacet - facet normal 0.150666 0.0771894 0.985567 - outer loop - vertex 1.04894 -0.309017 -0.075 - vertex 1.02814 -0.315287 -0.0713292 - vertex 1.17394 -0.599872 -0.0713293 - endloop - endfacet - facet normal -0.150709 -0.0767904 0.985591 - outer loop - vertex 1.06975 -0.302746 -0.0713293 - vertex 1.04894 -0.309017 -0.075 - vertex 1.19098 -0.587785 -0.075 - endloop - endfacet - facet normal -0.426527 -0.216067 0.878288 - outer loop - vertex 1.08874 -0.29693 -0.0606763 - vertex 1.06975 -0.302746 -0.0713293 - vertex 1.20802 -0.575698 -0.0713293 - endloop - endfacet - facet normal -0.961994 -0.145997 0.230764 - outer loop - vertex 1.07133 1.69407e-22 -0.0231763 - vertex 1.11507 -0.28821 -0.0231763 - vertex 1.12027 -0.285841 -4.92967e-18 - endloop - endfacet - facet normal -0.784749 -0.396487 0.476411 - outer loop - vertex 1.24632 -0.547987 -0.0231763 - vertex 1.11507 -0.28821 -0.0231763 - vertex 1.10428 -0.291976 -0.0440839 - endloop - endfacet - facet normal -0.640821 -0.322763 0.696543 - outer loop - vertex 1.23679 -0.555064 -0.0440839 - vertex 1.10428 -0.291976 -0.0440839 - vertex 1.08874 -0.29693 -0.0606763 - endloop - endfacet - facet normal 0.776205 0.398381 0.488671 - outer loop - vertex 0.982817 -0.329824 -0.0231763 - vertex 1.13564 -0.627584 -0.0231763 - vertex 1.14517 -0.620506 -0.0440839 - endloop - endfacet - facet normal 0.856008 0.436168 0.277503 - outer loop - vertex 0.977614 -0.332193 1.85288e-23 - vertex 1.13031 -0.631869 4.69839e-23 - vertex 1.13564 -0.627584 -0.0231763 - endloop - endfacet - facet normal 0.640825 0.329575 0.693342 - outer loop - vertex 1.14517 -0.620506 -0.0440839 - vertex 1.15826 -0.611052 -0.0606763 - vertex 1.00914 -0.321104 -0.0606763 - endloop - endfacet - facet normal 0.434341 0.222523 0.872829 - outer loop - vertex 1.15826 -0.611052 -0.0606763 - vertex 1.17394 -0.599872 -0.0713293 - vertex 1.02814 -0.315287 -0.0713292 - endloop - endfacet - facet normal 0.155791 0.07938 0.984595 - outer loop - vertex 1.17394 -0.599872 -0.0713293 - vertex 1.19098 -0.587785 -0.075 - vertex 1.04894 -0.309017 -0.075 - endloop - endfacet - facet normal -0.15603 -0.0790405 0.984585 - outer loop - vertex 1.19098 -0.587785 -0.075 - vertex 1.20802 -0.575698 -0.0713293 - vertex 1.06975 -0.302746 -0.0713293 - endloop - endfacet - facet normal -0.436054 -0.219927 0.872633 - outer loop - vertex 1.20802 -0.575698 -0.0713293 - vertex 1.2237 -0.564518 -0.0606763 - vertex 1.08874 -0.29693 -0.0606763 - endloop - endfacet - facet normal -0.865143 -0.440823 0.23917 - outer loop - vertex 1.25166 -0.543702 -4.50701e-18 - vertex 1.12027 -0.285841 -4.92967e-18 - vertex 1.11507 -0.28821 -0.0231763 - endloop - endfacet - facet normal -0.857453 -0.43322 0.27766 - outer loop - vertex 1.11507 -0.28821 -0.0231763 - vertex 1.24632 -0.547987 -0.0231763 - vertex 1.25166 -0.543702 -4.50701e-18 - endloop - endfacet - facet normal -0.779457 -0.39259 0.488179 - outer loop - vertex 1.10428 -0.291976 -0.0440839 - vertex 1.23679 -0.555064 -0.0440839 - vertex 1.24632 -0.547987 -0.0231763 - endloop - endfacet - facet normal -0.643789 -0.3247 0.692897 - outer loop - vertex 1.08874 -0.29693 -0.0606763 - vertex 1.2237 -0.564518 -0.0606763 - vertex 1.23679 -0.555064 -0.0440839 - endloop - endfacet - facet normal 0.616513 0.616508 0.489725 - outer loop - vertex 1.37949 -0.854828 -0.0440839 - vertex 1.14517 -0.620506 -0.0440839 - vertex 1.13564 -0.627584 -0.0231763 - endloop - endfacet - facet normal 0.678502 0.678527 0.28149 - outer loop - vertex 1.37242 -0.864355 -0.0231763 - vertex 1.13564 -0.627584 -0.0231763 - vertex 1.13031 -0.631869 4.69839e-23 - endloop - endfacet - facet normal 0.50991 0.509906 0.692811 - outer loop - vertex 1.15826 -0.611052 -0.0606763 - vertex 1.14517 -0.620506 -0.0440839 - vertex 1.37949 -0.854828 -0.0440839 - endloop - endfacet - facet normal 0.345913 0.345919 0.872172 - outer loop - vertex 1.17394 -0.599872 -0.0713293 - vertex 1.15826 -0.611052 -0.0606763 - vertex 1.38895 -0.841738 -0.0606763 - endloop - endfacet - facet normal 0.124069 0.124068 0.984487 - outer loop - vertex 1.41221 -0.809017 -0.075 - vertex 1.19098 -0.587785 -0.075 - vertex 1.17394 -0.599872 -0.0713293 - endloop - endfacet - facet normal -0.124069 -0.124068 0.984487 - outer loop - vertex 1.20802 -0.575698 -0.0713293 - vertex 1.19098 -0.587785 -0.075 - vertex 1.41221 -0.809017 -0.075 - endloop - endfacet - facet normal -0.345912 -0.345915 0.872174 - outer loop - vertex 1.2237 -0.564518 -0.0606763 - vertex 1.20802 -0.575698 -0.0713293 - vertex 1.4243 -0.791976 -0.0713293 - endloop - endfacet - facet normal -0.678462 -0.678455 0.281759 - outer loop - vertex 1.25166 -0.543702 -4.50701e-18 - vertex 1.24632 -0.547987 -0.0231763 - vertex 1.45201 -0.753679 -0.0231763 - endloop - endfacet - facet normal -0.616521 -0.616515 0.489706 - outer loop - vertex 1.45201 -0.753679 -0.0231763 - vertex 1.24632 -0.547987 -0.0231763 - vertex 1.23679 -0.555064 -0.0440839 - endloop - endfacet - facet normal -0.509908 -0.509913 0.692808 - outer loop - vertex 1.23679 -0.555064 -0.0440839 - vertex 1.2237 -0.564518 -0.0606763 - vertex 1.43548 -0.776296 -0.0606763 - endloop - endfacet - facet normal 0.616595 0.616618 0.489482 - outer loop - vertex 1.13564 -0.627584 -0.0231763 - vertex 1.37242 -0.864355 -0.0231763 - vertex 1.37949 -0.854828 -0.0440839 - endloop - endfacet - facet normal 0.678448 0.678436 0.281839 - outer loop - vertex 1.13031 -0.631869 4.69839e-23 - vertex 1.36813 -0.869693 7.54389e-23 - vertex 1.37242 -0.864355 -0.0231763 - endloop - endfacet - facet normal 0.509839 0.509848 0.692906 - outer loop - vertex 1.37949 -0.854828 -0.0440839 - vertex 1.38895 -0.841738 -0.0606763 - vertex 1.15826 -0.611052 -0.0606763 - endloop - endfacet - facet normal 0.34591 0.345917 0.872174 - outer loop - vertex 1.38895 -0.841738 -0.0606763 - vertex 1.40013 -0.826058 -0.0713293 - vertex 1.17394 -0.599872 -0.0713293 - endloop - endfacet - facet normal 0.124093 0.124095 0.98448 - outer loop - vertex 1.17394 -0.599872 -0.0713293 - vertex 1.40013 -0.826058 -0.0713293 - vertex 1.41221 -0.809017 -0.075 - endloop - endfacet - facet normal -0.124052 -0.124053 0.984491 - outer loop - vertex 1.41221 -0.809017 -0.075 - vertex 1.4243 -0.791976 -0.0713293 - vertex 1.20802 -0.575698 -0.0713293 - endloop - endfacet - facet normal -0.345913 -0.345916 0.872173 - outer loop - vertex 1.4243 -0.791976 -0.0713293 - vertex 1.43548 -0.776296 -0.0606763 - vertex 1.2237 -0.564518 -0.0606763 - endloop - endfacet - facet normal -0.67844 -0.678443 0.28184 - outer loop - vertex 1.45201 -0.753679 -0.0231763 - vertex 1.4563 -0.748341 -4.08435e-18 - vertex 1.25166 -0.543702 -4.50701e-18 - endloop - endfacet - facet normal -0.616595 -0.616618 0.489482 - outer loop - vertex 1.23679 -0.555064 -0.0440839 - vertex 1.44494 -0.763206 -0.0440839 - vertex 1.45201 -0.753679 -0.0231763 - endloop - endfacet - facet normal -0.509833 -0.509853 0.692907 - outer loop - vertex 1.43548 -0.776296 -0.0606763 - vertex 1.44494 -0.763206 -0.0440839 - vertex 1.23679 -0.555064 -0.0440839 - endloop - endfacet - facet normal 0.398435 0.776301 0.488473 - outer loop - vertex 1.37949 -0.854828 -0.0440839 - vertex 1.37242 -0.864355 -0.0231763 - vertex 1.67018 -1.01718 -0.0231763 - endloop - endfacet - facet normal 0.436118 0.855917 0.277861 - outer loop - vertex 1.37242 -0.864355 -0.0231763 - vertex 1.36813 -0.869693 7.54389e-23 - vertex 1.66781 -1.02239 1.03894e-22 - endloop - endfacet - facet normal 0.329542 0.640776 0.693403 - outer loop - vertex 1.6789 -0.990855 -0.0606763 - vertex 1.38895 -0.841738 -0.0606763 - vertex 1.37949 -0.854828 -0.0440839 - endloop - endfacet - facet normal 0.222532 0.434334 0.872831 - outer loop - vertex 1.68471 -0.971863 -0.0713293 - vertex 1.40013 -0.826058 -0.0713293 - vertex 1.38895 -0.841738 -0.0606763 - endloop - endfacet - facet normal 0.0793879 0.155809 0.984592 - outer loop - vertex 1.69098 -0.951056 -0.075 - vertex 1.41221 -0.809017 -0.075 - vertex 1.40013 -0.826058 -0.0713293 - endloop - endfacet - facet normal -0.0790346 -0.156012 0.984588 - outer loop - vertex 1.69725 -0.93025 -0.0713292 - vertex 1.4243 -0.791976 -0.0713293 - vertex 1.41221 -0.809017 -0.075 - endloop - endfacet - facet normal -0.219929 -0.436056 0.872632 - outer loop - vertex 1.70307 -0.911258 -0.0606763 - vertex 1.43548 -0.776296 -0.0606763 - vertex 1.4243 -0.791976 -0.0713293 - endloop - endfacet - facet normal -0.433217 -0.857449 0.277677 - outer loop - vertex 1.4563 -0.748341 -4.08435e-18 - vertex 1.45201 -0.753679 -0.0231763 - vertex 1.71179 -0.88493 -0.0231763 - endloop - endfacet - facet normal -0.392651 -0.779542 0.487994 - outer loop - vertex 1.45201 -0.753679 -0.0231763 - vertex 1.44494 -0.763206 -0.0440839 - vertex 1.70802 -0.895718 -0.0440839 - endloop - endfacet - facet normal -0.324674 -0.643733 0.692961 - outer loop - vertex 1.44494 -0.763206 -0.0440839 - vertex 1.43548 -0.776296 -0.0606763 - vertex 1.70307 -0.911258 -0.0606763 - endloop - endfacet - facet normal 0.443328 0.863768 0.23951 - outer loop - vertex 1.66781 -1.02239 1.03894e-22 - vertex 1.67018 -1.01718 -0.0231763 - vertex 1.37242 -0.864355 -0.0231763 - endloop - endfacet - facet normal 0.402501 0.781967 0.475942 - outer loop - vertex 1.67018 -1.01718 -0.0231763 - vertex 1.67394 -1.00639 -0.0440839 - vertex 1.37949 -0.854828 -0.0440839 - endloop - endfacet - facet normal 0.218863 0.425568 0.878061 - outer loop - vertex 1.38895 -0.841738 -0.0606763 - vertex 1.6789 -0.990855 -0.0606763 - vertex 1.68471 -0.971863 -0.0713293 - endloop - endfacet - facet normal 0.328623 0.638439 0.69599 - outer loop - vertex 1.37949 -0.854828 -0.0440839 - vertex 1.67394 -1.00639 -0.0440839 - vertex 1.6789 -0.990855 -0.0606763 - endloop - endfacet - facet normal 0.0771694 0.150618 0.985576 - outer loop - vertex 1.40013 -0.826058 -0.0713293 - vertex 1.68471 -0.971863 -0.0713293 - vertex 1.69098 -0.951056 -0.075 - endloop - endfacet - facet normal -0.0768055 -0.150741 0.985585 - outer loop - vertex 1.41221 -0.809017 -0.075 - vertex 1.69098 -0.951056 -0.075 - vertex 1.69725 -0.93025 -0.0713292 - endloop - endfacet - facet normal -0.216042 -0.426461 0.878326 - outer loop - vertex 1.4243 -0.791976 -0.0713293 - vertex 1.69725 -0.93025 -0.0713292 - vertex 1.70307 -0.911258 -0.0606763 - endloop - endfacet - facet normal -0.396486 -0.784749 0.47641 - outer loop - vertex 1.70802 -0.895718 -0.0440839 - vertex 1.71179 -0.88493 -0.0231763 - vertex 1.45201 -0.753679 -0.0231763 - endloop - endfacet - facet normal -0.4408 -0.865121 0.239293 - outer loop - vertex 1.71179 -0.88493 -0.0231763 - vertex 1.71416 -0.879727 -3.6617e-18 - vertex 1.4563 -0.748341 -4.08435e-18 - endloop - endfacet - facet normal -0.322793 -0.640851 0.696502 - outer loop - vertex 1.70307 -0.911258 -0.0606763 - vertex 1.70802 -0.895718 -0.0440839 - vertex 1.44494 -0.763206 -0.0440839 - endloop - endfacet - facet normal 0.152172 0.960845 0.23156 - outer loop - vertex 1.67018 -1.01718 -0.0231763 - vertex 1.66781 -1.02239 1.03894e-22 - vertex 2 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0.14265 0.868862 0.474056 - outer loop - vertex 1.67394 -1.00639 -0.0440839 - vertex 1.67018 -1.01718 -0.0231763 - vertex 2 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0.0764787 0.469883 0.87941 - outer loop - vertex 2 -1.02318 -0.0713293 - vertex 1.68471 -0.971863 -0.0713293 - vertex 1.6789 -0.990855 -0.0606763 - endloop - endfacet - facet normal 0.117229 0.707226 0.6972 - outer loop - vertex 2 -1.04408 -0.0606763 - vertex 1.6789 -0.990855 -0.0606763 - vertex 1.67394 -1.00639 -0.0440839 - endloop - endfacet - facet normal 0.0262896 0.165986 0.985778 - outer loop - vertex 2 -1 -0.075 - vertex 1.69098 -0.951056 -0.075 - vertex 1.68471 -0.971863 -0.0713293 - endloop - endfacet - facet normal -0.0255694 -0.166212 0.985759 - outer loop - vertex 2 -0.976824 -0.0713292 - vertex 1.69725 -0.93025 -0.0713292 - vertex 1.69098 -0.951056 -0.075 - endloop - endfacet - facet normal -0.0708931 -0.471366 0.879084 - outer loop - vertex 2 -0.955916 -0.0606763 - vertex 1.70307 -0.911258 -0.0606763 - vertex 1.69725 -0.93025 -0.0713292 - endloop - endfacet - facet normal -0.130134 -0.87136 0.473072 - outer loop - vertex 1.71179 -0.88493 -0.0231763 - vertex 1.70802 -0.895718 -0.0440839 - vertex 2 -0.939324 -0.0440839 - endloop - endfacet - facet normal -0.145995 -0.961965 0.230888 - outer loop - vertex 1.71416 -0.879727 -3.6617e-18 - vertex 1.71179 -0.88493 -0.0231763 - vertex 2 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0.106727 -0.709622 0.696452 - outer loop - vertex 1.70802 -0.895718 -0.0440839 - vertex 1.70307 -0.911258 -0.0606763 - vertex 2 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0.160069 0.974957 0.15439 - outer loop - vertex 2 -1.075 1.32349e-22 - vertex 2 -1.07133 -0.0231763 - vertex 1.67018 -1.01718 -0.0231763 - endloop - endfacet - facet normal 0.146758 0.881411 0.448973 - outer loop - vertex 2 -1.07133 -0.0231763 - vertex 2 -1.06068 -0.0440839 - vertex 1.67394 -1.00639 -0.0440839 - endloop - endfacet - facet normal 0.0254488 0.156357 0.987373 - outer loop - vertex 1.68471 -0.971863 -0.0713293 - vertex 2 -1.02318 -0.0713293 - vertex 2 -1 -0.075 - endloop - endfacet - facet normal 0.0750624 0.452842 0.888425 - outer loop - vertex 1.6789 -0.990855 -0.0606763 - vertex 2 -1.04408 -0.0606763 - vertex 2 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0.116901 0.702097 0.70242 - outer loop - vertex 1.67394 -1.00639 -0.0440839 - vertex 2 -1.06068 -0.0440839 - vertex 2 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0.0247698 -0.15639 0.987385 - outer loop - vertex 1.69098 -0.951056 -0.075 - vertex 2 -1 -0.075 - vertex 2 -0.976824 -0.0713292 - endloop - endfacet - facet normal -0.0696693 -0.452879 0.888846 - outer loop - vertex 1.69725 -0.93025 -0.0713292 - vertex 2 -0.976824 -0.0713292 - vertex 2 -0.955916 -0.0606763 - endloop - endfacet - facet normal -0.105021 -0.703206 0.703187 - outer loop - vertex 2 -0.955916 -0.0606763 - vertex 2 -0.939324 -0.0440839 - vertex 1.70802 -0.895718 -0.0440839 - endloop - endfacet - facet normal -0.134006 -0.882969 0.449898 - outer loop - vertex 2 -0.939324 -0.0440839 - vertex 2 -0.928671 -0.0231763 - vertex 1.71179 -0.88493 -0.0231763 - endloop - endfacet - facet normal -0.154556 -0.975819 0.154564 - outer loop - vertex 2 -0.928671 -0.0231763 - vertex 2 -0.925 -3.23904e-18 - vertex 1.71416 -0.879727 -3.6617e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 2.4 -1.07133 -0.0231763 - vertex 2 -1.07133 -0.0231763 - vertex 2 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 2.4 -1.06068 -0.0440839 - vertex 2 -1.06068 -0.0440839 - vertex 2 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 2.4 -1 -0.075 - vertex 2 -1 -0.075 - vertex 2 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 2.4 -1.02318 -0.0713293 - vertex 2 -1.02318 -0.0713293 - vertex 2 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 2.4 -1.04408 -0.0606763 - vertex 2 -1.04408 -0.0606763 - vertex 2 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 2 -0.976824 -0.0713292 - vertex 2 -1 -0.075 - vertex 2.4 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 2 -0.955916 -0.0606763 - vertex 2 -0.976824 -0.0713292 - vertex 2.4 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 2 -0.939324 -0.0440839 - vertex 2 -0.955916 -0.0606763 - vertex 2.4 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 2 -0.928671 -0.0231763 - vertex 2 -0.939324 -0.0440839 - vertex 2.4 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 2 -0.925 -3.23904e-18 - vertex 2 -0.928671 -0.0231763 - vertex 2.4 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 2 -1.075 1.32349e-22 - vertex 2.4 -1.075 1.32349e-22 - vertex 2.4 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 2 -1.07133 -0.0231763 - vertex 2.4 -1.07133 -0.0231763 - vertex 2.4 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 2 -1.06068 -0.0440839 - vertex 2.4 -1.06068 -0.0440839 - vertex 2.4 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 2 -1.02318 -0.0713293 - vertex 2.4 -1.02318 -0.0713293 - vertex 2.4 -1 -0.075 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 2 -1.04408 -0.0606763 - vertex 2.4 -1.04408 -0.0606763 - vertex 2.4 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 2.4 -1 -0.075 - vertex 2.4 -0.976824 -0.0713292 - vertex 2 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 2.4 -0.976824 -0.0713292 - vertex 2.4 -0.955916 -0.0606763 - vertex 2 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 2.4 -0.955916 -0.0606763 - vertex 2.4 -0.939324 -0.0440839 - vertex 2 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 2.4 -0.939324 -0.0440839 - vertex 2.4 -0.928671 -0.0231763 - vertex 2 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 2.4 -0.928671 -0.0231763 - vertex 2.4 -0.925 -3.23904e-18 - vertex 2 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 2.8 -1.07133 -0.0231763 - vertex 2.4 -1.07133 -0.0231763 - vertex 2.4 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 2.8 -1.06068 -0.0440839 - vertex 2.4 -1.06068 -0.0440839 - vertex 2.4 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 2.8 -1.04408 -0.0606763 - vertex 2.4 -1.04408 -0.0606763 - vertex 2.4 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 2.8 -1 -0.075 - vertex 2.4 -1 -0.075 - vertex 2.4 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 2.8 -1.02318 -0.0713293 - vertex 2.4 -1.02318 -0.0713293 - vertex 2.4 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 2.4 -0.976824 -0.0713292 - vertex 2.4 -1 -0.075 - vertex 2.8 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 2.4 -0.955916 -0.0606763 - vertex 2.4 -0.976824 -0.0713292 - vertex 2.8 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 2.4 -0.939324 -0.0440839 - vertex 2.4 -0.955916 -0.0606763 - vertex 2.8 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 2.4 -0.928671 -0.0231763 - vertex 2.4 -0.939324 -0.0440839 - vertex 2.8 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 2.4 -0.925 -3.23904e-18 - vertex 2.4 -0.928671 -0.0231763 - vertex 2.8 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 2.4 -1.075 1.32349e-22 - vertex 2.8 -1.075 1.32349e-22 - vertex 2.8 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 2.4 -1.07133 -0.0231763 - vertex 2.8 -1.07133 -0.0231763 - vertex 2.8 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 2.4 -1.06068 -0.0440839 - vertex 2.8 -1.06068 -0.0440839 - vertex 2.8 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 2.4 -1.04408 -0.0606763 - vertex 2.8 -1.04408 -0.0606763 - vertex 2.8 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 2.4 -1.02318 -0.0713293 - vertex 2.8 -1.02318 -0.0713293 - vertex 2.8 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 2.8 -1 -0.075 - vertex 2.8 -0.976824 -0.0713292 - vertex 2.4 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 2.8 -0.976824 -0.0713292 - vertex 2.8 -0.955916 -0.0606763 - vertex 2.4 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 2.8 -0.955916 -0.0606763 - vertex 2.8 -0.939324 -0.0440839 - vertex 2.4 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 2.8 -0.939324 -0.0440839 - vertex 2.8 -0.928671 -0.0231763 - vertex 2.4 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 2.8 -0.928671 -0.0231763 - vertex 2.8 -0.925 -3.23904e-18 - vertex 2.4 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 3.2 -1.07133 -0.0231763 - vertex 2.8 -1.07133 -0.0231763 - vertex 2.8 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 3.2 -1.06068 -0.0440839 - vertex 2.8 -1.06068 -0.0440839 - vertex 2.8 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 3.2 -1.04408 -0.0606763 - vertex 2.8 -1.04408 -0.0606763 - vertex 2.8 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 3.2 -1.02318 -0.0713293 - vertex 2.8 -1.02318 -0.0713293 - vertex 2.8 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 3.2 -1 -0.075 - vertex 2.8 -1 -0.075 - vertex 2.8 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 2.8 -0.976824 -0.0713292 - vertex 2.8 -1 -0.075 - vertex 3.2 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 2.8 -0.955916 -0.0606763 - vertex 2.8 -0.976824 -0.0713292 - vertex 3.2 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 2.8 -0.939324 -0.0440839 - vertex 2.8 -0.955916 -0.0606763 - vertex 3.2 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 2.8 -0.928671 -0.0231763 - vertex 2.8 -0.939324 -0.0440839 - vertex 3.2 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 2.8 -0.925 -3.23904e-18 - vertex 2.8 -0.928671 -0.0231763 - vertex 3.2 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 2.8 -1.075 1.32349e-22 - vertex 3.2 -1.075 1.32349e-22 - vertex 3.2 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 2.8 -1.07133 -0.0231763 - vertex 3.2 -1.07133 -0.0231763 - vertex 3.2 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 2.8 -1.06068 -0.0440839 - vertex 3.2 -1.06068 -0.0440839 - vertex 3.2 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 2.8 -1.04408 -0.0606763 - vertex 3.2 -1.04408 -0.0606763 - vertex 3.2 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 2.8 -1.02318 -0.0713293 - vertex 3.2 -1.02318 -0.0713293 - vertex 3.2 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 3.2 -1 -0.075 - vertex 3.2 -0.976824 -0.0713292 - vertex 2.8 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 3.2 -0.976824 -0.0713292 - vertex 3.2 -0.955916 -0.0606763 - vertex 2.8 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 3.2 -0.955916 -0.0606763 - vertex 3.2 -0.939324 -0.0440839 - vertex 2.8 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 3.2 -0.939324 -0.0440839 - vertex 3.2 -0.928671 -0.0231763 - vertex 2.8 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 3.2 -0.928671 -0.0231763 - vertex 3.2 -0.925 -3.23904e-18 - vertex 2.8 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 3.6 -1.07133 -0.0231763 - vertex 3.2 -1.07133 -0.0231763 - vertex 3.2 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 3.6 -1.06068 -0.0440839 - vertex 3.2 -1.06068 -0.0440839 - vertex 3.2 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 3.6 -1.04408 -0.0606763 - vertex 3.2 -1.04408 -0.0606763 - vertex 3.2 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 3.6 -1.02318 -0.0713293 - vertex 3.2 -1.02318 -0.0713293 - vertex 3.2 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 3.6 -1 -0.075 - vertex 3.2 -1 -0.075 - vertex 3.2 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 3.2 -0.976824 -0.0713292 - vertex 3.2 -1 -0.075 - vertex 3.6 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 3.2 -0.955916 -0.0606763 - vertex 3.2 -0.976824 -0.0713292 - vertex 3.6 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 3.2 -0.939324 -0.0440839 - vertex 3.2 -0.955916 -0.0606763 - vertex 3.6 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 3.2 -0.928671 -0.0231763 - vertex 3.2 -0.939324 -0.0440839 - vertex 3.6 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 3.2 -0.925 -3.23904e-18 - vertex 3.2 -0.928671 -0.0231763 - vertex 3.6 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 3.2 -1.075 1.32349e-22 - vertex 3.6 -1.075 1.32349e-22 - vertex 3.6 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 3.2 -1.07133 -0.0231763 - vertex 3.6 -1.07133 -0.0231763 - vertex 3.6 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 3.2 -1.06068 -0.0440839 - vertex 3.6 -1.06068 -0.0440839 - vertex 3.6 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 3.2 -1.04408 -0.0606763 - vertex 3.6 -1.04408 -0.0606763 - vertex 3.6 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 3.2 -1.02318 -0.0713293 - vertex 3.6 -1.02318 -0.0713293 - vertex 3.6 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 3.6 -1 -0.075 - vertex 3.6 -0.976824 -0.0713292 - vertex 3.2 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 3.6 -0.976824 -0.0713292 - vertex 3.6 -0.955916 -0.0606763 - vertex 3.2 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 3.6 -0.955916 -0.0606763 - vertex 3.6 -0.939324 -0.0440839 - vertex 3.2 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 3.6 -0.939324 -0.0440839 - vertex 3.6 -0.928671 -0.0231763 - vertex 3.2 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 3.6 -0.928671 -0.0231763 - vertex 3.6 -0.925 -3.23904e-18 - vertex 3.2 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 4 -1.07133 -0.0231763 - vertex 3.6 -1.07133 -0.0231763 - vertex 3.6 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 4 -1.06068 -0.0440839 - vertex 3.6 -1.06068 -0.0440839 - vertex 3.6 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 4 -1.04408 -0.0606763 - vertex 3.6 -1.04408 -0.0606763 - vertex 3.6 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 4 -1.02318 -0.0713293 - vertex 3.6 -1.02318 -0.0713293 - vertex 3.6 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 4 -1 -0.075 - vertex 3.6 -1 -0.075 - vertex 3.6 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 3.6 -0.976824 -0.0713292 - vertex 3.6 -1 -0.075 - vertex 4 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 3.6 -0.955916 -0.0606763 - vertex 3.6 -0.976824 -0.0713292 - vertex 4 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 3.6 -0.939324 -0.0440839 - vertex 3.6 -0.955916 -0.0606763 - vertex 4 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 3.6 -0.928671 -0.0231763 - vertex 3.6 -0.939324 -0.0440839 - vertex 4 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 3.6 -0.925 -3.23904e-18 - vertex 3.6 -0.928671 -0.0231763 - vertex 4 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 3.6 -1.075 1.32349e-22 - vertex 4 -1.075 1.32349e-22 - vertex 4 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 3.6 -1.07133 -0.0231763 - vertex 4 -1.07133 -0.0231763 - vertex 4 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 3.6 -1.06068 -0.0440839 - vertex 4 -1.06068 -0.0440839 - vertex 4 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 3.6 -1.04408 -0.0606763 - vertex 4 -1.04408 -0.0606763 - vertex 4 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 3.6 -1.02318 -0.0713293 - vertex 4 -1.02318 -0.0713293 - vertex 4 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 4 -1 -0.075 - vertex 4 -0.976824 -0.0713292 - vertex 3.6 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 4 -0.976824 -0.0713292 - vertex 4 -0.955916 -0.0606763 - vertex 3.6 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 4 -0.955916 -0.0606763 - vertex 4 -0.939324 -0.0440839 - vertex 3.6 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 4 -0.939324 -0.0440839 - vertex 4 -0.928671 -0.0231763 - vertex 3.6 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 4 -0.928671 -0.0231763 - vertex 4 -0.925 -3.23904e-18 - vertex 3.6 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 4.4 -1.07133 -0.0231763 - vertex 4 -1.07133 -0.0231763 - vertex 4 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 4.4 -1.06068 -0.0440839 - vertex 4 -1.06068 -0.0440839 - vertex 4 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 4.4 -1.04408 -0.0606763 - vertex 4 -1.04408 -0.0606763 - vertex 4 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 4.4 -1.02318 -0.0713293 - vertex 4 -1.02318 -0.0713293 - vertex 4 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 4.4 -1 -0.075 - vertex 4 -1 -0.075 - vertex 4 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 4 -0.976824 -0.0713292 - vertex 4 -1 -0.075 - vertex 4.4 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 4 -0.955916 -0.0606763 - vertex 4 -0.976824 -0.0713292 - vertex 4.4 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 4 -0.939324 -0.0440839 - vertex 4 -0.955916 -0.0606763 - vertex 4.4 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 4 -0.928671 -0.0231763 - vertex 4 -0.939324 -0.0440839 - vertex 4.4 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 4 -0.925 -3.23904e-18 - vertex 4 -0.928671 -0.0231763 - vertex 4.4 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 4 -1.075 1.32349e-22 - vertex 4.4 -1.075 1.32349e-22 - vertex 4.4 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 4 -1.07133 -0.0231763 - vertex 4.4 -1.07133 -0.0231763 - vertex 4.4 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 4 -1.06068 -0.0440839 - vertex 4.4 -1.06068 -0.0440839 - vertex 4.4 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 4 -1.04408 -0.0606763 - vertex 4.4 -1.04408 -0.0606763 - vertex 4.4 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 4 -1.02318 -0.0713293 - vertex 4.4 -1.02318 -0.0713293 - vertex 4.4 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 4.4 -1 -0.075 - vertex 4.4 -0.976824 -0.0713292 - vertex 4 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 4.4 -0.976824 -0.0713292 - vertex 4.4 -0.955916 -0.0606763 - vertex 4 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 4.4 -0.955916 -0.0606763 - vertex 4.4 -0.939324 -0.0440839 - vertex 4 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 4.4 -0.939324 -0.0440839 - vertex 4.4 -0.928671 -0.0231763 - vertex 4 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 4.4 -0.928671 -0.0231763 - vertex 4.4 -0.925 -3.23904e-18 - vertex 4 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 4.8 -1.07133 -0.0231763 - vertex 4.4 -1.07133 -0.0231763 - vertex 4.4 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 4.8 -1.06068 -0.0440839 - vertex 4.4 -1.06068 -0.0440839 - vertex 4.4 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 4.8 -1.04408 -0.0606763 - vertex 4.4 -1.04408 -0.0606763 - vertex 4.4 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 4.8 -1.02318 -0.0713293 - vertex 4.4 -1.02318 -0.0713293 - vertex 4.4 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 4.8 -1 -0.075 - vertex 4.4 -1 -0.075 - vertex 4.4 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 4.4 -0.976824 -0.0713292 - vertex 4.4 -1 -0.075 - vertex 4.8 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 4.4 -0.955916 -0.0606763 - vertex 4.4 -0.976824 -0.0713292 - vertex 4.8 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 4.4 -0.939324 -0.0440839 - vertex 4.4 -0.955916 -0.0606763 - vertex 4.8 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 4.4 -0.928671 -0.0231763 - vertex 4.4 -0.939324 -0.0440839 - vertex 4.8 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 4.4 -0.925 -3.23904e-18 - vertex 4.4 -0.928671 -0.0231763 - vertex 4.8 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 4.4 -1.075 1.32349e-22 - vertex 4.8 -1.075 1.32349e-22 - vertex 4.8 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 4.4 -1.07133 -0.0231763 - vertex 4.8 -1.07133 -0.0231763 - vertex 4.8 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 4.4 -1.06068 -0.0440839 - vertex 4.8 -1.06068 -0.0440839 - vertex 4.8 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 4.4 -1.04408 -0.0606763 - vertex 4.8 -1.04408 -0.0606763 - vertex 4.8 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 4.4 -1.02318 -0.0713293 - vertex 4.8 -1.02318 -0.0713293 - vertex 4.8 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 4.8 -1 -0.075 - vertex 4.8 -0.976824 -0.0713292 - vertex 4.4 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 4.8 -0.976824 -0.0713292 - vertex 4.8 -0.955916 -0.0606763 - vertex 4.4 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 4.8 -0.955916 -0.0606763 - vertex 4.8 -0.939324 -0.0440839 - vertex 4.4 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 4.8 -0.939324 -0.0440839 - vertex 4.8 -0.928671 -0.0231763 - vertex 4.4 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 4.8 -0.928671 -0.0231763 - vertex 4.8 -0.925 -3.23904e-18 - vertex 4.4 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 5.2 -1.07133 -0.0231763 - vertex 4.8 -1.07133 -0.0231763 - vertex 4.8 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 5.2 -1.06068 -0.0440839 - vertex 4.8 -1.06068 -0.0440839 - vertex 4.8 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 5.2 -1.04408 -0.0606763 - vertex 4.8 -1.04408 -0.0606763 - vertex 4.8 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 5.2 -1.02318 -0.0713293 - vertex 4.8 -1.02318 -0.0713293 - vertex 4.8 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 5.2 -1 -0.075 - vertex 4.8 -1 -0.075 - vertex 4.8 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 4.8 -0.976824 -0.0713292 - vertex 4.8 -1 -0.075 - vertex 5.2 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 4.8 -0.955916 -0.0606763 - vertex 4.8 -0.976824 -0.0713292 - vertex 5.2 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 4.8 -0.939324 -0.0440839 - vertex 4.8 -0.955916 -0.0606763 - vertex 5.2 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 4.8 -0.928671 -0.0231763 - vertex 4.8 -0.939324 -0.0440839 - vertex 5.2 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 4.8 -0.925 -3.23904e-18 - vertex 4.8 -0.928671 -0.0231763 - vertex 5.2 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 4.8 -1.075 1.32349e-22 - vertex 5.2 -1.075 1.32349e-22 - vertex 5.2 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 4.8 -1.07133 -0.0231763 - vertex 5.2 -1.07133 -0.0231763 - vertex 5.2 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 4.8 -1.06068 -0.0440839 - vertex 5.2 -1.06068 -0.0440839 - vertex 5.2 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 4.8 -1.04408 -0.0606763 - vertex 5.2 -1.04408 -0.0606763 - vertex 5.2 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 4.8 -1.02318 -0.0713293 - vertex 5.2 -1.02318 -0.0713293 - vertex 5.2 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 5.2 -1 -0.075 - vertex 5.2 -0.976824 -0.0713292 - vertex 4.8 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 5.2 -0.976824 -0.0713292 - vertex 5.2 -0.955916 -0.0606763 - vertex 4.8 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 5.2 -0.955916 -0.0606763 - vertex 5.2 -0.939324 -0.0440839 - vertex 4.8 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 5.2 -0.939324 -0.0440839 - vertex 5.2 -0.928671 -0.0231763 - vertex 4.8 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 5.2 -0.928671 -0.0231763 - vertex 5.2 -0.925 -3.23904e-18 - vertex 4.8 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 5.6 -1.07133 -0.0231763 - vertex 5.2 -1.07133 -0.0231763 - vertex 5.2 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 5.6 -1.06068 -0.0440839 - vertex 5.2 -1.06068 -0.0440839 - vertex 5.2 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 5.6 -1.04408 -0.0606763 - vertex 5.2 -1.04408 -0.0606763 - vertex 5.2 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 5.6 -1.02318 -0.0713293 - vertex 5.2 -1.02318 -0.0713293 - vertex 5.2 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 5.6 -1 -0.075 - vertex 5.2 -1 -0.075 - vertex 5.2 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 5.2 -0.976824 -0.0713292 - vertex 5.2 -1 -0.075 - vertex 5.6 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 5.2 -0.955916 -0.0606763 - vertex 5.2 -0.976824 -0.0713292 - vertex 5.6 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 5.2 -0.939324 -0.0440839 - vertex 5.2 -0.955916 -0.0606763 - vertex 5.6 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 5.2 -0.928671 -0.0231763 - vertex 5.2 -0.939324 -0.0440839 - vertex 5.6 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 5.2 -0.925 -3.23904e-18 - vertex 5.2 -0.928671 -0.0231763 - vertex 5.6 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 5.2 -1.075 1.32349e-22 - vertex 5.6 -1.075 1.32349e-22 - vertex 5.6 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 5.2 -1.07133 -0.0231763 - vertex 5.6 -1.07133 -0.0231763 - vertex 5.6 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 5.2 -1.06068 -0.0440839 - vertex 5.6 -1.06068 -0.0440839 - vertex 5.6 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 5.2 -1.04408 -0.0606763 - vertex 5.6 -1.04408 -0.0606763 - vertex 5.6 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 5.2 -1.02318 -0.0713293 - vertex 5.6 -1.02318 -0.0713293 - vertex 5.6 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 5.6 -1 -0.075 - vertex 5.6 -0.976824 -0.0713292 - vertex 5.2 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 5.6 -0.976824 -0.0713292 - vertex 5.6 -0.955916 -0.0606763 - vertex 5.2 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 5.6 -0.955916 -0.0606763 - vertex 5.6 -0.939324 -0.0440839 - vertex 5.2 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 5.6 -0.939324 -0.0440839 - vertex 5.6 -0.928671 -0.0231763 - vertex 5.2 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 5.6 -0.928671 -0.0231763 - vertex 5.6 -0.925 -3.23904e-18 - vertex 5.2 -0.925 -3.23904e-18 - endloop - endfacet - facet normal 0 0.987693 0.156407 - outer loop - vertex 6 -1.07133 -0.0231763 - vertex 5.6 -1.07133 -0.0231763 - vertex 5.6 -1.075 1.32349e-22 - endloop - endfacet - facet normal 0 0.891059 0.453888 - outer loop - vertex 6 -1.06068 -0.0440839 - vertex 5.6 -1.06068 -0.0440839 - vertex 5.6 -1.07133 -0.0231763 - endloop - endfacet - facet normal 0 0.706945 0.707269 - outer loop - vertex 6 -1.04408 -0.0606763 - vertex 5.6 -1.04408 -0.0606763 - vertex 5.6 -1.06068 -0.0440839 - endloop - endfacet - facet normal 0 0.454123 0.890939 - outer loop - vertex 6 -1.02318 -0.0713293 - vertex 5.6 -1.02318 -0.0713293 - vertex 5.6 -1.04408 -0.0606763 - endloop - endfacet - facet normal 0 0.156407 0.987693 - outer loop - vertex 6 -1 -0.075 - vertex 5.6 -1 -0.075 - vertex 5.6 -1.02318 -0.0713293 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 5.6 -0.976824 -0.0713292 - vertex 5.6 -1 -0.075 - vertex 6 -1 -0.075 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 5.6 -0.955916 -0.0606763 - vertex 5.6 -0.976824 -0.0713292 - vertex 6 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 5.6 -0.939324 -0.0440839 - vertex 5.6 -0.955916 -0.0606763 - vertex 6 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 5.6 -0.928671 -0.0231763 - vertex 5.6 -0.939324 -0.0440839 - vertex 6 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 5.6 -0.925 -3.23904e-18 - vertex 5.6 -0.928671 -0.0231763 - vertex 6 -0.928671 -0.0231763 - endloop - endfacet - facet normal -0 0.987693 0.156407 - outer loop - vertex 5.6 -1.075 1.32349e-22 - vertex 6 -1.075 1.32349e-22 - vertex 6 -1.07133 -0.0231763 - endloop - endfacet - facet normal -0 0.891059 0.453888 - outer loop - vertex 5.6 -1.07133 -0.0231763 - vertex 6 -1.07133 -0.0231763 - vertex 6 -1.06068 -0.0440839 - endloop - endfacet - facet normal -0 0.706945 0.707269 - outer loop - vertex 5.6 -1.06068 -0.0440839 - vertex 6 -1.06068 -0.0440839 - vertex 6 -1.04408 -0.0606763 - endloop - endfacet - facet normal -0 0.454123 0.890939 - outer loop - vertex 5.6 -1.04408 -0.0606763 - vertex 6 -1.04408 -0.0606763 - vertex 6 -1.02318 -0.0713293 - endloop - endfacet - facet normal -0 0.156407 0.987693 - outer loop - vertex 5.6 -1.02318 -0.0713293 - vertex 6 -1.02318 -0.0713293 - vertex 6 -1 -0.075 - endloop - endfacet - facet normal 0 -0.156438 0.987688 - outer loop - vertex 6 -1 -0.075 - vertex 6 -0.976824 -0.0713292 - vertex 5.6 -0.976824 -0.0713292 - endloop - endfacet - facet normal 0 -0.453982 0.891011 - outer loop - vertex 6 -0.976824 -0.0713292 - vertex 6 -0.955916 -0.0606763 - vertex 5.6 -0.955916 -0.0606763 - endloop - endfacet - facet normal 0 -0.707116 0.707098 - outer loop - vertex 6 -0.955916 -0.0606763 - vertex 6 -0.939324 -0.0440839 - vertex 5.6 -0.939324 -0.0440839 - endloop - endfacet - facet normal 0 -0.891005 0.453993 - outer loop - vertex 6 -0.939324 -0.0440839 - vertex 6 -0.928671 -0.0231763 - vertex 5.6 -0.928671 -0.0231763 - endloop - endfacet - facet normal 0 -0.987687 0.156444 - outer loop - vertex 6 -0.928671 -0.0231763 - vertex 6 -0.925 -3.23904e-18 - vertex 5.6 -0.925 -3.23904e-18 - endloop - endfacet -endsolid walls -solid walls1 - facet normal 0 0.98769 -0.156423 - outer loop - vertex -2 1.5 -4.9133e-17 - vertex -1.6 1.5 -4.9133e-17 - vertex -1.6 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -1.2 1.47553 -0.154509 - vertex -1.6 1.47553 -0.154509 - vertex -1.6 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -1.6 1.47553 -0.154509 - vertex -2 1.47553 -0.154509 - vertex -2 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -1.6 1.5 -4.9133e-17 - vertex -1.2 1.5 -4.9133e-17 - vertex -1.2 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -1.6 1.47553 -0.154509 - vertex -1.2 1.47553 -0.154509 - vertex -1.2 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -2 1.47553 -0.154509 - vertex -1.6 1.47553 -0.154509 - vertex -1.6 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -0.8 1.47553 -0.154509 - vertex -1.2 1.47553 -0.154509 - vertex -1.2 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -0.8 1.40451 -0.293893 - vertex -1.2 1.40451 -0.293893 - vertex -1.2 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -1.2 1.40451 -0.293893 - vertex -1.6 1.40451 -0.293893 - vertex -1.6 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -1.6 1.40451 -0.293893 - vertex -2 1.40451 -0.293893 - vertex -2 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -1.2 1.5 -4.9133e-17 - vertex -0.8 1.5 -4.9133e-17 - vertex -0.8 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -1.2 1.47553 -0.154509 - vertex -0.8 1.47553 -0.154509 - vertex -0.8 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -1.2 1.40451 -0.293893 - vertex -0.8 1.40451 -0.293893 - vertex -0.8 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -1.6 1.40451 -0.293893 - vertex -1.2 1.40451 -0.293893 - vertex -1.2 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -2 1.40451 -0.293893 - vertex -1.6 1.40451 -0.293893 - vertex -1.6 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -0.4 1.47553 -0.154509 - vertex -0.8 1.47553 -0.154509 - vertex -0.8 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -0.4 1.40451 -0.293893 - vertex -0.8 1.40451 -0.293893 - vertex -0.8 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -0.4 1.29389 -0.404509 - vertex -0.8 1.29389 -0.404509 - vertex -0.8 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -0.8 1.29389 -0.404509 - vertex -1.2 1.29389 -0.404509 - vertex -1.2 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -1.2 1.29389 -0.404509 - vertex -1.6 1.29389 -0.404509 - vertex -1.6 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -1.6 1.29389 -0.404509 - vertex -2 1.29389 -0.404509 - vertex -2 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -0.8 1.5 -4.9133e-17 - vertex -0.4 1.5 -4.9133e-17 - vertex -0.4 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -0.8 1.47553 -0.154509 - vertex -0.4 1.47553 -0.154509 - vertex -0.4 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -0.8 1.40451 -0.293893 - vertex -0.4 1.40451 -0.293893 - vertex -0.4 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -0.8 1.29389 -0.404509 - vertex -0.4 1.29389 -0.404509 - vertex -0.4 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -1.2 1.29389 -0.404509 - vertex -0.8 1.29389 -0.404509 - vertex -0.8 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -1.6 1.29389 -0.404509 - vertex -1.2 1.29389 -0.404509 - vertex -1.2 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -2 1.29389 -0.404509 - vertex -1.6 1.29389 -0.404509 - vertex -1.6 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -8.73503e-23 1.47553 -0.154509 - vertex -0.4 1.47553 -0.154509 - vertex -0.4 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -6.88214e-23 1.40451 -0.293893 - vertex -0.4 1.40451 -0.293893 - vertex -0.4 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -5.02926e-23 1.29389 -0.404509 - vertex -0.4 1.29389 -0.404509 - vertex -0.4 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -3.17637e-23 1.15451 -0.475528 - vertex -0.4 1.15451 -0.475528 - vertex -0.4 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -0.4 1.15451 -0.475528 - vertex -0.8 1.15451 -0.475528 - vertex -0.8 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -0.8 1.15451 -0.475528 - vertex -1.2 1.15451 -0.475528 - vertex -1.2 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -1.2 1.15451 -0.475528 - vertex -1.6 1.15451 -0.475528 - vertex -1.6 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -1.6 1.15451 -0.475528 - vertex -2 1.15451 -0.475528 - vertex -2 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.98769 -0.156423 - outer loop - vertex -0.4 1.5 -4.9133e-17 - vertex -1.05879e-22 1.5 -4.9133e-17 - vertex -8.73503e-23 1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891006 -0.453992 - outer loop - vertex -0.4 1.47553 -0.154509 - vertex -8.73503e-23 1.47553 -0.154509 - vertex -6.88214e-23 1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.707094 -0.70712 - outer loop - vertex -0.4 1.40451 -0.293893 - vertex -6.88214e-23 1.40451 -0.293893 - vertex -5.02926e-23 1.29389 -0.404509 - endloop - endfacet - facet normal 0 0.453997 -0.891003 - outer loop - vertex -0.4 1.29389 -0.404509 - vertex -5.02926e-23 1.29389 -0.404509 - vertex -3.17637e-23 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -0.4 1.15451 -0.475528 - vertex -3.17637e-23 1.15451 -0.475528 - vertex -1.32349e-23 1 -0.5 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -0.8 1.15451 -0.475528 - vertex -0.4 1.15451 -0.475528 - vertex -0.4 1 -0.5 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -1.2 1.15451 -0.475528 - vertex -0.8 1.15451 -0.475528 - vertex -0.8 1 -0.5 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -1.6 1.15451 -0.475528 - vertex -1.2 1.15451 -0.475528 - vertex -1.2 1 -0.5 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -2 1.15451 -0.475528 - vertex -1.6 1.15451 -0.475528 - vertex -1.6 1 -0.5 - endloop - endfacet - facet normal 0.181426 0.971299 -0.153827 - outer loop - vertex 0.447729 1.3919 -0.154509 - vertex -8.73503e-23 1.47553 -0.154509 - vertex -1.05879e-22 1.5 -4.9133e-17 - endloop - endfacet - facet normal 0.16417 0.878917 -0.447832 - outer loop - vertex -6.88214e-23 1.40451 -0.293893 - vertex -8.73503e-23 1.47553 -0.154509 - vertex 0.447729 1.3919 -0.154509 - endloop - endfacet - facet normal 0.140034 0.700127 -0.700152 - outer loop - vertex -5.02926e-23 1.29389 -0.404509 - vertex -6.88214e-23 1.40451 -0.293893 - vertex 0.422624 1.31998 -0.293893 - endloop - endfacet - facet normal 0.0899557 0.452157 -0.887391 - outer loop - vertex -3.17637e-23 1.15451 -0.475528 - vertex -5.02926e-23 1.29389 -0.404509 - vertex 0.389599 1.21638 -0.404509 - endloop - endfacet - facet normal 0.0288563 0.156369 -0.987277 - outer loop - vertex -1.32349e-23 1 -0.5 - vertex -3.17637e-23 1.15451 -0.475528 - vertex 0.35082 1.08977 -0.475528 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -1.32349e-23 1 -0.5 - vertex -0.4 1 -0.5 - vertex -0.4 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -0.4 1 -0.5 - vertex -0.8 1 -0.5 - vertex -0.8 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -0.8 1 -0.5 - vertex -1.2 1 -0.5 - vertex -1.2 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -1.2 1 -0.5 - vertex -1.6 1 -0.5 - vertex -1.6 1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.156435 -0.987688 - outer loop - vertex -1.6 1 -0.5 - vertex -2 1 -0.5 - vertex -2 1.15451 -0.475528 - endloop - endfacet - facet normal 0.152204 0.960917 -0.231241 - outer loop - vertex -1.05879e-22 1.5 -4.9133e-17 - vertex 0.463525 1.42658 -3.43825e-17 - vertex 0.447729 1.3919 -0.154509 - endloop - endfacet - facet normal 0.172481 0.862351 -0.476026 - outer loop - vertex 0.447729 1.3919 -0.154509 - vertex 0.422624 1.31998 -0.293893 - vertex -6.88214e-23 1.40451 -0.293893 - endloop - endfacet - facet normal 0.139581 0.701597 -0.69877 - outer loop - vertex 0.422624 1.31998 -0.293893 - vertex 0.389599 1.21638 -0.404509 - vertex -5.02926e-23 1.29389 -0.404509 - endloop - endfacet - facet normal 0.0862132 0.467181 -0.879948 - outer loop - vertex 0.389599 1.21638 -0.404509 - vertex 0.35082 1.08977 -0.475528 - vertex -3.17637e-23 1.15451 -0.475528 - endloop - endfacet - facet normal 0.0262899 0.16599 -0.985777 - outer loop - vertex 0.35082 1.08977 -0.475528 - vertex 0.309017 0.951057 -0.5 - vertex -1.32349e-23 1 -0.5 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -0.4 0.845491 -0.475528 - vertex -0.4 1 -0.5 - vertex -1.32349e-23 1 -0.5 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -0.8 0.845491 -0.475528 - vertex -0.8 1 -0.5 - vertex -0.4 1 -0.5 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -1.2 0.845491 -0.475528 - vertex -1.2 1 -0.5 - vertex -0.8 1 -0.5 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -1.6 0.845491 -0.475528 - vertex -1.6 1 -0.5 - vertex -1.2 1 -0.5 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -2 0.845491 -0.475528 - vertex -2 1 -0.5 - vertex -1.6 1 -0.5 - endloop - endfacet - facet normal 0.453236 0.85873 -0.239081 - outer loop - vertex 0.853111 1.17794 -0.154509 - vertex 0.447729 1.3919 -0.154509 - vertex 0.463525 1.42658 -3.43825e-17 - endloop - endfacet - facet normal 0.410648 0.778039 -0.475419 - outer loop - vertex 0.422624 1.31998 -0.293893 - vertex 0.447729 1.3919 -0.154509 - vertex 0.853111 1.17794 -0.154509 - endloop - endfacet - facet normal 0.339824 0.633688 -0.694952 - outer loop - vertex 0.389599 1.21638 -0.404509 - vertex 0.422624 1.31998 -0.293893 - vertex 0.805924 1.11443 -0.293893 - endloop - endfacet - facet normal 0.226458 0.422829 -0.877458 - outer loop - vertex 0.35082 1.08977 -0.475528 - vertex 0.389599 1.21638 -0.404509 - vertex 0.742899 1.02716 -0.404509 - endloop - endfacet - facet normal 0.0789878 0.150063 -0.985516 - outer loop - vertex 0.309017 0.951057 -0.5 - vertex 0.35082 1.08977 -0.475528 - vertex 0.668367 0.922624 -0.475528 - endloop - endfacet - facet normal -0.0262899 -0.16599 -0.985777 - outer loop - vertex -1.32349e-23 1 -0.5 - vertex 0.309017 0.951057 -0.5 - vertex 0.267214 0.812344 -0.475528 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -0.4 1 -0.5 - vertex -0.4 0.845491 -0.475528 - vertex -0.8 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -1.32349e-23 1 -0.5 - vertex -5.29396e-24 0.845491 -0.475528 - vertex -0.4 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -0.8 1 -0.5 - vertex -0.8 0.845491 -0.475528 - vertex -1.2 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -1.2 1 -0.5 - vertex -1.2 0.845491 -0.475528 - vertex -1.6 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156436 -0.987688 - outer loop - vertex -1.6 1 -0.5 - vertex -1.6 0.845491 -0.475528 - vertex -2 0.845491 -0.475528 - endloop - endfacet - facet normal 0.436106 0.855946 -0.277792 - outer loop - vertex 0.463525 1.42658 -3.43825e-17 - vertex 0.881678 1.21353 -1.96321e-17 - vertex 0.853111 1.17794 -0.154509 - endloop - endfacet - facet normal 0.412073 0.768414 -0.489629 - outer loop - vertex 0.853111 1.17794 -0.154509 - vertex 0.805924 1.11443 -0.293893 - vertex 0.422624 1.31998 -0.293893 - endloop - endfacet - facet normal 0.339826 0.634503 -0.694208 - outer loop - vertex 0.805924 1.11443 -0.293893 - vertex 0.742899 1.02716 -0.404509 - vertex 0.389599 1.21638 -0.404509 - endloop - endfacet - facet normal 0.227037 0.431329 -0.87316 - outer loop - vertex 0.742899 1.02716 -0.404509 - vertex 0.668367 0.922624 -0.475528 - vertex 0.35082 1.08977 -0.475528 - endloop - endfacet - facet normal 0.0793782 0.155788 -0.984596 - outer loop - vertex 0.668367 0.922624 -0.475528 - vertex 0.587785 0.809017 -0.5 - vertex 0.309017 0.951057 -0.5 - endloop - endfacet - facet normal -0.0194016 -0.156406 -0.987502 - outer loop - vertex 0.267214 0.812344 -0.475528 - vertex -5.29396e-24 0.845491 -0.475528 - vertex -1.32349e-23 1 -0.5 - endloop - endfacet - facet normal -0.0738809 -0.151629 -0.985672 - outer loop - vertex 0.507203 0.69541 -0.475528 - vertex 0.267214 0.812344 -0.475528 - vertex 0.309017 0.951057 -0.5 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -0.8 0.706107 -0.404509 - vertex -0.8 0.845491 -0.475528 - vertex -0.4 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -0.4 0.706107 -0.404509 - vertex -0.4 0.845491 -0.475528 - vertex -5.29396e-24 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -1.2 0.706107 -0.404509 - vertex -1.2 0.845491 -0.475528 - vertex -0.8 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -1.6 0.706107 -0.404509 - vertex -1.6 0.845491 -0.475528 - vertex -1.2 0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -2 0.706107 -0.404509 - vertex -2 0.845491 -0.475528 - vertex -1.6 0.845491 -0.475528 - endloop - endfacet - facet normal 0.678467 0.678467 -0.28172 - outer loop - vertex 1.17794 0.853111 -0.154509 - vertex 0.853111 1.17794 -0.154509 - vertex 0.881678 1.21353 -1.96321e-17 - endloop - endfacet - facet normal 0.61654 0.61654 -0.489649 - outer loop - vertex 1.11443 0.805924 -0.293893 - vertex 0.805924 1.11443 -0.293893 - vertex 0.853111 1.17794 -0.154509 - endloop - endfacet - facet normal 0.509906 0.509906 -0.692814 - outer loop - vertex 1.02716 0.742899 -0.404509 - vertex 0.742899 1.02716 -0.404509 - vertex 0.805924 1.11443 -0.293893 - endloop - endfacet - facet normal 0.345909 0.345909 -0.872178 - outer loop - vertex 0.922624 0.668367 -0.475528 - vertex 0.668367 0.922624 -0.475528 - vertex 0.742899 1.02716 -0.404509 - endloop - endfacet - facet normal 0.124067 0.124067 -0.984487 - outer loop - vertex 0.809017 0.587785 -0.5 - vertex 0.587785 0.809017 -0.5 - vertex 0.668367 0.922624 -0.475528 - endloop - endfacet - facet normal -0.0793782 -0.155788 -0.984596 - outer loop - vertex 0.309017 0.951057 -0.5 - vertex 0.587785 0.809017 -0.5 - vertex 0.507203 0.69541 -0.475528 - endloop - endfacet - facet normal -0.0588707 -0.474585 -0.878239 - outer loop - vertex -5.29396e-24 0.845491 -0.475528 - vertex 0.267214 0.812344 -0.475528 - vertex 0.228435 0.685731 -0.404509 - endloop - endfacet - facet normal -0.214278 -0.439772 -0.872173 - outer loop - vertex 0.267214 0.812344 -0.475528 - vertex 0.507203 0.69541 -0.475528 - vertex 0.432671 0.590878 -0.404509 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -0.8 0.845491 -0.475528 - vertex -0.8 0.706107 -0.404509 - vertex -1.2 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -0.4 0.845491 -0.475528 - vertex -0.4 0.706107 -0.404509 - vertex -0.8 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -5.29396e-24 0.845491 -0.475528 - vertex 2.64698e-24 0.706107 -0.404509 - vertex -0.4 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -1.2 0.845491 -0.475528 - vertex -1.2 0.706107 -0.404509 - vertex -1.6 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.453987 -0.891008 - outer loop - vertex -1.6 0.845491 -0.475528 - vertex -1.6 0.706107 -0.404509 - vertex -2 0.706107 -0.404509 - endloop - endfacet - facet normal 0.61654 0.61654 -0.489649 - outer loop - vertex 0.853111 1.17794 -0.154509 - vertex 1.17794 0.853111 -0.154509 - vertex 1.11443 0.805924 -0.293893 - endloop - endfacet - facet normal 0.678467 0.678467 -0.28172 - outer loop - vertex 0.881678 1.21353 -1.96321e-17 - vertex 1.21353 0.881678 -4.88165e-18 - vertex 1.17794 0.853111 -0.154509 - endloop - endfacet - facet normal 0.509906 0.509906 -0.692814 - outer loop - vertex 0.805924 1.11443 -0.293893 - vertex 1.11443 0.805924 -0.293893 - vertex 1.02716 0.742899 -0.404509 - endloop - endfacet - facet normal 0.345909 0.345909 -0.872178 - outer loop - vertex 0.742899 1.02716 -0.404509 - vertex 1.02716 0.742899 -0.404509 - vertex 0.922624 0.668367 -0.475528 - endloop - endfacet - facet normal 0.124067 0.124067 -0.984487 - outer loop - vertex 0.668367 0.922624 -0.475528 - vertex 0.922624 0.668367 -0.475528 - vertex 0.809017 0.587785 -0.5 - endloop - endfacet - facet normal -0.124067 -0.124067 -0.984487 - outer loop - vertex 0.507203 0.69541 -0.475528 - vertex 0.587785 0.809017 -0.5 - vertex 0.809017 0.587785 -0.5 - endloop - endfacet - facet normal -0.0404617 -0.453615 -0.890279 - outer loop - vertex 0.228435 0.685731 -0.404509 - vertex 2.64698e-24 0.706107 -0.404509 - vertex -5.29396e-24 0.845491 -0.475528 - endloop - endfacet - facet normal -0.200553 -0.431829 -0.879376 - outer loop - vertex 0.432671 0.590878 -0.404509 - vertex 0.228435 0.685731 -0.404509 - vertex 0.267214 0.812344 -0.475528 - endloop - endfacet - facet normal -0.345915 -0.345915 -0.872173 - outer loop - vertex 0.432671 0.590878 -0.404509 - vertex 0.507203 0.69541 -0.475528 - vertex 0.69541 0.507203 -0.475528 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -1.2 0.595491 -0.293893 - vertex -1.2 0.706107 -0.404509 - vertex -0.8 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -0.8 0.595491 -0.293893 - vertex -0.8 0.706107 -0.404509 - vertex -0.4 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -0.4 0.595491 -0.293893 - vertex -0.4 0.706107 -0.404509 - vertex 2.64698e-24 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -1.6 0.595491 -0.293893 - vertex -1.6 0.706107 -0.404509 - vertex -1.2 0.706107 -0.404509 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -2 0.595491 -0.293893 - vertex -2 0.706107 -0.404509 - vertex -1.6 0.706107 -0.404509 - endloop - endfacet - facet normal 0.768414 0.412073 -0.489629 - outer loop - vertex 1.31998 0.422624 -0.293893 - vertex 1.11443 0.805924 -0.293893 - vertex 1.17794 0.853111 -0.154509 - endloop - endfacet - facet normal 0.855946 0.436106 -0.277792 - outer loop - vertex 1.17794 0.853111 -0.154509 - vertex 1.21353 0.881678 -4.88165e-18 - vertex 1.42658 0.463525 9.86879e-18 - endloop - endfacet - facet normal 0.634503 0.339826 -0.694208 - outer loop - vertex 1.21638 0.389599 -0.404509 - vertex 1.02716 0.742899 -0.404509 - vertex 1.11443 0.805924 -0.293893 - endloop - endfacet - facet normal 0.431329 0.227037 -0.87316 - outer loop - vertex 1.08977 0.35082 -0.475528 - vertex 0.922624 0.668367 -0.475528 - vertex 1.02716 0.742899 -0.404509 - endloop - endfacet - facet normal 0.155788 0.0793782 -0.984596 - outer loop - vertex 0.951057 0.309017 -0.5 - vertex 0.809017 0.587785 -0.5 - vertex 0.922624 0.668367 -0.475528 - endloop - endfacet - facet normal -0.124067 -0.124067 -0.984487 - outer loop - vertex 0.809017 0.587785 -0.5 - vertex 0.69541 0.507203 -0.475528 - vertex 0.507203 0.69541 -0.475528 - endloop - endfacet - facet normal -0.0641121 -0.718758 -0.692298 - outer loop - vertex 2.64698e-24 0.706107 -0.404509 - vertex 0.228435 0.685731 -0.404509 - vertex 0.19541 0.582133 -0.293893 - endloop - endfacet - facet normal -0.304538 -0.655727 -0.690854 - outer loop - vertex 0.228435 0.685731 -0.404509 - vertex 0.432671 0.590878 -0.404509 - vertex 0.369646 0.503607 -0.293893 - endloop - endfacet - facet normal -0.345915 -0.345915 -0.872173 - outer loop - vertex 0.69541 0.507203 -0.475528 - vertex 0.590878 0.432671 -0.404509 - vertex 0.432671 0.590878 -0.404509 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -1.2 0.706107 -0.404509 - vertex -1.2 0.595491 -0.293893 - vertex -1.6 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -0.8 0.706107 -0.404509 - vertex -0.8 0.595491 -0.293893 - vertex -1.2 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -0.4 0.706107 -0.404509 - vertex -0.4 0.595491 -0.293893 - vertex -0.8 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex 2.64698e-24 0.706107 -0.404509 - vertex 1.05879e-23 0.595491 -0.293893 - vertex -0.4 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.707107 -0.707107 - outer loop - vertex -1.6 0.706107 -0.404509 - vertex -1.6 0.595491 -0.293893 - vertex -2 0.595491 -0.293893 - endloop - endfacet - facet normal 0.633688 0.339824 -0.694952 - outer loop - vertex 1.11443 0.805924 -0.293893 - vertex 1.31998 0.422624 -0.293893 - vertex 1.21638 0.389599 -0.404509 - endloop - endfacet - facet normal 0.778039 0.410648 -0.475419 - outer loop - vertex 1.17794 0.853111 -0.154509 - vertex 1.3919 0.447729 -0.154509 - vertex 1.31998 0.422624 -0.293893 - endloop - endfacet - facet normal 0.85873 0.453236 -0.239081 - outer loop - vertex 1.42658 0.463525 9.86879e-18 - vertex 1.3919 0.447729 -0.154509 - vertex 1.17794 0.853111 -0.154509 - endloop - endfacet - facet normal 0.422829 0.226458 -0.877458 - outer loop - vertex 1.02716 0.742899 -0.404509 - vertex 1.21638 0.389599 -0.404509 - vertex 1.08977 0.35082 -0.475528 - endloop - endfacet - facet normal 0.150063 0.0789878 -0.985516 - outer loop - vertex 0.922624 0.668367 -0.475528 - vertex 1.08977 0.35082 -0.475528 - vertex 0.951057 0.309017 -0.5 - endloop - endfacet - facet normal -0.155788 -0.0793782 -0.984596 - outer loop - vertex 0.69541 0.507203 -0.475528 - vertex 0.809017 0.587785 -0.5 - vertex 0.951057 0.309017 -0.5 - endloop - endfacet - facet normal -0.0482806 -0.706282 -0.706282 - outer loop - vertex 0.19541 0.582133 -0.293893 - vertex 1.05879e-23 0.595491 -0.293893 - vertex 2.64698e-24 0.706107 -0.404509 - endloop - endfacet - facet normal -0.293971 -0.652273 -0.698656 - outer loop - vertex 0.369646 0.503607 -0.293893 - vertex 0.19541 0.582133 -0.293893 - vertex 0.228435 0.685731 -0.404509 - endloop - endfacet - facet normal -0.509904 -0.509904 -0.692817 - outer loop - vertex 0.369646 0.503607 -0.293893 - vertex 0.432671 0.590878 -0.404509 - vertex 0.590878 0.432671 -0.404509 - endloop - endfacet - facet normal -0.439772 -0.214278 -0.872173 - outer loop - vertex 0.590878 0.432671 -0.404509 - vertex 0.69541 0.507203 -0.475528 - vertex 0.812344 0.267214 -0.475528 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -1.6 0.524472 -0.154509 - vertex -1.6 0.595491 -0.293893 - vertex -1.2 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -1.2 0.524472 -0.154509 - vertex -1.2 0.595491 -0.293893 - vertex -0.8 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -0.8 0.524472 -0.154509 - vertex -0.8 0.595491 -0.293893 - vertex -0.4 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -0.4 0.524472 -0.154509 - vertex -0.4 0.595491 -0.293893 - vertex 1.05879e-23 0.595491 -0.293893 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -2 0.524472 -0.154509 - vertex -2 0.595491 -0.293893 - vertex -1.6 0.595491 -0.293893 - endloop - endfacet - facet normal 0.701597 0.139581 -0.69877 - outer loop - vertex 1.29389 4.23516e-23 -0.404509 - vertex 1.21638 0.389599 -0.404509 - vertex 1.31998 0.422624 -0.293893 - endloop - endfacet - facet normal 0.862351 0.172481 -0.476026 - outer loop - vertex 1.40451 6.35275e-23 -0.293893 - vertex 1.31998 0.422624 -0.293893 - vertex 1.3919 0.447729 -0.154509 - endloop - endfacet - facet normal 0.960917 0.152204 -0.231241 - outer loop - vertex 1.3919 0.447729 -0.154509 - vertex 1.42658 0.463525 9.86879e-18 - vertex 1.5 1.05879e-22 2.46192e-17 - endloop - endfacet - facet normal 0.467181 0.0862132 -0.879948 - outer loop - vertex 1.15451 2.11758e-23 -0.475528 - vertex 1.08977 0.35082 -0.475528 - vertex 1.21638 0.389599 -0.404509 - endloop - endfacet - facet normal 0.16599 0.0262899 -0.985777 - outer loop - vertex 1 0 -0.5 - vertex 0.951057 0.309017 -0.5 - vertex 1.08977 0.35082 -0.475528 - endloop - endfacet - facet normal -0.151629 -0.0738809 -0.985672 - outer loop - vertex 0.951057 0.309017 -0.5 - vertex 0.812344 0.267214 -0.475528 - vertex 0.69541 0.507203 -0.475528 - endloop - endfacet - facet normal -0.0603321 -0.882579 -0.466277 - outer loop - vertex 1.05879e-23 0.595491 -0.293893 - vertex 0.19541 0.582133 -0.293893 - vertex 0.170305 0.510211 -0.154509 - endloop - endfacet - facet normal -0.359335 -0.797304 -0.484959 - outer loop - vertex 0.19541 0.582133 -0.293893 - vertex 0.369646 0.503607 -0.293893 - vertex 0.32246 0.440093 -0.154509 - endloop - endfacet - facet normal -0.509904 -0.509904 -0.692817 - outer loop - vertex 0.590878 0.432671 -0.404509 - vertex 0.503607 0.369646 -0.293893 - vertex 0.369646 0.503607 -0.293893 - endloop - endfacet - facet normal -0.431829 -0.200553 -0.879376 - outer loop - vertex 0.812344 0.267214 -0.475528 - vertex 0.685731 0.228435 -0.404509 - vertex 0.590878 0.432671 -0.404509 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -1.6 0.595491 -0.293893 - vertex -1.6 0.524472 -0.154509 - vertex -2 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -1.2 0.595491 -0.293893 - vertex -1.2 0.524472 -0.154509 - vertex -1.6 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -0.8 0.595491 -0.293893 - vertex -0.8 0.524472 -0.154509 - vertex -1.2 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex -0.4 0.595491 -0.293893 - vertex -0.4 0.524472 -0.154509 - vertex -0.8 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.891008 -0.453987 - outer loop - vertex 1.05879e-23 0.595491 -0.293893 - vertex 1.85288e-23 0.524472 -0.154509 - vertex -0.4 0.524472 -0.154509 - endloop - endfacet - facet normal 0.452157 0.0899557 -0.887391 - outer loop - vertex 1.21638 0.389599 -0.404509 - vertex 1.29389 4.23516e-23 -0.404509 - vertex 1.15451 2.11758e-23 -0.475528 - endloop - endfacet - facet normal 0.700127 0.140034 -0.700152 - outer loop - vertex 1.31998 0.422624 -0.293893 - vertex 1.40451 6.35275e-23 -0.293893 - vertex 1.29389 4.23516e-23 -0.404509 - endloop - endfacet - facet normal 0.878917 0.16417 -0.447832 - outer loop - vertex 1.3919 0.447729 -0.154509 - vertex 1.47553 8.47033e-23 -0.154509 - vertex 1.40451 6.35275e-23 -0.293893 - endloop - endfacet - facet normal 0.971299 0.181426 -0.153827 - outer loop - vertex 1.5 1.05879e-22 2.46192e-17 - vertex 1.47553 8.47033e-23 -0.154509 - vertex 1.3919 0.447729 -0.154509 - endloop - endfacet - facet normal 0.156369 0.0288563 -0.987277 - outer loop - vertex 1.08977 0.35082 -0.475528 - vertex 1.15451 2.11758e-23 -0.475528 - vertex 1 0 -0.5 - endloop - endfacet - facet normal -0.16599 -0.0262899 -0.985777 - outer loop - vertex 0.812344 0.267214 -0.475528 - vertex 0.951057 0.309017 -0.5 - vertex 1 0 -0.5 - endloop - endfacet - facet normal -0.0744045 -0.888539 -0.452729 - outer loop - vertex 0.170305 0.510211 -0.154509 - vertex 1.85288e-23 0.524472 -0.154509 - vertex 1.05879e-23 0.595491 -0.293893 - endloop - endfacet - facet normal -0.367648 -0.79779 -0.477877 - outer loop - vertex 0.32246 0.440093 -0.154509 - vertex 0.170305 0.510211 -0.154509 - vertex 0.19541 0.582133 -0.293893 - endloop - endfacet - facet normal -0.616536 -0.616536 -0.489659 - outer loop - vertex 0.32246 0.440093 -0.154509 - vertex 0.369646 0.503607 -0.293893 - vertex 0.503607 0.369646 -0.293893 - endloop - endfacet - facet normal -0.655727 -0.304538 -0.690854 - outer loop - vertex 0.503607 0.369646 -0.293893 - vertex 0.590878 0.432671 -0.404509 - vertex 0.685731 0.228435 -0.404509 - endloop - endfacet - facet normal -0.474585 -0.0588707 -0.878239 - outer loop - vertex 0.685731 0.228435 -0.404509 - vertex 0.812344 0.267214 -0.475528 - vertex 0.845491 -2.64698e-24 -0.475528 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -2 0.5 -5.29396e-23 - vertex -2 0.524472 -0.154509 - vertex -1.6 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -1.6 0.5 -5.29396e-23 - vertex -1.6 0.524472 -0.154509 - vertex -1.2 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -1.2 0.5 -5.29396e-23 - vertex -1.2 0.524472 -0.154509 - vertex -0.8 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -0.8 0.5 -5.29396e-23 - vertex -0.8 0.524472 -0.154509 - vertex -0.4 0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -0.4 0.5 -5.29396e-23 - vertex -0.4 0.524472 -0.154509 - vertex 1.85288e-23 0.524472 -0.154509 - endloop - endfacet - facet normal 0.453625 0.0404706 -0.890273 - outer loop - vertex 1.15451 2.11758e-23 -0.475528 - vertex 1.29389 4.23516e-23 -0.404509 - vertex 1.31427 -0.228435 -0.404509 - endloop - endfacet - facet normal 0.706269 0.048287 -0.706295 - outer loop - vertex 1.29389 4.23516e-23 -0.404509 - vertex 1.40451 6.35275e-23 -0.293893 - vertex 1.41787 -0.19541 -0.293893 - endloop - endfacet - facet normal 0.888536 0.0743987 -0.452734 - outer loop - vertex 1.40451 6.35275e-23 -0.293893 - vertex 1.47553 8.47033e-23 -0.154509 - vertex 1.48979 -0.170305 -0.154509 - endloop - endfacet - facet normal 0.975824 0.154544 -0.154544 - outer loop - vertex 1.47553 8.47033e-23 -0.154509 - vertex 1.5 1.05879e-22 2.46192e-17 - vertex 1.52447 -0.154509 2.09388e-17 - endloop - endfacet - facet normal 0.156405 0.0194033 -0.987502 - outer loop - vertex 1 0 -0.5 - vertex 1.15451 2.11758e-23 -0.475528 - vertex 1.18766 -0.267214 -0.475528 - endloop - endfacet - facet normal -0.156406 -0.0194016 -0.987502 - outer loop - vertex 1 0 -0.5 - vertex 0.845491 -2.64698e-24 -0.475528 - vertex 0.812344 0.267214 -0.475528 - endloop - endfacet - facet normal -0.0812831 -0.970683 -0.226201 - outer loop - vertex 1.85288e-23 0.524472 -0.154509 - vertex 0.170305 0.510211 -0.154509 - vertex 0.154509 0.475528 -4.10282e-23 - endloop - endfacet - facet normal -0.402338 -0.873067 -0.275459 - outer loop - vertex 0.170305 0.510211 -0.154509 - vertex 0.32246 0.440093 -0.154509 - vertex 0.293893 0.404509 -2.91168e-23 - endloop - endfacet - facet normal -0.616536 -0.616536 -0.489659 - outer loop - vertex 0.503607 0.369646 -0.293893 - vertex 0.440093 0.32246 -0.154509 - vertex 0.32246 0.440093 -0.154509 - endloop - endfacet - facet normal -0.652273 -0.293971 -0.698656 - outer loop - vertex 0.685731 0.228435 -0.404509 - vertex 0.582133 0.19541 -0.293893 - vertex 0.503607 0.369646 -0.293893 - endloop - endfacet - facet normal -0.453615 -0.0404617 -0.890279 - outer loop - vertex 0.845491 -2.64698e-24 -0.475528 - vertex 0.706107 -5.29396e-24 -0.404509 - vertex 0.685731 0.228435 -0.404509 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -1.6 0.524472 -0.154509 - vertex -1.6 0.5 -5.29396e-23 - vertex -2 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -1.2 0.524472 -0.154509 - vertex -1.2 0.5 -5.29396e-23 - vertex -1.6 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -0.8 0.524472 -0.154509 - vertex -0.8 0.5 -5.29396e-23 - vertex -1.2 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex -0.4 0.524472 -0.154509 - vertex -0.4 0.5 -5.29396e-23 - vertex -0.8 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0 -0.987688 -0.156436 - outer loop - vertex 1.85288e-23 0.524472 -0.154509 - vertex 2.64698e-23 0.5 -5.29396e-23 - vertex -0.4 0.5 -5.29396e-23 - endloop - endfacet - facet normal 0.718749 0.0641238 -0.692306 - outer loop - vertex 1.41787 -0.19541 -0.293893 - vertex 1.31427 -0.228435 -0.404509 - vertex 1.29389 4.23516e-23 -0.404509 - endloop - endfacet - facet normal 0.474592 0.0588768 -0.878234 - outer loop - vertex 1.31427 -0.228435 -0.404509 - vertex 1.18766 -0.267214 -0.475528 - vertex 1.15451 2.11758e-23 -0.475528 - endloop - endfacet - facet normal 0.882584 0.0603415 -0.466267 - outer loop - vertex 1.48979 -0.170305 -0.154509 - vertex 1.41787 -0.19541 -0.293893 - vertex 1.40451 6.35275e-23 -0.293893 - endloop - endfacet - facet normal 0.970688 0.0812774 -0.226183 - outer loop - vertex 1.52447 -0.154509 2.09388e-17 - vertex 1.48979 -0.170305 -0.154509 - vertex 1.47553 8.47033e-23 -0.154509 - endloop - endfacet - facet normal 0.165982 0.0262871 -0.985778 - outer loop - vertex 1.18766 -0.267214 -0.475528 - vertex 1.04894 -0.309017 -0.5 - vertex 1 0 -0.5 - endloop - endfacet - facet normal -0.15637 -0.0288565 -0.987277 - outer loop - vertex 0.910231 -0.35082 -0.475528 - vertex 0.845491 -2.64698e-24 -0.475528 - vertex 1 0 -0.5 - endloop - endfacet - facet normal -0.154556 -0.97582 -0.154556 - outer loop - vertex 0.154509 0.475528 -4.10282e-23 - vertex 2.64698e-23 0.5 -5.29396e-23 - vertex 1.85288e-23 0.524472 -0.154509 - endloop - endfacet - facet normal -0.440801 -0.865129 -0.239262 - outer loop - vertex 0.293893 0.404509 -2.91168e-23 - vertex 0.154509 0.475528 -4.10282e-23 - vertex 0.170305 0.510211 -0.154509 - endloop - endfacet - facet normal -0.678472 -0.678472 -0.281696 - outer loop - vertex 0.293893 0.404509 -2.91168e-23 - vertex 0.32246 0.440093 -0.154509 - vertex 0.440093 0.32246 -0.154509 - endloop - endfacet - facet normal -0.797304 -0.359335 -0.484959 - outer loop - vertex 0.440093 0.32246 -0.154509 - vertex 0.503607 0.369646 -0.293893 - vertex 0.582133 0.19541 -0.293893 - endloop - endfacet - facet normal -0.718758 -0.0641121 -0.692298 - outer loop - vertex 0.582133 0.19541 -0.293893 - vertex 0.685731 0.228435 -0.404509 - vertex 0.706107 -5.29396e-24 -0.404509 - endloop - endfacet - facet normal -0.452146 -0.0899548 -0.887396 - outer loop - vertex 0.783618 -0.389599 -0.404509 - vertex 0.706107 -5.29396e-24 -0.404509 - vertex 0.845491 -2.64698e-24 -0.475528 - endloop - endfacet - facet normal 0.652275 0.29395 -0.698664 - outer loop - vertex 1.31427 -0.228435 -0.404509 - vertex 1.41787 -0.19541 -0.293893 - vertex 1.49639 -0.369646 -0.293893 - endloop - endfacet - facet normal 0.431837 0.200551 -0.879372 - outer loop - vertex 1.18766 -0.267214 -0.475528 - vertex 1.31427 -0.228435 -0.404509 - vertex 1.40912 -0.432671 -0.404509 - endloop - endfacet - facet normal 0.79779 0.367659 -0.477868 - outer loop - vertex 1.41787 -0.19541 -0.293893 - vertex 1.48979 -0.170305 -0.154509 - vertex 1.55991 -0.32246 -0.154509 - endloop - endfacet - facet normal 0.86513 0.440808 -0.239246 - outer loop - vertex 1.48979 -0.170305 -0.154509 - vertex 1.52447 -0.154509 2.09388e-17 - vertex 1.59549 -0.293893 1.72583e-17 - endloop - endfacet - facet normal 0.151623 0.0738755 -0.985674 - outer loop - vertex 1.04894 -0.309017 -0.5 - vertex 1.18766 -0.267214 -0.475528 - vertex 1.30459 -0.507203 -0.475528 - endloop - endfacet - facet normal -0.165995 -0.0262891 -0.985776 - outer loop - vertex 1 0 -0.5 - vertex 1.04894 -0.309017 -0.5 - vertex 0.910231 -0.35082 -0.475528 - endloop - endfacet - facet normal -0.467173 -0.0862117 -0.879953 - outer loop - vertex 0.845491 -2.64698e-24 -0.475528 - vertex 0.910231 -0.35082 -0.475528 - vertex 0.783618 -0.389599 -0.404509 - endloop - endfacet - facet normal -0.678472 -0.678472 -0.281696 - outer loop - vertex 0.440093 0.32246 -0.154509 - vertex 0.404509 0.293893 -1.72054e-23 - vertex 0.293893 0.404509 -2.91168e-23 - endloop - endfacet - facet normal -0.79779 -0.367648 -0.477877 - outer loop - vertex 0.582133 0.19541 -0.293893 - vertex 0.510211 0.170305 -0.154509 - vertex 0.440093 0.32246 -0.154509 - endloop - endfacet - facet normal -0.706282 -0.0482806 -0.706282 - outer loop - vertex 0.706107 -5.29396e-24 -0.404509 - vertex 0.595491 -7.94093e-24 -0.293893 - vertex 0.582133 0.19541 -0.293893 - endloop - endfacet - facet normal -0.701603 -0.139584 -0.698763 - outer loop - vertex 0.706107 -5.29396e-24 -0.404509 - vertex 0.783618 -0.389599 -0.404509 - vertex 0.68002 -0.422624 -0.293893 - endloop - endfacet - facet normal 0.797302 0.359306 -0.484983 - outer loop - vertex 1.55991 -0.32246 -0.154509 - vertex 1.49639 -0.369646 -0.293893 - vertex 1.41787 -0.19541 -0.293893 - endloop - endfacet - facet normal 0.655734 0.304532 -0.69085 - outer loop - vertex 1.49639 -0.369646 -0.293893 - vertex 1.40912 -0.432671 -0.404509 - vertex 1.31427 -0.228435 -0.404509 - endloop - endfacet - facet normal 0.439781 0.214275 -0.872169 - outer loop - vertex 1.40912 -0.432671 -0.404509 - vertex 1.30459 -0.507203 -0.475528 - vertex 1.18766 -0.267214 -0.475528 - endloop - endfacet - facet normal 0.873068 0.40235 -0.275438 - outer loop - vertex 1.59549 -0.293893 1.72583e-17 - vertex 1.55991 -0.32246 -0.154509 - vertex 1.48979 -0.170305 -0.154509 - endloop - endfacet - facet normal 0.155785 0.0793767 -0.984597 - outer loop - vertex 1.30459 -0.507203 -0.475528 - vertex 1.19098 -0.587785 -0.5 - vertex 1.04894 -0.309017 -0.5 - endloop - endfacet - facet normal -0.150066 -0.078991 -0.985515 - outer loop - vertex 1.07738 -0.668367 -0.475528 - vertex 0.910231 -0.35082 -0.475528 - vertex 1.04894 -0.309017 -0.5 - endloop - endfacet - facet normal -0.42282 -0.226461 -0.877462 - outer loop - vertex 0.972844 -0.742899 -0.404509 - vertex 0.783618 -0.389599 -0.404509 - vertex 0.910231 -0.35082 -0.475528 - endloop - endfacet - facet normal -0.873067 -0.402338 -0.275459 - outer loop - vertex 0.404509 0.293893 -1.72054e-23 - vertex 0.440093 0.32246 -0.154509 - vertex 0.510211 0.170305 -0.154509 - endloop - endfacet - facet normal -0.882579 -0.0603321 -0.466277 - outer loop - vertex 0.510211 0.170305 -0.154509 - vertex 0.582133 0.19541 -0.293893 - vertex 0.595491 -7.94093e-24 -0.293893 - endloop - endfacet - facet normal -0.700139 -0.140035 -0.700139 - outer loop - vertex 0.68002 -0.422624 -0.293893 - vertex 0.595491 -7.94093e-24 -0.293893 - vertex 0.706107 -5.29396e-24 -0.404509 - endloop - endfacet - facet normal -0.633692 -0.339831 -0.694946 - outer loop - vertex 0.885573 -0.805924 -0.293893 - vertex 0.68002 -0.422624 -0.293893 - vertex 0.783618 -0.389599 -0.404509 - endloop - endfacet - facet normal 0.61653 0.616526 -0.489679 - outer loop - vertex 1.63035 -0.503607 -0.293893 - vertex 1.49639 -0.369646 -0.293893 - vertex 1.55991 -0.32246 -0.154509 - endloop - endfacet - facet normal 0.509908 0.509904 -0.692814 - outer loop - vertex 1.40912 -0.432671 -0.404509 - vertex 1.49639 -0.369646 -0.293893 - vertex 1.63035 -0.503607 -0.293893 - endloop - endfacet - facet normal 0.345915 0.345921 -0.87217 - outer loop - vertex 1.30459 -0.507203 -0.475528 - vertex 1.40912 -0.432671 -0.404509 - vertex 1.56733 -0.590878 -0.404509 - endloop - endfacet - facet normal 0.678484 0.678466 -0.28168 - outer loop - vertex 1.67754 -0.440093 -0.154509 - vertex 1.55991 -0.32246 -0.154509 - vertex 1.59549 -0.293893 1.72583e-17 - endloop - endfacet - facet normal 0.124065 0.124064 -0.984488 - outer loop - vertex 1.41221 -0.809017 -0.5 - vertex 1.19098 -0.587785 -0.5 - vertex 1.30459 -0.507203 -0.475528 - endloop - endfacet - facet normal -0.155795 -0.0793816 -0.984595 - outer loop - vertex 1.04894 -0.309017 -0.5 - vertex 1.19098 -0.587785 -0.5 - vertex 1.07738 -0.668367 -0.475528 - endloop - endfacet - facet normal -0.431328 -0.22704 -0.873161 - outer loop - vertex 0.910231 -0.35082 -0.475528 - vertex 1.07738 -0.668367 -0.475528 - vertex 0.972844 -0.742899 -0.404509 - endloop - endfacet - facet normal -0.634495 -0.339833 -0.694212 - outer loop - vertex 0.783618 -0.389599 -0.404509 - vertex 0.972844 -0.742899 -0.404509 - vertex 0.885573 -0.805924 -0.293893 - endloop - endfacet - facet normal -0.865129 -0.440801 -0.239262 - outer loop - vertex 0.510211 0.170305 -0.154509 - vertex 0.475528 0.154509 -5.29396e-24 - vertex 0.404509 0.293893 -1.72054e-23 - endloop - endfacet - facet normal -0.888539 -0.0744045 -0.452729 - outer loop - vertex 0.595491 -7.94093e-24 -0.293893 - vertex 0.524472 -1.05879e-23 -0.154509 - vertex 0.510211 0.170305 -0.154509 - endloop - endfacet - facet normal -0.862347 -0.172478 -0.476036 - outer loop - vertex 0.595491 -7.94093e-24 -0.293893 - vertex 0.68002 -0.422624 -0.293893 - vertex 0.608098 -0.447729 -0.154509 - endloop - endfacet - facet normal -0.768403 -0.412073 -0.489646 - outer loop - vertex 0.68002 -0.422624 -0.293893 - vertex 0.885573 -0.805924 -0.293893 - vertex 0.822059 -0.853111 -0.154509 - endloop - endfacet - facet normal 0.61654 0.616523 -0.489671 - outer loop - vertex 1.55991 -0.32246 -0.154509 - vertex 1.67754 -0.440093 -0.154509 - vertex 1.63035 -0.503607 -0.293893 - endloop - endfacet - facet normal 0.509907 0.509917 -0.692805 - outer loop - vertex 1.63035 -0.503607 -0.293893 - vertex 1.56733 -0.590878 -0.404509 - vertex 1.40912 -0.432671 -0.404509 - endloop - endfacet - facet normal 0.345915 0.34592 -0.872171 - outer loop - vertex 1.56733 -0.590878 -0.404509 - vertex 1.4928 -0.69541 -0.475528 - vertex 1.30459 -0.507203 -0.475528 - endloop - endfacet - facet normal 0.678456 0.678481 -0.281709 - outer loop - vertex 1.59549 -0.293893 1.72583e-17 - vertex 1.70611 -0.404509 1.35778e-17 - vertex 1.67754 -0.440093 -0.154509 - endloop - endfacet - facet normal 0.12406 0.124062 -0.984488 - outer loop - vertex 1.30459 -0.507203 -0.475528 - vertex 1.4928 -0.69541 -0.475528 - vertex 1.41221 -0.809017 -0.5 - endloop - endfacet - facet normal -0.124071 -0.12407 -0.984486 - outer loop - vertex 1.07738 -0.668367 -0.475528 - vertex 1.19098 -0.587785 -0.5 - vertex 1.41221 -0.809017 -0.5 - endloop - endfacet - facet normal -0.345913 -0.345904 -0.872178 - outer loop - vertex 0.972844 -0.742899 -0.404509 - vertex 1.07738 -0.668367 -0.475528 - vertex 1.33163 -0.922624 -0.475528 - endloop - endfacet - facet normal -0.509909 -0.5099 -0.692817 - outer loop - vertex 0.885573 -0.805924 -0.293893 - vertex 0.972844 -0.742899 -0.404509 - vertex 1.2571 -1.02716 -0.404509 - endloop - endfacet - facet normal -0.970683 -0.0812831 -0.226201 - outer loop - vertex 0.475528 0.154509 -5.29396e-24 - vertex 0.510211 0.170305 -0.154509 - vertex 0.524472 -1.05879e-23 -0.154509 - endloop - endfacet - facet normal -0.87892 -0.164163 -0.447828 - outer loop - vertex 0.608098 -0.447729 -0.154509 - vertex 0.524472 -1.05879e-23 -0.154509 - vertex 0.595491 -7.94093e-24 -0.293893 - endloop - endfacet - facet normal -0.778034 -0.410647 -0.475428 - outer loop - vertex 0.822059 -0.853111 -0.154509 - vertex 0.608098 -0.447729 -0.154509 - vertex 0.68002 -0.422624 -0.293893 - endloop - endfacet - facet normal -0.616533 -0.616537 -0.489662 - outer loop - vertex 1.14689 -1.17794 -0.154509 - vertex 0.822059 -0.853111 -0.154509 - vertex 0.885573 -0.805924 -0.293893 - endloop - endfacet - facet normal 0.359327 0.797303 -0.484966 - outer loop - vertex 1.80459 -0.582133 -0.293893 - vertex 1.63035 -0.503607 -0.293893 - vertex 1.67754 -0.440093 -0.154509 - endloop - endfacet - facet normal 0.304548 0.655729 -0.690847 - outer loop - vertex 1.77156 -0.685731 -0.404509 - vertex 1.56733 -0.590878 -0.404509 - vertex 1.63035 -0.503607 -0.293893 - endloop - endfacet - facet normal 0.214278 0.439775 -0.872171 - outer loop - vertex 1.73279 -0.812344 -0.475528 - vertex 1.4928 -0.69541 -0.475528 - vertex 1.56733 -0.590878 -0.404509 - endloop - endfacet - facet normal 0.402326 0.873071 -0.275465 - outer loop - vertex 1.8297 -0.510211 -0.154509 - vertex 1.67754 -0.440093 -0.154509 - vertex 1.70611 -0.404509 1.35778e-17 - endloop - endfacet - facet normal 0.0793753 0.155784 -0.984597 - outer loop - vertex 1.69098 -0.951056 -0.5 - vertex 1.41221 -0.809017 -0.5 - vertex 1.4928 -0.69541 -0.475528 - endloop - endfacet - facet normal -0.12407 -0.124066 -0.984487 - outer loop - vertex 1.41221 -0.809017 -0.5 - vertex 1.33163 -0.922624 -0.475528 - vertex 1.07738 -0.668367 -0.475528 - endloop - endfacet - facet normal -0.345915 -0.345909 -0.872175 - outer loop - vertex 1.33163 -0.922624 -0.475528 - vertex 1.2571 -1.02716 -0.404509 - vertex 0.972844 -0.742899 -0.404509 - endloop - endfacet - facet normal -0.509914 -0.509915 -0.692802 - outer loop - vertex 1.2571 -1.02716 -0.404509 - vertex 1.19408 -1.11443 -0.293893 - vertex 0.885573 -0.805924 -0.293893 - endloop - endfacet - facet normal -0.97582 -0.154556 -0.154556 - outer loop - vertex 0.524472 -1.05879e-23 -0.154509 - vertex 0.5 -1.32349e-23 6.61744e-24 - vertex 0.475528 0.154509 -5.29396e-24 - endloop - endfacet - facet normal -0.971299 -0.181417 -0.15384 - outer loop - vertex 0.5 -1.32349e-23 6.61744e-24 - vertex 0.524472 -1.05879e-23 -0.154509 - vertex 0.608098 -0.447729 -0.154509 - endloop - endfacet - facet normal -0.858726 -0.453236 -0.239096 - outer loop - vertex 0.573415 -0.463525 2.64698e-23 - vertex 0.608098 -0.447729 -0.154509 - vertex 0.822059 -0.853111 -0.154509 - endloop - endfacet - facet normal -0.678469 -0.678474 -0.281696 - outer loop - vertex 0.786475 -0.881678 4.63221e-23 - vertex 0.822059 -0.853111 -0.154509 - vertex 1.14689 -1.17794 -0.154509 - endloop - endfacet - facet normal -0.616535 -0.616537 -0.489659 - outer loop - vertex 0.885573 -0.805924 -0.293893 - vertex 1.19408 -1.11443 -0.293893 - vertex 1.14689 -1.17794 -0.154509 - endloop - endfacet - facet normal 0.367635 0.797789 -0.477888 - outer loop - vertex 1.67754 -0.440093 -0.154509 - vertex 1.8297 -0.510211 -0.154509 - vertex 1.80459 -0.582133 -0.293893 - endloop - endfacet - facet normal 0.293963 0.652269 -0.698664 - outer loop - vertex 1.63035 -0.503607 -0.293893 - vertex 1.80459 -0.582133 -0.293893 - vertex 1.77156 -0.685731 -0.404509 - endloop - endfacet - facet normal 0.200563 0.431837 -0.87937 - outer loop - vertex 1.56733 -0.590878 -0.404509 - vertex 1.77156 -0.685731 -0.404509 - vertex 1.73279 -0.812344 -0.475528 - endloop - endfacet - facet normal 0.0738795 0.151627 -0.985673 - outer loop - vertex 1.4928 -0.69541 -0.475528 - vertex 1.73279 -0.812344 -0.475528 - vertex 1.69098 -0.951056 -0.5 - endloop - endfacet - facet normal 0.440813 0.865127 -0.239246 - outer loop - vertex 1.70611 -0.404509 1.35778e-17 - vertex 1.84549 -0.475528 9.89734e-18 - vertex 1.8297 -0.510211 -0.154509 - endloop - endfacet - facet normal -0.0793779 -0.155789 -0.984596 - outer loop - vertex 1.33163 -0.922624 -0.475528 - vertex 1.41221 -0.809017 -0.5 - vertex 1.69098 -0.951056 -0.5 - endloop - endfacet - facet normal -0.227037 -0.431333 -0.873159 - outer loop - vertex 1.2571 -1.02716 -0.404509 - vertex 1.33163 -0.922624 -0.475528 - vertex 1.64918 -1.08977 -0.475528 - endloop - endfacet - facet normal -0.33983 -0.634509 -0.6942 - outer loop - vertex 1.19408 -1.11443 -0.293893 - vertex 1.2571 -1.02716 -0.404509 - vertex 1.6104 -1.21638 -0.404509 - endloop - endfacet - facet normal -0.960915 -0.152194 -0.231258 - outer loop - vertex 0.608098 -0.447729 -0.154509 - vertex 0.573415 -0.463525 2.64698e-23 - vertex 0.5 -1.32349e-23 6.61744e-24 - endloop - endfacet - facet normal -0.855945 -0.436127 -0.277762 - outer loop - vertex 0.822059 -0.853111 -0.154509 - vertex 0.786475 -0.881678 4.63221e-23 - vertex 0.573415 -0.463525 2.64698e-23 - endloop - endfacet - facet normal -0.678471 -0.678457 -0.281732 - outer loop - vertex 1.14689 -1.17794 -0.154509 - vertex 1.11832 -1.21353 6.61744e-23 - vertex 0.786475 -0.881678 4.63221e-23 - endloop - endfacet - facet normal -0.412071 -0.76841 -0.489636 - outer loop - vertex 1.14689 -1.17794 -0.154509 - vertex 1.19408 -1.11443 -0.293893 - vertex 1.57738 -1.31998 -0.293893 - endloop - endfacet - facet normal 0.060332 0.882578 -0.466278 - outer loop - vertex 2 -0.595491 -0.293893 - vertex 1.80459 -0.582133 -0.293893 - vertex 1.8297 -0.510211 -0.154509 - endloop - endfacet - facet normal 0.0641105 0.718757 -0.692299 - outer loop - vertex 2 -0.706107 -0.404509 - vertex 1.77156 -0.685731 -0.404509 - vertex 1.80459 -0.582133 -0.293893 - endloop - endfacet - facet normal 0.0588719 0.474588 -0.878237 - outer loop - vertex 2 -0.845491 -0.475528 - vertex 1.73279 -0.812344 -0.475528 - vertex 1.77156 -0.685731 -0.404509 - endloop - endfacet - facet normal 0.0262902 0.16599 -0.985777 - outer loop - vertex 2 -1 -0.5 - vertex 1.69098 -0.951056 -0.5 - vertex 1.73279 -0.812344 -0.475528 - endloop - endfacet - facet normal 0.0812855 0.970684 -0.226199 - outer loop - vertex 2 -0.524472 -0.154509 - vertex 1.8297 -0.510211 -0.154509 - vertex 1.84549 -0.475528 9.89734e-18 - endloop - endfacet - facet normal -0.0789875 -0.150063 -0.985516 - outer loop - vertex 1.69098 -0.951056 -0.5 - vertex 1.64918 -1.08977 -0.475528 - vertex 1.33163 -0.922624 -0.475528 - endloop - endfacet - facet normal -0.226457 -0.422827 -0.877459 - outer loop - vertex 1.64918 -1.08977 -0.475528 - vertex 1.6104 -1.21638 -0.404509 - vertex 1.2571 -1.02716 -0.404509 - endloop - endfacet - facet normal -0.339828 -0.633695 -0.694944 - outer loop - vertex 1.6104 -1.21638 -0.404509 - vertex 1.57738 -1.31998 -0.293893 - vertex 1.19408 -1.11443 -0.293893 - endloop - endfacet - facet normal -0.436108 -0.855942 -0.2778 - outer loop - vertex 1.53647 -1.42658 8.60268e-23 - vertex 1.11832 -1.21353 6.61744e-23 - vertex 1.14689 -1.17794 -0.154509 - endloop - endfacet - facet normal -0.410647 -0.778033 -0.47543 - outer loop - vertex 1.57738 -1.31998 -0.293893 - vertex 1.55227 -1.3919 -0.154509 - vertex 1.14689 -1.17794 -0.154509 - endloop - endfacet - facet normal 0.0744067 0.888538 -0.452728 - outer loop - vertex 1.8297 -0.510211 -0.154509 - vertex 2 -0.524472 -0.154509 - vertex 2 -0.595491 -0.293893 - endloop - endfacet - facet normal 0.0482806 0.706282 -0.706282 - outer loop - vertex 1.80459 -0.582133 -0.293893 - vertex 2 -0.595491 -0.293893 - vertex 2 -0.706107 -0.404509 - endloop - endfacet - facet normal 0.0404608 0.453615 -0.890279 - outer loop - vertex 1.77156 -0.685731 -0.404509 - vertex 2 -0.706107 -0.404509 - vertex 2 -0.845491 -0.475528 - endloop - endfacet - facet normal 0.0194019 0.156406 -0.987502 - outer loop - vertex 1.73279 -0.812344 -0.475528 - vertex 2 -0.845491 -0.475528 - vertex 2 -1 -0.5 - endloop - endfacet - facet normal -0.0262901 -0.165989 -0.985777 - outer loop - vertex 1.64918 -1.08977 -0.475528 - vertex 1.69098 -0.951056 -0.5 - vertex 2 -1 -0.5 - endloop - endfacet - facet normal 0.154555 0.97582 -0.154556 - outer loop - vertex 1.84549 -0.475528 9.89734e-18 - vertex 2 -0.5 6.21687e-18 - vertex 2 -0.524472 -0.154509 - endloop - endfacet - facet normal -0.0862131 -0.46718 -0.879949 - outer loop - vertex 1.6104 -1.21638 -0.404509 - vertex 1.64918 -1.08977 -0.475528 - vertex 2 -1.15451 -0.475528 - endloop - endfacet - facet normal -0.139582 -0.7016 -0.698766 - outer loop - vertex 1.57738 -1.31998 -0.293893 - vertex 1.6104 -1.21638 -0.404509 - vertex 2 -1.29389 -0.404509 - endloop - endfacet - facet normal -0.453237 -0.858727 -0.239092 - outer loop - vertex 1.14689 -1.17794 -0.154509 - vertex 1.55227 -1.3919 -0.154509 - vertex 1.53647 -1.42658 8.60268e-23 - endloop - endfacet - facet normal -0.172482 -0.862349 -0.47603 - outer loop - vertex 1.55227 -1.3919 -0.154509 - vertex 1.57738 -1.31998 -0.293893 - vertex 2 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 2.4 -0.595491 -0.293893 - vertex 2 -0.595491 -0.293893 - vertex 2 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 2.4 -0.706107 -0.404509 - vertex 2 -0.706107 -0.404509 - vertex 2 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 2.4 -0.845491 -0.475528 - vertex 2 -0.845491 -0.475528 - vertex 2 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 2.4 -1 -0.5 - vertex 2 -1 -0.5 - vertex 2 -0.845491 -0.475528 - endloop - endfacet - facet normal -0.0288563 -0.156369 -0.987277 - outer loop - vertex 2 -1 -0.5 - vertex 2 -1.15451 -0.475528 - vertex 1.64918 -1.08977 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 2.4 -0.524472 -0.154509 - vertex 2 -0.524472 -0.154509 - vertex 2 -0.5 6.21687e-18 - endloop - endfacet - facet normal -0.0899555 -0.452157 -0.887391 - outer loop - vertex 2 -1.15451 -0.475528 - vertex 2 -1.29389 -0.404509 - vertex 1.6104 -1.21638 -0.404509 - endloop - endfacet - facet normal -0.140035 -0.700127 -0.700152 - outer loop - vertex 2 -1.29389 -0.404509 - vertex 2 -1.40451 -0.293893 - vertex 1.57738 -1.31998 -0.293893 - endloop - endfacet - facet normal -0.152203 -0.960916 -0.231245 - outer loop - vertex 2 -1.5 1.05879e-22 - vertex 1.53647 -1.42658 8.60268e-23 - vertex 1.55227 -1.3919 -0.154509 - endloop - endfacet - facet normal -0.16417 -0.878917 -0.447832 - outer loop - vertex 2 -1.40451 -0.293893 - vertex 2 -1.47553 -0.154509 - vertex 1.55227 -1.3919 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 2 -0.524472 -0.154509 - vertex 2.4 -0.524472 -0.154509 - vertex 2.4 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 2 -0.595491 -0.293893 - vertex 2.4 -0.595491 -0.293893 - vertex 2.4 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 2 -0.706107 -0.404509 - vertex 2.4 -0.706107 -0.404509 - vertex 2.4 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 2 -0.845491 -0.475528 - vertex 2.4 -0.845491 -0.475528 - vertex 2.4 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 2 -1.15451 -0.475528 - vertex 2 -1 -0.5 - vertex 2.4 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 2 -0.5 6.21687e-18 - vertex 2.4 -0.5 6.21687e-18 - vertex 2.4 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 2 -1.29389 -0.404509 - vertex 2 -1.15451 -0.475528 - vertex 2.4 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 2 -1.40451 -0.293893 - vertex 2 -1.29389 -0.404509 - vertex 2.4 -1.29389 -0.404509 - endloop - endfacet - facet normal -0.181426 -0.971299 -0.153827 - outer loop - vertex 1.55227 -1.3919 -0.154509 - vertex 2 -1.47553 -0.154509 - vertex 2 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 2 -1.47553 -0.154509 - vertex 2 -1.40451 -0.293893 - vertex 2.4 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 2.8 -0.595491 -0.293893 - vertex 2.4 -0.595491 -0.293893 - vertex 2.4 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 2.8 -0.706107 -0.404509 - vertex 2.4 -0.706107 -0.404509 - vertex 2.4 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 2.8 -0.845491 -0.475528 - vertex 2.4 -0.845491 -0.475528 - vertex 2.4 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 2.8 -1 -0.5 - vertex 2.4 -1 -0.5 - vertex 2.4 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 2.4 -1 -0.5 - vertex 2.4 -1.15451 -0.475528 - vertex 2 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 2.8 -0.524472 -0.154509 - vertex 2.4 -0.524472 -0.154509 - vertex 2.4 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 2.4 -1.15451 -0.475528 - vertex 2.4 -1.29389 -0.404509 - vertex 2 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 2.4 -1.29389 -0.404509 - vertex 2.4 -1.40451 -0.293893 - vertex 2 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 2 -1.5 1.05879e-22 - vertex 2 -1.47553 -0.154509 - vertex 2.4 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 2.4 -1.40451 -0.293893 - vertex 2.4 -1.47553 -0.154509 - vertex 2 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 2.4 -0.524472 -0.154509 - vertex 2.8 -0.524472 -0.154509 - vertex 2.8 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 2.4 -0.595491 -0.293893 - vertex 2.8 -0.595491 -0.293893 - vertex 2.8 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 2.4 -0.706107 -0.404509 - vertex 2.8 -0.706107 -0.404509 - vertex 2.8 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 2.4 -0.845491 -0.475528 - vertex 2.8 -0.845491 -0.475528 - vertex 2.8 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 2.4 -1.15451 -0.475528 - vertex 2.4 -1 -0.5 - vertex 2.8 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 2.4 -0.5 6.21687e-18 - vertex 2.8 -0.5 6.21687e-18 - vertex 2.8 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 2.4 -1.29389 -0.404509 - vertex 2.4 -1.15451 -0.475528 - vertex 2.8 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 2.4 -1.40451 -0.293893 - vertex 2.4 -1.29389 -0.404509 - vertex 2.8 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 2.4 -1.47553 -0.154509 - vertex 2.4 -1.5 1.05879e-22 - vertex 2 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 2.4 -1.47553 -0.154509 - vertex 2.4 -1.40451 -0.293893 - vertex 2.8 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 3.2 -0.595491 -0.293893 - vertex 2.8 -0.595491 -0.293893 - vertex 2.8 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 3.2 -0.706107 -0.404509 - vertex 2.8 -0.706107 -0.404509 - vertex 2.8 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 3.2 -0.845491 -0.475528 - vertex 2.8 -0.845491 -0.475528 - vertex 2.8 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 3.2 -1 -0.5 - vertex 2.8 -1 -0.5 - vertex 2.8 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 2.8 -1 -0.5 - vertex 2.8 -1.15451 -0.475528 - vertex 2.4 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 3.2 -0.524472 -0.154509 - vertex 2.8 -0.524472 -0.154509 - vertex 2.8 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 2.8 -1.15451 -0.475528 - vertex 2.8 -1.29389 -0.404509 - vertex 2.4 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 2.8 -1.29389 -0.404509 - vertex 2.8 -1.40451 -0.293893 - vertex 2.4 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 2.4 -1.5 1.05879e-22 - vertex 2.4 -1.47553 -0.154509 - vertex 2.8 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 2.8 -1.40451 -0.293893 - vertex 2.8 -1.47553 -0.154509 - vertex 2.4 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 2.8 -0.524472 -0.154509 - vertex 3.2 -0.524472 -0.154509 - vertex 3.2 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 2.8 -0.595491 -0.293893 - vertex 3.2 -0.595491 -0.293893 - vertex 3.2 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 2.8 -0.706107 -0.404509 - vertex 3.2 -0.706107 -0.404509 - vertex 3.2 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 2.8 -0.845491 -0.475528 - vertex 3.2 -0.845491 -0.475528 - vertex 3.2 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 2.8 -1.15451 -0.475528 - vertex 2.8 -1 -0.5 - vertex 3.2 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 2.8 -0.5 6.21687e-18 - vertex 3.2 -0.5 6.21687e-18 - vertex 3.2 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 2.8 -1.29389 -0.404509 - vertex 2.8 -1.15451 -0.475528 - vertex 3.2 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 2.8 -1.40451 -0.293893 - vertex 2.8 -1.29389 -0.404509 - vertex 3.2 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 2.8 -1.47553 -0.154509 - vertex 2.8 -1.5 1.05879e-22 - vertex 2.4 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 2.8 -1.47553 -0.154509 - vertex 2.8 -1.40451 -0.293893 - vertex 3.2 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 3.6 -0.595491 -0.293893 - vertex 3.2 -0.595491 -0.293893 - vertex 3.2 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 3.6 -0.706107 -0.404509 - vertex 3.2 -0.706107 -0.404509 - vertex 3.2 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 3.6 -0.845491 -0.475528 - vertex 3.2 -0.845491 -0.475528 - vertex 3.2 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 3.6 -1 -0.5 - vertex 3.2 -1 -0.5 - vertex 3.2 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 3.2 -1 -0.5 - vertex 3.2 -1.15451 -0.475528 - vertex 2.8 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 3.6 -0.524472 -0.154509 - vertex 3.2 -0.524472 -0.154509 - vertex 3.2 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 3.2 -1.15451 -0.475528 - vertex 3.2 -1.29389 -0.404509 - vertex 2.8 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 3.2 -1.29389 -0.404509 - vertex 3.2 -1.40451 -0.293893 - vertex 2.8 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 2.8 -1.5 1.05879e-22 - vertex 2.8 -1.47553 -0.154509 - vertex 3.2 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 3.2 -1.40451 -0.293893 - vertex 3.2 -1.47553 -0.154509 - vertex 2.8 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 3.2 -0.524472 -0.154509 - vertex 3.6 -0.524472 -0.154509 - vertex 3.6 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 3.2 -0.595491 -0.293893 - vertex 3.6 -0.595491 -0.293893 - vertex 3.6 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 3.2 -0.706107 -0.404509 - vertex 3.6 -0.706107 -0.404509 - vertex 3.6 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 3.2 -0.845491 -0.475528 - vertex 3.6 -0.845491 -0.475528 - vertex 3.6 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 3.2 -1.15451 -0.475528 - vertex 3.2 -1 -0.5 - vertex 3.6 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 3.2 -0.5 6.21687e-18 - vertex 3.6 -0.5 6.21687e-18 - vertex 3.6 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 3.2 -1.29389 -0.404509 - vertex 3.2 -1.15451 -0.475528 - vertex 3.6 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 3.2 -1.40451 -0.293893 - vertex 3.2 -1.29389 -0.404509 - vertex 3.6 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 3.2 -1.47553 -0.154509 - vertex 3.2 -1.5 1.05879e-22 - vertex 2.8 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 3.2 -1.47553 -0.154509 - vertex 3.2 -1.40451 -0.293893 - vertex 3.6 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 4 -0.595491 -0.293893 - vertex 3.6 -0.595491 -0.293893 - vertex 3.6 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 4 -0.706107 -0.404509 - vertex 3.6 -0.706107 -0.404509 - vertex 3.6 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 4 -0.845491 -0.475528 - vertex 3.6 -0.845491 -0.475528 - vertex 3.6 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 4 -1 -0.5 - vertex 3.6 -1 -0.5 - vertex 3.6 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 3.6 -1 -0.5 - vertex 3.6 -1.15451 -0.475528 - vertex 3.2 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 4 -0.524472 -0.154509 - vertex 3.6 -0.524472 -0.154509 - vertex 3.6 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 3.6 -1.15451 -0.475528 - vertex 3.6 -1.29389 -0.404509 - vertex 3.2 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 3.6 -1.29389 -0.404509 - vertex 3.6 -1.40451 -0.293893 - vertex 3.2 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 3.2 -1.5 1.05879e-22 - vertex 3.2 -1.47553 -0.154509 - vertex 3.6 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 3.6 -1.40451 -0.293893 - vertex 3.6 -1.47553 -0.154509 - vertex 3.2 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 3.6 -0.524472 -0.154509 - vertex 4 -0.524472 -0.154509 - vertex 4 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 3.6 -0.595491 -0.293893 - vertex 4 -0.595491 -0.293893 - vertex 4 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 3.6 -0.706107 -0.404509 - vertex 4 -0.706107 -0.404509 - vertex 4 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 3.6 -0.845491 -0.475528 - vertex 4 -0.845491 -0.475528 - vertex 4 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 3.6 -1.15451 -0.475528 - vertex 3.6 -1 -0.5 - vertex 4 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 3.6 -0.5 6.21687e-18 - vertex 4 -0.5 6.21687e-18 - vertex 4 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 3.6 -1.29389 -0.404509 - vertex 3.6 -1.15451 -0.475528 - vertex 4 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 3.6 -1.40451 -0.293893 - vertex 3.6 -1.29389 -0.404509 - vertex 4 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 3.6 -1.47553 -0.154509 - vertex 3.6 -1.5 1.05879e-22 - vertex 3.2 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 3.6 -1.47553 -0.154509 - vertex 3.6 -1.40451 -0.293893 - vertex 4 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 4.4 -0.595491 -0.293893 - vertex 4 -0.595491 -0.293893 - vertex 4 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 4.4 -0.706107 -0.404509 - vertex 4 -0.706107 -0.404509 - vertex 4 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 4.4 -0.845491 -0.475528 - vertex 4 -0.845491 -0.475528 - vertex 4 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 4.4 -1 -0.5 - vertex 4 -1 -0.5 - vertex 4 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 4 -1 -0.5 - vertex 4 -1.15451 -0.475528 - vertex 3.6 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 4.4 -0.524472 -0.154509 - vertex 4 -0.524472 -0.154509 - vertex 4 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 4 -1.15451 -0.475528 - vertex 4 -1.29389 -0.404509 - vertex 3.6 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 4 -1.29389 -0.404509 - vertex 4 -1.40451 -0.293893 - vertex 3.6 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 3.6 -1.5 1.05879e-22 - vertex 3.6 -1.47553 -0.154509 - vertex 4 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 4 -1.40451 -0.293893 - vertex 4 -1.47553 -0.154509 - vertex 3.6 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 4 -0.524472 -0.154509 - vertex 4.4 -0.524472 -0.154509 - vertex 4.4 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 4 -0.595491 -0.293893 - vertex 4.4 -0.595491 -0.293893 - vertex 4.4 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 4 -0.706107 -0.404509 - vertex 4.4 -0.706107 -0.404509 - vertex 4.4 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 4 -0.845491 -0.475528 - vertex 4.4 -0.845491 -0.475528 - vertex 4.4 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 4 -1.15451 -0.475528 - vertex 4 -1 -0.5 - vertex 4.4 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 4 -0.5 6.21687e-18 - vertex 4.4 -0.5 6.21687e-18 - vertex 4.4 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 4 -1.29389 -0.404509 - vertex 4 -1.15451 -0.475528 - vertex 4.4 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 4 -1.40451 -0.293893 - vertex 4 -1.29389 -0.404509 - vertex 4.4 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 4 -1.47553 -0.154509 - vertex 4 -1.5 1.05879e-22 - vertex 3.6 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 4 -1.47553 -0.154509 - vertex 4 -1.40451 -0.293893 - vertex 4.4 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 4.8 -0.595491 -0.293893 - vertex 4.4 -0.595491 -0.293893 - vertex 4.4 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 4.8 -0.706107 -0.404509 - vertex 4.4 -0.706107 -0.404509 - vertex 4.4 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 4.8 -0.845491 -0.475528 - vertex 4.4 -0.845491 -0.475528 - vertex 4.4 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 4.8 -1 -0.5 - vertex 4.4 -1 -0.5 - vertex 4.4 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 4.4 -1 -0.5 - vertex 4.4 -1.15451 -0.475528 - vertex 4 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 4.8 -0.524472 -0.154509 - vertex 4.4 -0.524472 -0.154509 - vertex 4.4 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 4.4 -1.15451 -0.475528 - vertex 4.4 -1.29389 -0.404509 - vertex 4 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 4.4 -1.29389 -0.404509 - vertex 4.4 -1.40451 -0.293893 - vertex 4 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 4 -1.5 1.05879e-22 - vertex 4 -1.47553 -0.154509 - vertex 4.4 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 4.4 -1.40451 -0.293893 - vertex 4.4 -1.47553 -0.154509 - vertex 4 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 4.4 -0.524472 -0.154509 - vertex 4.8 -0.524472 -0.154509 - vertex 4.8 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 4.4 -0.595491 -0.293893 - vertex 4.8 -0.595491 -0.293893 - vertex 4.8 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 4.4 -0.706107 -0.404509 - vertex 4.8 -0.706107 -0.404509 - vertex 4.8 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 4.4 -0.845491 -0.475528 - vertex 4.8 -0.845491 -0.475528 - vertex 4.8 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 4.4 -1.15451 -0.475528 - vertex 4.4 -1 -0.5 - vertex 4.8 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 4.4 -0.5 6.21687e-18 - vertex 4.8 -0.5 6.21687e-18 - vertex 4.8 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 4.4 -1.29389 -0.404509 - vertex 4.4 -1.15451 -0.475528 - vertex 4.8 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 4.4 -1.40451 -0.293893 - vertex 4.4 -1.29389 -0.404509 - vertex 4.8 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 4.4 -1.47553 -0.154509 - vertex 4.4 -1.5 1.05879e-22 - vertex 4 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 4.4 -1.47553 -0.154509 - vertex 4.4 -1.40451 -0.293893 - vertex 4.8 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 5.2 -0.595491 -0.293893 - vertex 4.8 -0.595491 -0.293893 - vertex 4.8 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 5.2 -0.706107 -0.404509 - vertex 4.8 -0.706107 -0.404509 - vertex 4.8 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 5.2 -0.845491 -0.475528 - vertex 4.8 -0.845491 -0.475528 - vertex 4.8 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 5.2 -1 -0.5 - vertex 4.8 -1 -0.5 - vertex 4.8 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 4.8 -1 -0.5 - vertex 4.8 -1.15451 -0.475528 - vertex 4.4 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 5.2 -0.524472 -0.154509 - vertex 4.8 -0.524472 -0.154509 - vertex 4.8 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 4.8 -1.15451 -0.475528 - vertex 4.8 -1.29389 -0.404509 - vertex 4.4 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 4.8 -1.29389 -0.404509 - vertex 4.8 -1.40451 -0.293893 - vertex 4.4 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 4.4 -1.5 1.05879e-22 - vertex 4.4 -1.47553 -0.154509 - vertex 4.8 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 4.8 -1.40451 -0.293893 - vertex 4.8 -1.47553 -0.154509 - vertex 4.4 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 4.8 -0.524472 -0.154509 - vertex 5.2 -0.524472 -0.154509 - vertex 5.2 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 4.8 -0.595491 -0.293893 - vertex 5.2 -0.595491 -0.293893 - vertex 5.2 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 4.8 -0.706107 -0.404509 - vertex 5.2 -0.706107 -0.404509 - vertex 5.2 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 4.8 -0.845491 -0.475528 - vertex 5.2 -0.845491 -0.475528 - vertex 5.2 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 4.8 -1.15451 -0.475528 - vertex 4.8 -1 -0.5 - vertex 5.2 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 4.8 -0.5 6.21687e-18 - vertex 5.2 -0.5 6.21687e-18 - vertex 5.2 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 4.8 -1.29389 -0.404509 - vertex 4.8 -1.15451 -0.475528 - vertex 5.2 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 4.8 -1.40451 -0.293893 - vertex 4.8 -1.29389 -0.404509 - vertex 5.2 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 4.8 -1.47553 -0.154509 - vertex 4.8 -1.5 1.05879e-22 - vertex 4.4 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 4.8 -1.47553 -0.154509 - vertex 4.8 -1.40451 -0.293893 - vertex 5.2 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 5.6 -0.595491 -0.293893 - vertex 5.2 -0.595491 -0.293893 - vertex 5.2 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 5.6 -0.706107 -0.404509 - vertex 5.2 -0.706107 -0.404509 - vertex 5.2 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 5.6 -0.845491 -0.475528 - vertex 5.2 -0.845491 -0.475528 - vertex 5.2 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 5.6 -1 -0.5 - vertex 5.2 -1 -0.5 - vertex 5.2 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 5.2 -1 -0.5 - vertex 5.2 -1.15451 -0.475528 - vertex 4.8 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 5.6 -0.524472 -0.154509 - vertex 5.2 -0.524472 -0.154509 - vertex 5.2 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 5.2 -1.15451 -0.475528 - vertex 5.2 -1.29389 -0.404509 - vertex 4.8 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 5.2 -1.29389 -0.404509 - vertex 5.2 -1.40451 -0.293893 - vertex 4.8 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 4.8 -1.5 1.05879e-22 - vertex 4.8 -1.47553 -0.154509 - vertex 5.2 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 5.2 -1.40451 -0.293893 - vertex 5.2 -1.47553 -0.154509 - vertex 4.8 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 5.2 -0.524472 -0.154509 - vertex 5.6 -0.524472 -0.154509 - vertex 5.6 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 5.2 -0.595491 -0.293893 - vertex 5.6 -0.595491 -0.293893 - vertex 5.6 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 5.2 -0.706107 -0.404509 - vertex 5.6 -0.706107 -0.404509 - vertex 5.6 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 5.2 -0.845491 -0.475528 - vertex 5.6 -0.845491 -0.475528 - vertex 5.6 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 5.2 -1.15451 -0.475528 - vertex 5.2 -1 -0.5 - vertex 5.6 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 5.2 -0.5 6.21687e-18 - vertex 5.6 -0.5 6.21687e-18 - vertex 5.6 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 5.2 -1.29389 -0.404509 - vertex 5.2 -1.15451 -0.475528 - vertex 5.6 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 5.2 -1.40451 -0.293893 - vertex 5.2 -1.29389 -0.404509 - vertex 5.6 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 5.2 -1.47553 -0.154509 - vertex 5.2 -1.5 1.05879e-22 - vertex 4.8 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 5.2 -1.47553 -0.154509 - vertex 5.2 -1.40451 -0.293893 - vertex 5.6 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 6 -0.595491 -0.293893 - vertex 5.6 -0.595491 -0.293893 - vertex 5.6 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 6 -0.706107 -0.404509 - vertex 5.6 -0.706107 -0.404509 - vertex 5.6 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 6 -0.845491 -0.475528 - vertex 5.6 -0.845491 -0.475528 - vertex 5.6 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 6 -1 -0.5 - vertex 5.6 -1 -0.5 - vertex 5.6 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 5.6 -1 -0.5 - vertex 5.6 -1.15451 -0.475528 - vertex 5.2 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 6 -0.524472 -0.154509 - vertex 5.6 -0.524472 -0.154509 - vertex 5.6 -0.5 6.21687e-18 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 5.6 -1.15451 -0.475528 - vertex 5.6 -1.29389 -0.404509 - vertex 5.2 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 5.6 -1.29389 -0.404509 - vertex 5.6 -1.40451 -0.293893 - vertex 5.2 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 5.2 -1.5 1.05879e-22 - vertex 5.2 -1.47553 -0.154509 - vertex 5.6 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 5.6 -1.40451 -0.293893 - vertex 5.6 -1.47553 -0.154509 - vertex 5.2 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 0.891008 -0.453987 - outer loop - vertex 5.6 -0.524472 -0.154509 - vertex 6 -0.524472 -0.154509 - vertex 6 -0.595491 -0.293893 - endloop - endfacet - facet normal 0 0.707107 -0.707107 - outer loop - vertex 5.6 -0.595491 -0.293893 - vertex 6 -0.595491 -0.293893 - vertex 6 -0.706107 -0.404509 - endloop - endfacet - facet normal 0 0.453987 -0.891008 - outer loop - vertex 5.6 -0.706107 -0.404509 - vertex 6 -0.706107 -0.404509 - vertex 6 -0.845491 -0.475528 - endloop - endfacet - facet normal 0 0.156436 -0.987688 - outer loop - vertex 5.6 -0.845491 -0.475528 - vertex 6 -0.845491 -0.475528 - vertex 6 -1 -0.5 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 5.6 -1.15451 -0.475528 - vertex 5.6 -1 -0.5 - vertex 6 -1 -0.5 - endloop - endfacet - facet normal 0 0.987688 -0.156436 - outer loop - vertex 5.6 -0.5 6.21687e-18 - vertex 6 -0.5 6.21687e-18 - vertex 6 -0.524472 -0.154509 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 5.6 -1.29389 -0.404509 - vertex 5.6 -1.15451 -0.475528 - vertex 6 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 5.6 -1.40451 -0.293893 - vertex 5.6 -1.29389 -0.404509 - vertex 6 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 5.6 -1.47553 -0.154509 - vertex 5.6 -1.5 1.05879e-22 - vertex 5.2 -1.5 1.05879e-22 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 5.6 -1.47553 -0.154509 - vertex 5.6 -1.40451 -0.293893 - vertex 6 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.156435 -0.987688 - outer loop - vertex 6 -1 -0.5 - vertex 6 -1.15451 -0.475528 - vertex 5.6 -1.15451 -0.475528 - endloop - endfacet - facet normal 0 -0.453997 -0.891003 - outer loop - vertex 6 -1.15451 -0.475528 - vertex 6 -1.29389 -0.404509 - vertex 5.6 -1.29389 -0.404509 - endloop - endfacet - facet normal 0 -0.707094 -0.70712 - outer loop - vertex 6 -1.29389 -0.404509 - vertex 6 -1.40451 -0.293893 - vertex 5.6 -1.40451 -0.293893 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 5.6 -1.5 1.05879e-22 - vertex 5.6 -1.47553 -0.154509 - vertex 6 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.891006 -0.453992 - outer loop - vertex 6 -1.40451 -0.293893 - vertex 6 -1.47553 -0.154509 - vertex 5.6 -1.47553 -0.154509 - endloop - endfacet - facet normal 0 -0.98769 -0.156423 - outer loop - vertex 6 -1.47553 -0.154509 - vertex 6 -1.5 1.05879e-22 - vertex 5.6 -1.5 1.05879e-22 - endloop - endfacet -endsolid walls1 diff --git a/tutorials/sBendOctree/system/cellSetDict b/tutorials/sBendOctree/system/cellSetDict deleted file mode 100644 index 29080b06d9dad66bab4edcb44a656858d787ba1d..0000000000000000000000000000000000000000 --- a/tutorials/sBendOctree/system/cellSetDict +++ /dev/null @@ -1,128 +0,0 @@ -/*---------------------------------------------------------------------------*\ -| ========= | | -| \\ / F ield | OpenFOAM: The Open Source CFD Toolbox | -| \\ / O peration | Version: 1.0 | -| \\ / A nd | Web: http://www.openfoam.org | -| \\/ M anipulation | | -\*---------------------------------------------------------------------------*/ - -FoamFile -{ - version 2.0; - format ascii; - - root "/home/penfold/mattijs/foam/mattijs2.2/run/icoFoam"; - case "cavityTut"; - instance "system"; - local ""; - - class dictionary; - object cellSetDict; -} - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -// Name of set to operate on -name CommonVrtFaces; - -// One of clear/new/invert/add/delete|subset/list -action new; - -// Actions to apply to cellSet. These are all the topoSetSource's ending -// in ..ToCell (see the meshTools library). - -topoSetSources -( - // Copy elements from cellSet -/* - cellToCell - { - set c1; - } -*/ - // Select based on faceSet - faceToCell - { - set edgeFaces; // Name of faceSet - - //option neighbour; // cell with neighbour in faceSet - //option owner; // ,, owner - option any; // cell with any face in faceSet - //option all; // cell with all faces in faceSet - } -/* - // Select based on pointSet - pointToCell - { - set p0; - option any; // cell with any point in pointSet - //option all; // cell with all points in pointSet - } - - // Select by explicitly providing cell labels - labelToCell - { - value (12 13 56); // labels of cells - } - - // Select based on cellShape - shapeToCell - { - type hex; // hex/wedge/prism/pyr/tet/tetWedge/splitHex - } - - // Cells with cell centre within box - boxToCell - { - box (0 0 0) (1 1 1); - } - - // Cells with cell centre within box - // Is skewed, rotated box. Given as origin and three spanning vectors. - rotatedBoxToCell - { - origin (0.2 0.2 -10); - i (0.2 0.2 0); - j (-0.2 0.2 0); - k (10 10 10); - } - - // Cells in cell zone - zoneToCell - { - name cellZone; // name of cellZone - } - - // values of field within certain range - fieldToCell - { - fieldName U; // Note: uses mag(U) since volVectorField - min 0.1; - max 0.5; - } - - // Cells with cellCentre nearest to coordinates - nearestToCell - { - points ((0 0 0) (1 1 1)(2 2 2)); - } - - // Select based on surface - surfaceToCell - { - file "www.avl.com-geometry.stl"; - outsidePoints ((-99 -99 -59)); // definition of outside - includeCut false; // cells cut by surface - includeInside false; // cells not on outside of surf - includeOutside false; // cells on outside of surf - nearDistance -1; // cells with centre near surf - // (set to -1 if not used) - curvature 0.9; // cells within nearDistance - // and near surf curvature - // (set to -100 if not used) - } -*/ -); - - -// ************************************************************************* // diff --git a/tutorials/sBendOctree/system/controlDict b/tutorials/sBendOctree/system/controlDict deleted file mode 100755 index d6862566e4eeb5af886fc037a550da26e6e96e4b..0000000000000000000000000000000000000000 --- a/tutorials/sBendOctree/system/controlDict +++ /dev/null @@ -1,49 +0,0 @@ -// ************************************************************************* // -// FoamX Case Dictionary. - -version 1.0; -format ascii; -root "/home/franjo/foam/franjo2.0/run"; -case "tubeBundleAdaptive"; -instance "system"; -local ""; -class dictionary; -form dictionary; -object controlDict; - -// ************************************************************************* // - -applicationClass icoFoam; - -startFrom latestTime; - -startTime 0; - -stopAt endTime; - -endTime 2000; - -deltaT 1; - -writeControl timeStep; - -writeInterval 100; - -cycleWrite 0; - -writeFormat ascii; - -writeCompression compressed; - -timeFormat general; - -timePrecision 6; - -runTimeModifiable yes; - -nCorrectors 2; - -nNonOrthogonalCorrectors 0; - - -// ************************************************************************* // diff --git a/tutorials/sBendOctree/system/meshDict b/tutorials/sBendOctree/system/meshDict deleted file mode 100755 index 16a02393c860f7676f6bab4049290edb28eb5b59..0000000000000000000000000000000000000000 --- a/tutorials/sBendOctree/system/meshDict +++ /dev/null @@ -1,46 +0,0 @@ -// The FOAM Project // File: adaptiveProperties -/* -------------------------------------------------------------------------------- - ========= | dictionary - \\ / | - \\ / | Name: adaptiveProperties - \\ / | Family: Data file - \\/ | - F ield | FOAM version: 1.9.6 - O peration | Product of Nabla Ltd. - A and | - M anipulation | Email: Enquiries@Nabla.co.uk -------------------------------------------------------------------------------- -*/ - -version 0.5; -format ascii; - -root "/home/larson/franjo/foam/run"; -case "thetaTest"; -instance "system"; -local ""; - -note "fvSchemes for Foam"; - -class dictionary; -object adaptiveProperties; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -surfaceFile "geom.stl"; - -maxCellSize 0.09999; - -boundaryCellSize 0.05; - -minCellSize 0.05; - -patchCellSize -2 -( - walls 0.025 - walls1 0.025 -); - -// ************************************************************************* // diff --git a/tutorials/sawOctree/system/controlDict b/tutorials/sawOctree/system/controlDict deleted file mode 100755 index c016ed2e7772add9024ad2e9a105b48603128a58..0000000000000000000000000000000000000000 --- a/tutorials/sawOctree/system/controlDict +++ /dev/null @@ -1,49 +0,0 @@ -// ************************************************************************* // -// FoamX Case Dictionary. - -version 1.0; -format ascii; -root "/home/franjo/foam/franjo2.0/run"; -case "jetAdaptive"; -instance "system"; -local ""; -class dictionary; -form dictionary; -object controlDict; - -// ************************************************************************* // - -applicationClass icoFoam; - -startFrom latestTime; - -startTime 0; - -stopAt endTime; - -endTime 500; - -deltaT 1; - -writeControl timeStep; - -writeInterval 100; - -cycleWrite 0; - -writeFormat binary; - -writeCompression compressed; - -timeFormat general; - -timePrecision 6; - -runTimeModifiable yes; - -nCorrectors 2; - -nNonOrthogonalCorrectors 0; - - -// ************************************************************************* // diff --git a/tutorials/sawOctree/system/meshDict b/tutorials/sawOctree/system/meshDict deleted file mode 100755 index 87f3f69fba7793d6085bb4c92120cb0ffb39cd0c..0000000000000000000000000000000000000000 --- a/tutorials/sawOctree/system/meshDict +++ /dev/null @@ -1,48 +0,0 @@ -// The FOAM Project // File: adaptiveProperties -/* -------------------------------------------------------------------------------- - ========= | dictionary - \\ / | - \\ / | Name: adaptiveProperties - \\ / | Family: Data file - \\/ | - F ield | FOAM version: 1.9.6 - O peration | Product of Nabla Ltd. - A and | - M anipulation | Email: Enquiries@Nabla.co.uk -------------------------------------------------------------------------------- -*/ - -version 0.5; -format ascii; - -root "/home/larson/franjo/foam/run"; -case "thetaTest"; -instance "system"; -local ""; - -note "fvSchemes for Foam"; - -class dictionary; -object adaptiveProperties; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -surfaceFile "sav1.stl"; - -maxCellSize 1.0; - -boundaryCellSize 0.25; - -minCellSize 0.05; - -internalVertex (0.0 1.0 -0.25); -/* -patchCellSize -2 -( - walls 0.05 - walls1 0.05 -); - */ -// ************************************************************************* // diff --git a/tutorials/socketOctree/socket.stl b/tutorials/socketOctree/socket.stl deleted file mode 100644 index 96695074eb13d970673e68e25e9b3e40f9de9d28..0000000000000000000000000000000000000000 --- a/tutorials/socketOctree/socket.stl +++ /dev/null @@ -1,11874 +0,0 @@ -solid patch0 - facet normal 0 -0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -75 -10 25 - vertex -86.3348 -19.8135 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -62.9265 -20.6629 25 - vertex -67.9289 -7.07107 25 - vertex -75 -10 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -9.6225 25 - vertex -65 0 25 - vertex -67.9289 -7.07107 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 9.6225 25 - vertex -67.9289 7.07107 25 - vertex -65 0 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -58.9291 18.1066 25 - vertex -67.9289 7.07107 25 - vertex -50 9.6225 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -61.4482 60.1728 25 - vertex -50 48.1125 25 - vertex -50 67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.1254 44.5169 25 - vertex -50 48.1125 25 - vertex -61.4482 60.1728 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -50 28.8675 25 - vertex -50 48.1125 25 - vertex -64.1254 44.5169 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 28.8675 25 - vertex -64.1254 44.5169 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 28.8675 25 - vertex -67.5886 27.0128 25 - vertex -58.9291 18.1066 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 28.8675 25 - vertex -58.9291 18.1066 25 - vertex -50 9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -67.5886 27.0128 25 - vertex -67.9289 7.07107 25 - vertex -58.9291 18.1066 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -75 10 25 - vertex -67.9289 7.07107 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 86.6025 25 - vertex -64.2788 76.6044 25 - vertex -50 67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.2788 76.6044 25 - vertex -61.4482 60.1728 25 - vertex -50 67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -76.6044 64.2788 25 - vertex -64.1254 44.5169 25 - vertex -61.4482 60.1728 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -77.7885 41.2952 25 - vertex -67.5886 27.0128 25 - vertex -64.1254 44.5169 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -81.203 24.5589 25 - vertex -75 10 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -82.0711 7.07107 25 - vertex -75 10 25 - vertex -81.203 24.5589 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -82.0711 7.07107 25 - vertex -81.203 24.5589 25 - vertex -90.472 14.6634 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -82.0711 7.07107 25 - vertex -90.472 14.6634 25 - vertex -85 -0 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 36.3417 9.24839 75 - vertex 36.3417 -9.24839 75 - vertex 50 9.6225 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 40.559 40.5083 75 - vertex 27.5 43.1574 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 60.8198 75 - vertex 27.5 43.1574 75 - vertex 38.9169 56.2753 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 78.4821 75 - vertex 27.5 60.8198 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 38.9169 56.2753 75 - vertex 50 67.3575 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -98.4808 17.3648 25 - vertex -90.472 14.6634 25 - vertex -93.9693 34.202 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -100 0 25 - vertex -85 -0 25 - vertex -90.472 14.6634 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -91.3679 -8.97974 25 - vertex -85 -0 25 - vertex -100 0 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -82.0711 -7.07107 25 - vertex -85 -0 25 - vertex -91.3679 -8.97974 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -98.4808 -17.3648 25 - vertex -86.3348 -19.8135 25 - vertex -91.3679 -8.97974 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -98.4808 -17.3648 25 - vertex -91.3679 -8.97974 25 - vertex -100 0 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -86.3348 -19.8135 25 - vertex -82.0711 -7.07107 25 - vertex -91.3679 -8.97974 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -75 -10 25 - vertex -82.0711 -7.07107 25 - vertex -86.3348 -19.8135 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -50 -28.8675 25 - vertex -50 -9.6225 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -9.6225 25 - vertex -67.9289 -7.07107 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 9.6225 25 - vertex -65 0 25 - vertex -50 -9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -65.9129 -50.6425 25 - vertex -77.4233 -43.4472 25 - vertex -76.6044 -64.2788 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -63.2012 -36.5076 25 - vertex -77.4233 -43.4472 25 - vertex -65.9129 -50.6425 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -77.4233 -43.4472 25 - vertex -63.2012 -36.5076 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -63.2012 -36.5076 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -62.9265 -20.6629 25 - vertex -75 -10 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -63.2012 -36.5076 25 - vertex -50 -28.8675 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -50 -48.1125 25 - vertex -50 -28.8675 25 - vertex -63.2012 -36.5076 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 25 - vertex -63.2012 -36.5076 25 - vertex -65.9129 -50.6425 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 25 - vertex -65.9129 -50.6425 25 - vertex -61.2753 -61.6257 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 25 - vertex -61.2753 -61.6257 25 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -65.9129 -50.6425 25 - vertex -76.6044 -64.2788 25 - vertex -61.2753 -61.6257 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -77.4233 -43.4472 25 - vertex -86.6025 -50 25 - vertex -76.6044 -64.2788 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -86.6025 -50 25 - vertex -77.4233 -43.4472 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -77.4233 -43.4472 25 - vertex -76.5403 -27.9427 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -76.5403 -27.9427 25 - vertex -86.3348 -19.8135 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -86.3348 -19.8135 25 - vertex -98.4808 -17.3648 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.8583 -55.5402 75 - vertex 50 -48.1125 75 - vertex 38.9258 -37.7032 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 50 -67.3575 75 - vertex 50 -48.1125 75 - vertex 38.8583 -55.5402 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -67.3575 75 - vertex 38.8583 -55.5402 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -67.3575 75 - vertex 38.6268 -74.3693 75 - vertex 50 -86.6025 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.8583 -55.5402 75 - vertex 27.5 -60.8198 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -43.1574 75 - vertex 27.5 -60.8198 75 - vertex 38.8583 -55.5402 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 -43.1574 75 - vertex 38.8583 -55.5402 75 - vertex 38.9258 -37.7032 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -43.1574 75 - vertex 38.9258 -37.7032 75 - vertex 27.5 -25.4951 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 47.412 0 - vertex -0 60.5293 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -0 60.5293 0 - vertex -20 64.8505 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 80.0149 0 - vertex -20 64.8505 0 - vertex -0 60.5293 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 81.4151 0 - vertex -20 64.8505 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 81.4151 0 - vertex 20 97.9796 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 48.286 0 - vertex 6.99057 36.8427 0 - vertex 20 31.7214 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 0 47.412 0 - vertex 6.99057 36.8427 0 - vertex 20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -6.99057 36.8427 0 - vertex 6.99057 36.8427 0 - vertex 0 47.412 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -13.3836 99.1004 0 - vertex -20 97.9796 0 - vertex -20 81.4151 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -13.3836 99.1004 0 - vertex -20 81.4151 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -13.3836 99.1004 0 - vertex 0 80.0149 0 - vertex -6.70689 99.7748 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 0 80.0149 0 - vertex 0 100 0 - vertex -6.70689 99.7748 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 6.70689 99.7748 0 - vertex 0 100 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 6.70689 99.7748 0 - vertex 0 80.0149 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 80.0149 0 - vertex 20 81.4151 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 64.8505 0 - vertex 20 81.4151 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 64.8505 0 - vertex 0 80.0149 0 - vertex -0 60.5293 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 64.8505 0 - vertex -0 60.5293 0 - vertex 20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 42.7684 90.3928 75 - vertex 35.2517 93.5805 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 42.7684 90.3928 75 - vertex 38.6275 74.5675 75 - vertex 50 86.6025 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 38.6275 74.5675 75 - vertex 50 67.3575 75 - vertex 50 86.6025 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 38.9169 56.2753 75 - vertex 50 48.1125 75 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 40.559 40.5083 75 - vertex 50 48.1125 75 - vertex 38.9169 56.2753 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 50 28.8675 75 - vertex 50 48.1125 75 - vertex 40.559 40.5083 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 96.1444 75 - vertex 27.5 78.4821 75 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 78.4821 75 - vertex 38.6275 74.5675 75 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 60.8198 75 - vertex 38.9169 56.2753 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 43.1574 75 - vertex 40.559 40.5083 75 - vertex 38.9169 56.2753 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.7748 25.5778 75 - vertex 50 28.8675 75 - vertex 40.559 40.5083 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 50 9.6225 75 - vertex 50 28.8675 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 40.3789 -22.1533 75 - vertex 50 -9.6225 75 - vertex 36.3417 -9.24839 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 -25.4951 75 - vertex 38.9258 -37.7032 75 - vertex 40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -25.4951 75 - vertex 40.3789 -22.1533 75 - vertex 36.3417 -9.24839 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.9258 -37.7032 75 - vertex 50 -28.8675 75 - vertex 40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -78.4821 75 - vertex 27.5 -96.1444 75 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 42.7684 -90.3928 75 - vertex 50 -86.6025 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 42.7684 -90.3928 75 - vertex 38.6268 -74.3693 75 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.6268 -74.3693 75 - vertex 27.5 -78.4821 75 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -60.8198 75 - vertex 27.5 -78.4821 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 25.4951 75 - vertex 36.3417 9.24839 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 25.4951 75 - vertex 38.7748 25.5778 75 - vertex 27.5 43.1574 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 36.3417 9.24839 75 - vertex 50 9.6225 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 36.3417 -9.24839 75 - vertex 50 -9.6225 75 - vertex 50 9.6225 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 40.3789 -22.1533 75 - vertex 50 -28.8675 75 - vertex 50 -9.6225 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 38.9258 -37.7032 75 - vertex 50 -48.1125 75 - vertex 50 -28.8675 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -7.54086 40.5115 - vertex -50 -24.3141 38.9123 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.1125 75 - vertex -50 67.3575 75 - vertex -50 50 60 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 75 - vertex -50 48.1125 75 - vertex -50 38.1931 66.569 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.6225 75 - vertex -50 28.8675 75 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 75 - vertex -50 9.6225 75 - vertex -50 7.72654 59.5349 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 75 - vertex -50 -9.6225 75 - vertex -50 -9.20725 58.1596 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -72.4016 61.5374 - vertex -50 -67.3575 75 - vertex -50 -59.3991 66.7554 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 25 - vertex -50 -48.1125 25 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 25 - vertex -50 -28.8675 25 - vertex -50 -24.3141 38.9123 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.6225 25 - vertex -50 -9.6225 25 - vertex -50 -7.54086 40.5115 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 25 - vertex -50 9.6225 25 - vertex -50 9.31671 41.8755 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 86.6025 58.3333 - vertex -50 72.7615 54.9694 - vertex -50 67.3575 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 58.3333 - vertex -50 67.3575 75 - vertex -50 86.6025 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 72.7615 54.9694 - vertex -50 57.0711 57.0711 - vertex -50 67.3575 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -50 72.9043 38.7048 - vertex -50 72.7615 54.9694 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -50 72.7615 54.9694 - vertex -50 86.6025 58.3333 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 72.9043 38.7048 - vertex -50 60 50 - vertex -50 72.7615 54.9694 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 25 - vertex -50 67.3575 25 - vertex -50 72.9043 38.7048 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 25 - vertex -50 72.9043 38.7048 - vertex -50 86.6025 41.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 25 - vertex -50 57.0711 42.9289 - vertex -50 72.9043 38.7048 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 38.1931 66.569 - vertex -50 42.9289 57.0711 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 50 60 - vertex -50 42.9289 57.0711 - vertex -50 38.1931 66.569 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 40 50 - vertex -50 24.425 45.4369 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 40 50 - vertex -50 24.777 61.2904 - vertex -50 42.9289 57.0711 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 24.425 45.4369 - vertex -50 7.72654 59.5349 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.31671 41.8755 - vertex -50 -9.20725 58.1596 - vertex -50 7.72654 59.5349 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -63.77 35.8952 -25 - vertex -78.1277 25.7829 -25 - vertex -77.6899 42.7319 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -63.1721 20.406 -25 - vertex -75 10 -25 - vertex -78.1277 25.7829 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.9289 7.07107 -25 - vertex -75 10 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 76.6044 -25 - vertex -50 86.6025 -25 - vertex -50 67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 76.6044 -25 - vertex -50 67.3575 -25 - vertex -61.3177 61.5263 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -64.2788 76.6044 -25 - vertex -61.3177 61.5263 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -61.3177 61.5263 -25 - vertex -66.0782 50.3346 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -50 48.1125 -25 - vertex -63.77 35.8952 -25 - vertex -66.0782 50.3346 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -50 28.8675 -25 - vertex -63.1721 20.406 -25 - vertex -63.77 35.8952 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -50 9.6225 -25 - vertex -67.9289 7.07107 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -65 -0 -25 - vertex -67.9289 7.07107 -25 - vertex -50 9.6225 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -65 -0 -25 - vertex -50 9.6225 -25 - vertex -50 -9.6225 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -65 -0 -25 - vertex -50 -9.6225 -25 - vertex -67.9289 -7.07107 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -86.6025 -25 - vertex -64.2788 -76.6044 -25 - vertex -50 -67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -61.418 -60.2423 -25 - vertex -50 -67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -76.6044 -64.2788 -25 - vertex -63.9539 -44.7004 -25 - vertex -61.418 -60.2423 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -77.4794 -42.1095 -25 - vertex -67.1672 -27.2873 -25 - vertex -63.9539 -44.7004 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -79.8138 -27.1233 -25 - vertex -75 -10 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -86.6025 -50 -25 - vertex -93.9693 -34.202 -25 - vertex -77.4794 -42.1095 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -86.6025 -50 -25 - vertex -77.4794 -42.1095 -25 - vertex -76.6044 -64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 -34.202 -25 - vertex -79.8138 -27.1233 -25 - vertex -77.4794 -42.1095 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -87.1351 -19.2209 -25 - vertex -75 -10 -25 - vertex -79.8138 -27.1233 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -75 -10 -25 - vertex -87.1351 -19.2209 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -87.1351 -19.2209 -25 - vertex -91.5168 -8.74011 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -91.5168 -8.74011 -25 - vertex -85 0 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.20725 58.1596 - vertex -50 9.31671 41.8755 - vertex -50 -7.54086 40.5115 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 7.72654 59.5349 - vertex -50 24.425 45.4369 - vertex -50 9.31671 41.8755 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -50 -72.7398 45.1315 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -50 -67.3575 25 - vertex -50 -86.6025 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -72.7398 45.1315 - vertex -50 -57.0711 42.9289 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -60 50 - vertex -50 -57.0711 42.9289 - vertex -50 -72.7398 45.1315 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -50 60 - vertex -50 -59.3991 66.7554 - vertex -50 -48.1125 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -50 60 - vertex -50 -48.1125 75 - vertex -50 -42.9289 57.0711 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -59.3991 66.7554 - vertex -50 -67.3575 75 - vertex -50 -48.1125 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -72.4016 61.5374 - vertex -50 -86.6025 75 - vertex -50 -67.3575 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -50 -86.6025 75 - vertex -50 -72.4016 61.5374 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -50 -72.4016 61.5374 - vertex -50 -72.7398 45.1315 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -50 -72.7398 45.1315 - vertex -50 -86.6025 41.6667 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -72.4016 61.5374 - vertex -50 -60 50 - vertex -50 -72.7398 45.1315 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -60 50 - vertex -50 -72.4016 61.5374 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -72.4016 61.5374 - vertex -50 -59.3991 66.7554 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -59.3991 66.7554 - vertex -50 -50 60 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -77.7885 41.2952 25 - vertex -81.203 24.5589 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -67.3575 25 - vertex -64.2788 -76.6044 25 - vertex -50 -86.6025 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -61.2753 -61.6257 25 - vertex -64.2788 -76.6044 25 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -76.6044 -64.2788 25 - vertex -64.2788 -76.6044 25 - vertex -61.2753 -61.6257 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 34.202 25 - vertex -90.472 14.6634 25 - vertex -81.203 24.5589 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -93.9693 34.202 25 - vertex -81.203 24.5589 25 - vertex -77.7885 41.2952 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 34.202 25 - vertex -77.7885 41.2952 25 - vertex -86.6025 50 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -77.7885 41.2952 25 - vertex -76.6044 64.2788 25 - vertex -86.6025 50 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.1254 44.5169 25 - vertex -76.6044 64.2788 25 - vertex -77.7885 41.2952 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.2788 76.6044 25 - vertex -76.6044 64.2788 25 - vertex -61.4482 60.1728 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -98.4808 17.3648 25 - vertex -100 0 25 - vertex -90.472 14.6634 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -7.54086 40.5115 - vertex -50 -24.3431 54.6496 - vertex -50 -9.20725 58.1596 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -24.3141 38.9123 - vertex -50 -40 50 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 42.9289 - vertex -50 -40 50 - vertex -50 -24.3141 38.9123 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 57.0711 - vertex -50 -48.1125 75 - vertex -50 -28.8675 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 57.0711 - vertex -50 -28.8675 75 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 57.0711 - vertex -50 -24.3431 54.6496 - vertex -50 -40 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 75 - vertex -50 -9.20725 58.1596 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 75 - vertex -50 7.72654 59.5349 - vertex -50 -9.20725 58.1596 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 9.6225 75 - vertex -50 24.777 61.2904 - vertex -50 7.72654 59.5349 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 28.8675 75 - vertex -50 38.1931 66.569 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 48.1125 75 - vertex -50 50 60 - vertex -50 38.1931 66.569 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 75 - vertex -50 57.0711 57.0711 - vertex -50 50 60 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 72.7615 54.9694 - vertex -50 60 50 - vertex -50 57.0711 57.0711 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 72.9043 38.7048 - vertex -50 57.0711 42.9289 - vertex -50 60 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 25 - vertex -50 50 40 - vertex -50 57.0711 42.9289 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.1125 25 - vertex -50 50 40 - vertex -50 67.3575 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 50 40 - vertex -50 48.1125 25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 48.1125 25 - vertex -50 28.8675 25 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 28.8675 25 - vertex -50 24.425 45.4369 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 24.425 45.4369 - vertex -50 40 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 25 - vertex -50 9.31671 41.8755 - vertex -50 24.425 45.4369 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.6225 25 - vertex -50 -7.54086 40.5115 - vertex -50 9.31671 41.8755 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 25 - vertex -50 -24.3141 38.9123 - vertex -50 -7.54086 40.5115 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 25 - vertex -50 -42.9289 42.9289 - vertex -50 -24.3141 38.9123 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 25 - vertex -50 -50 40 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -67.3575 25 - vertex -50 -50 40 - vertex -50 -48.1125 25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -57.0711 42.9289 - vertex -50 -50 40 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal 0.737448 -0.674954 0.0246338 - outer loop - vertex -21.8234 30.4957 -38.0135 - vertex -33.2312 17.3763 -55.9708 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal -0.252934 -0.966161 0.050566 - outer loop - vertex 16.1087 33.8639 -36.7898 - vertex -1.45427 37.4718 -55.7041 - vertex 19.8668 31.805 -57.3293 - endloop - endfacet - facet normal -0.770325 -0.632173 0.0834073 - outer loop - vertex 31.5798 20.2229 -36.9367 - vertex 19.8668 31.805 -57.3293 - vertex 34.9655 13.5522 -56.227 - endloop - endfacet - facet normal -0.993784 -0.0796494 0.0777769 - outer loop - vertex 37.4996 -0.172499 -37.9034 - vertex 34.9655 13.5522 -56.227 - vertex 36.6441 -7.96625 -56.816 - endloop - endfacet - facet normal -0.877962 0.472106 0.0793671 - outer loop - vertex 32.0358 -19.4924 -39.2304 - vertex 36.6441 -7.96625 -56.816 - vertex 26.8281 -26.2012 -56.9324 - endloop - endfacet - facet normal -0.772989 0.632626 -0.0476708 - outer loop - vertex 33.6967 -16.4554 -19.5029 - vertex 23.2669 -29.4092 -22.2881 - vertex 20 -31.7214 0 - endloop - endfacet - facet normal -0.499519 0.863174 0.0735612 - outer loop - vertex 17.3132 -33.2642 -38.6666 - vertex 26.8281 -26.2012 -56.9324 - vertex 9.4897 -36.2794 -56.4108 - endloop - endfacet - facet normal 0.00744584 0.997883 0.0646006 - outer loop - vertex -1.8284 -37.4554 -36.9408 - vertex 9.4897 -36.2794 -56.4108 - vertex -9.77074 -36.2047 -55.3444 - endloop - endfacet - facet normal 0.765996 0.640114 0.0591945 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -30.9723 -21.1416 -14.419 - vertex -21.223 -30.9166 -34.874 - endloop - endfacet - facet normal 0.771631 0.633319 -0.0591013 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -21.223 -30.9166 -34.874 - vertex -25.0898 -27.8703 -52.7154 - endloop - endfacet - facet normal 0.802894 0.595999 -0.0121428 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -25.0898 -27.8703 -52.7154 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.483318 0.874311 0.0445316 - outer loop - vertex -21.223 -30.9166 -34.874 - vertex -9.77074 -36.2047 -55.3444 - vertex -25.0898 -27.8703 -52.7154 - endloop - endfacet - facet normal 0.95727 0.289114 -0.00690685 - outer loop - vertex -37.4323 -2.25275 2.36658 - vertex -37.4611 -1.70839 21.1626 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.737943 -0.674821 -0.00753515 - outer loop - vertex -20 31.7214 0 - vertex -33.3888 17.0715 0.780048 - vertex -33.1556 17.5202 -16.5603 - endloop - endfacet - facet normal 0.766101 -0.63993 -0.0598234 - outer loop - vertex -20 31.7214 0 - vertex -33.1556 17.5202 -16.5603 - vertex -24.242 28.6108 -21.0482 - endloop - endfacet - facet normal 0.975128 -0.22152 0.0073841 - outer loop - vertex -33.3888 17.0715 0.780048 - vertex -37.4717 -1.45742 -15.9083 - vertex -33.1556 17.5202 -16.5603 - endloop - endfacet - facet normal 0.97829 -0.205806 0.0243364 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -34.2369 15.2998 35.3898 - vertex -37.4611 -1.70839 21.1626 - endloop - endfacet - facet normal 0.978019 -0.20838 0.00753306 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -37.4611 -1.70839 21.1626 - vertex -37.4323 -2.25275 2.36658 - endloop - endfacet - facet normal 0.978844 -0.20459 0.00275438 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -37.4323 -2.25275 2.36658 - vertex -33.3888 17.0715 0.780048 - endloop - endfacet - facet normal 0.97856 -0.205664 -0.01106 - outer loop - vertex -37.4323 -2.25275 2.36658 - vertex -37.4717 -1.45742 -15.9083 - vertex -33.3888 17.0715 0.780048 - endloop - endfacet - facet normal 0.94925 0.314306 0.0116325 - outer loop - vertex -30.9723 -21.1416 -14.419 - vertex -37.4717 -1.45742 -15.9083 - vertex -37.4323 -2.25275 2.36658 - endloop - endfacet - facet normal 0.969427 -0.245379 -0.000218133 - outer loop - vertex -33.2228 17.3925 -36.523 - vertex -37.4964 0.521254 -50.7867 - vertex -33.2312 17.3763 -55.9708 - endloop - endfacet - facet normal 0.975604 0.219484 -0.00487096 - outer loop - vertex -37.5 0 -75 - vertex -37.4964 0.521254 -50.7867 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.984152 -0.172729 0.0401091 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -34.2369 15.2998 35.3898 - vertex -35.6139 11.743 53.8604 - endloop - endfacet - facet normal 0.992874 -0.11854 -0.0122144 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -35.6139 11.743 53.8604 - vertex -37.3561 -3.2825 58.0705 - endloop - endfacet - facet normal 0.964461 0.263926 0.0125572 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -37.3561 -3.2825 58.0705 - vertex -33.3967 -17.056 43.464 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 31.7214 33.3333 - vertex -20 43.9211 27.0189 - vertex -20 42.9289 42.9289 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 31.7214 33.3333 - vertex -20 42.9289 42.9289 - vertex -20 31.7214 50 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 43.9211 27.0189 - vertex -20 50 40 - vertex -20 42.9289 42.9289 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 58.6722 27.2612 - vertex -20 57.0711 42.9289 - vertex -20 50 40 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 74.5519 34.028 - vertex -20 60 50 - vertex -20 57.0711 42.9289 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 78.9898 50 - vertex -20 60 50 - vertex -20 74.5519 34.028 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 81.4151 0 - vertex -20 97.9796 0 - vertex -20 97.9796 16.6667 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 81.4151 0 - vertex -20 97.9796 16.6667 - vertex -20 83.9674 19.9229 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 81.4151 0 - vertex -20 83.9674 19.9229 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 81.4151 0 - vertex -20 68.9073 15.3707 - vertex -20 64.8505 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 83.9674 19.9229 - vertex -20 74.5519 34.028 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 97.9796 33.3333 - vertex -20 78.9898 50 - vertex -20 74.5519 34.028 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 97.9796 50 - vertex -20 78.9898 50 - vertex -20 97.9796 33.3333 - endloop - endfacet - facet normal 0.470977 0.880835 -0.048057 - outer loop - vertex -18.75 -32.476 -75 - vertex -25.0898 -27.8703 -52.7154 - vertex -9.77074 -36.2047 -55.3444 - endloop - endfacet - facet normal 0.326071 0.941988 0.0795955 - outer loop - vertex -13.4703 -34.9972 -18.3411 - vertex -1.8284 -37.4554 -36.9408 - vertex -21.223 -30.9166 -34.874 - endloop - endfacet - facet normal -0.207743 0.975953 0.0660117 - outer loop - vertex 7.0086 -36.8392 -18.2398 - vertex 17.3132 -33.2642 -38.6666 - vertex -1.8284 -37.4554 -36.9408 - endloop - endfacet - facet normal -0.983875 0.178835 0.00285881 - outer loop - vertex 33.7839 -16.2758 -0.75261 - vertex 37.3331 3.53357 -18.437 - vertex 33.6967 -16.4554 -19.5029 - endloop - endfacet - facet normal -0.962216 0.269403 0.0395361 - outer loop - vertex 33.6967 -16.4554 -19.5029 - vertex 37.4996 -0.172499 -37.9034 - vertex 32.0358 -19.4924 -39.2304 - endloop - endfacet - facet normal -0.98005 0.197951 0.0178003 - outer loop - vertex 33.6503 -16.5501 17.5219 - vertex 37.4483 1.96876 20.689 - vertex 37.3569 3.2728 1.15635 - endloop - endfacet - facet normal -0.983616 0.180221 -0.00448245 - outer loop - vertex 33.6503 -16.5501 17.5219 - vertex 37.3569 3.2728 1.15635 - vertex 33.7839 -16.2758 -0.75261 - endloop - endfacet - facet normal -0.952482 -0.304183 -0.0158522 - outer loop - vertex 37.4483 1.96876 20.689 - vertex 32.1117 19.3672 7.48614 - vertex 37.3569 3.2728 1.15635 - endloop - endfacet - facet normal -0.928769 -0.37064 -0.00380635 - outer loop - vertex 37.3331 3.53357 -18.437 - vertex 37.3569 3.2728 1.15635 - vertex 29.4828 23.1736 -15.3386 - endloop - endfacet - facet normal -0.942973 -0.328488 0.0538288 - outer loop - vertex 37.3569 3.2728 1.15635 - vertex 32.1117 19.3672 7.48614 - vertex 29.4828 23.1736 -15.3386 - endloop - endfacet - facet normal -0.957876 -0.287044 0.00891317 - outer loop - vertex 37.4483 1.96876 20.689 - vertex 32.4669 18.7657 26.2883 - vertex 32.1117 19.3672 7.48614 - endloop - endfacet - facet normal -0.958808 -0.280438 0.0451919 - outer loop - vertex 37.3331 3.53357 -18.437 - vertex 31.5798 20.2229 -36.9367 - vertex 37.4996 -0.172499 -37.9034 - endloop - endfacet - facet normal -0.660658 -0.74971 0.038278 - outer loop - vertex 29.4828 23.1736 -15.3386 - vertex 16.1087 33.8639 -36.7898 - vertex 31.5798 20.2229 -36.9367 - endloop - endfacet - facet normal -0.164428 -0.984461 0.0616418 - outer loop - vertex 11.0649 35.8304 -18.8367 - vertex -4.28242 37.2547 -37.0287 - vertex 16.1087 33.8639 -36.7898 - endloop - endfacet - facet normal -0.638659 -0.769303 0.0169588 - outer loop - vertex 22.6774 29.8661 50 - vertex 20 31.7214 33.3333 - vertex 25.1837 27.7854 50 - endloop - endfacet - facet normal -0.702209 -0.710164 0.0506905 - outer loop - vertex 20 31.7214 33.3333 - vertex 27.5 25.4951 50 - vertex 25.1837 27.7854 50 - endloop - endfacet - facet normal -0.770909 -0.626892 0.112714 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 27.5 25.4951 50 - vertex 20 31.7214 33.3333 - endloop - endfacet - facet normal -0.958919 -0.28066 0.0412778 - outer loop - vertex 33.5378 16.777 61.0519 - vertex 37.3559 3.28438 58.0102 - vertex 36.3417 9.24839 75 - endloop - endfacet - facet normal -0.875455 -0.476434 -0.0811725 - outer loop - vertex 33.5378 16.777 61.0519 - vertex 36.3417 9.24839 75 - vertex 27.5 25.4951 75 - endloop - endfacet - facet normal -0.998223 0 -0.0595897 - outer loop - vertex 37.3559 3.28438 58.0102 - vertex 36.3417 -9.24839 75 - vertex 36.3417 9.24839 75 - endloop - endfacet - facet normal -0.99382 0.108982 0.0210656 - outer loop - vertex 35.6194 -11.7263 53.7453 - vertex 36.3417 -9.24839 75 - vertex 37.3559 3.28438 58.0102 - endloop - endfacet - facet normal -0.861383 0.507956 0 - outer loop - vertex 27.5 -25.4951 50 - vertex 27.5 -25.4951 62.5 - vertex 35.6194 -11.7263 53.7453 - endloop - endfacet - facet normal -0.868763 0.494428 -0.0281209 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 36.3417 -9.24839 75 - vertex 35.6194 -11.7263 53.7453 - endloop - endfacet - facet normal -0.878353 0.478012 0 - outer loop - vertex 27.5 -25.4951 75 - vertex 36.3417 -9.24839 75 - vertex 27.5 -25.4951 62.5 - endloop - endfacet - facet normal -0.984519 0.170877 0.0390314 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 35.6194 -11.7263 53.7453 - vertex 37.4402 2.11676 39.0684 - endloop - endfacet - facet normal -0.983644 0.180113 -0.0018825 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 37.4402 2.11676 39.0684 - vertex 37.4483 1.96876 20.689 - endloop - endfacet - facet normal -0.98008 0.197616 0.0197939 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 37.4483 1.96876 20.689 - vertex 33.6503 -16.5501 17.5219 - endloop - endfacet - facet normal -0.958556 -0.284899 0.00187311 - outer loop - vertex 37.4402 2.11676 39.0684 - vertex 32.4669 18.7657 26.2883 - vertex 37.4483 1.96876 20.689 - endloop - endfacet - facet normal -0.963049 -0.268119 0.0254811 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 32.4669 18.7657 26.2883 - vertex 37.4402 2.11676 39.0684 - endloop - endfacet - facet normal -0.964297 -0.26455 0.0120152 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 37.4402 2.11676 39.0684 - vertex 37.3559 3.28438 58.0102 - endloop - endfacet - facet normal -0.962008 -0.273 0.00342495 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 37.3559 3.28438 58.0102 - vertex 33.5378 16.777 61.0519 - endloop - endfacet - facet normal -0.992922 0.118189 -0.0117053 - outer loop - vertex 37.4402 2.11676 39.0684 - vertex 35.6194 -11.7263 53.7453 - vertex 37.3559 3.28438 58.0102 - endloop - endfacet - facet normal -0.856738 0.514598 -0.0344844 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 27.5 -25.4951 50 - vertex 35.6194 -11.7263 53.7453 - endloop - endfacet - facet normal 0.63022 0.771575 0.0865655 - outer loop - vertex -30.9723 -21.1416 -14.419 - vertex -20 -31.7214 0 - vertex -13.4703 -34.9972 -18.3411 - endloop - endfacet - facet normal 0.718226 0.69581 0 - outer loop - vertex -20 -31.7214 16.6667 - vertex -20 -31.7214 0 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.721158 0.692771 0 - outer loop - vertex -20 -31.7214 33.3333 - vertex -20 -31.7214 16.6667 - vertex -32.4986 -18.7106 26.4243 - endloop - endfacet - facet normal 0.56957 0.821943 0 - outer loop - vertex -22.6774 -29.8661 50 - vertex -20 -31.7214 50 - vertex -20 -31.7214 33.3333 - endloop - endfacet - facet normal 0.638659 0.769303 0.0169588 - outer loop - vertex -22.6774 -29.8661 50 - vertex -20 -31.7214 33.3333 - vertex -25.1837 -27.7854 50 - endloop - endfacet - facet normal 0.702209 0.710164 0.0506905 - outer loop - vertex -20 -31.7214 33.3333 - vertex -27.5 -25.4951 50 - vertex -25.1837 -27.7854 50 - endloop - endfacet - facet normal 0.771234 0.626436 0.113031 - outer loop - vertex -33.3967 -17.056 43.464 - vertex -27.5 -25.4951 50 - vertex -20 -31.7214 33.3333 - endloop - endfacet - facet normal 0.993786 -0.10925 0.0213191 - outer loop - vertex -35.6139 11.743 53.8604 - vertex -36.3417 9.24839 75 - vertex -37.3561 -3.2825 58.0705 - endloop - endfacet - facet normal 0.878353 -0.478012 0 - outer loop - vertex -27.5 25.4951 62.5 - vertex -27.5 25.4951 75 - vertex -36.3417 9.24839 75 - endloop - endfacet - facet normal 0.958921 0.280631 0.0414365 - outer loop - vertex -33.5351 -16.7824 61.0745 - vertex -37.3561 -3.2825 58.0705 - vertex -36.3417 -9.24839 75 - endloop - endfacet - facet normal 0.99821 0 -0.0598108 - outer loop - vertex -37.3561 -3.2825 58.0705 - vertex -36.3417 9.24839 75 - vertex -36.3417 -9.24839 75 - endloop - endfacet - facet normal 0.86864 -0.494626 -0.0284651 - outer loop - vertex -35.6139 11.743 53.8604 - vertex -27.5 25.4951 62.5 - vertex -36.3417 9.24839 75 - endloop - endfacet - facet normal 0.861264 -0.508157 0 - outer loop - vertex -27.5 25.4951 50 - vertex -27.5 25.4951 62.5 - vertex -35.6139 11.743 53.8604 - endloop - endfacet - facet normal 0.856349 -0.515185 -0.0353649 - outer loop - vertex -27.5 25.4951 50 - vertex -35.6139 11.743 53.8604 - vertex -34.2369 15.2998 35.3898 - endloop - endfacet - facet normal 0.757952 -0.644556 0.100285 - outer loop - vertex -27.5 25.4951 50 - vertex -34.2369 15.2998 35.3898 - vertex -20 31.7214 33.3333 - endloop - endfacet - facet normal 0.702209 -0.710164 0.0506905 - outer loop - vertex -27.5 25.4951 50 - vertex -20 31.7214 33.3333 - vertex -25.1837 27.7854 50 - endloop - endfacet - facet normal 0.638659 -0.769303 0.0169588 - outer loop - vertex -20 31.7214 33.3333 - vertex -22.6774 29.8661 50 - vertex -25.1837 27.7854 50 - endloop - endfacet - facet normal 0.56957 -0.821943 0 - outer loop - vertex -20 31.7214 50 - vertex -22.6774 29.8661 50 - vertex -20 31.7214 33.3333 - endloop - endfacet - facet normal 0.959549 0.281504 0.00466012 - outer loop - vertex -32.4986 -18.7106 26.4243 - vertex -37.4611 -1.70839 21.1626 - vertex -37.4428 -2.06999 39.2501 - endloop - endfacet - facet normal 0.983195 -0.182498 -0.00463993 - outer loop - vertex -37.4611 -1.70839 21.1626 - vertex -34.2369 15.2998 35.3898 - vertex -37.4428 -2.06999 39.2501 - endloop - endfacet - facet normal 0.753547 -0.656799 -0.0279772 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -20 31.7214 33.3333 - vertex -34.2369 15.2998 35.3898 - endloop - endfacet - facet normal 0.739819 -0.672805 0 - outer loop - vertex -20 31.7214 16.6667 - vertex -20 31.7214 33.3333 - vertex -33.4723 16.9073 18.2472 - endloop - endfacet - facet normal 0.739668 -0.672966 -0.00279397 - outer loop - vertex -20 31.7214 16.6667 - vertex -33.4723 16.9073 18.2472 - vertex -33.3888 17.0715 0.780048 - endloop - endfacet - facet normal 0.738164 -0.674621 0 - outer loop - vertex -20 31.7214 16.6667 - vertex -33.3888 17.0715 0.780048 - vertex -20 31.7214 0 - endloop - endfacet - facet normal 0.298174 -0.953904 0.0340648 - outer loop - vertex -1.45427 37.4718 -55.7041 - vertex -4.28242 37.2547 -37.0287 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal 0.360616 -0.932411 -0.023786 - outer loop - vertex -4.28242 37.2547 -37.0287 - vertex -21.8234 30.4957 -38.0135 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal 0.357058 -0.933048 0.0439505 - outer loop - vertex -8.64115 36.4908 -17.8341 - vertex -21.8234 30.4957 -38.0135 - vertex -4.28242 37.2547 -37.0287 - endloop - endfacet - facet normal -0.0358893 -0.998208 -0.0478732 - outer loop - vertex -8.64115 36.4908 -17.8341 - vertex -4.28242 37.2547 -37.0287 - vertex 11.0649 35.8304 -18.8367 - endloop - endfacet - facet normal -0.0310724 -0.998415 0.0469324 - outer loop - vertex -8.64115 36.4908 -17.8341 - vertex 11.0649 35.8304 -18.8367 - vertex 6.99057 36.8427 0 - endloop - endfacet - facet normal -0.366139 -0.930102 -0.0292124 - outer loop - vertex 11.0649 35.8304 -18.8367 - vertex 20 31.7214 0 - vertex 6.99057 36.8427 0 - endloop - endfacet - facet normal -0.576081 -0.811712 0.0961981 - outer loop - vertex 29.4828 23.1736 -15.3386 - vertex 20 31.7214 0 - vertex 11.0649 35.8304 -18.8367 - endloop - endfacet - facet normal -0.714081 -0.700063 -0 - outer loop - vertex 20 31.7214 16.6667 - vertex 20 31.7214 0 - vertex 32.1117 19.3672 7.48614 - endloop - endfacet - facet normal -0.720571 -0.693381 -0 - outer loop - vertex 20 31.7214 33.3333 - vertex 20 31.7214 16.6667 - vertex 32.4669 18.7657 26.2883 - endloop - endfacet - facet normal -0.56957 -0.821943 0 - outer loop - vertex 22.6774 29.8661 50 - vertex 20 31.7214 50 - vertex 20 31.7214 33.3333 - endloop - endfacet - facet normal -0.0755011 -0.381591 0.921243 - outer loop - vertex 35.1847 56.4486 36.4569 - vertex 50 50 35 - vertex 50 60.6066 39.3934 - endloop - endfacet - facet normal 0.0536682 -0.101139 0.993424 - outer loop - vertex 37.135 46.7259 35.3617 - vertex 50 50 35 - vertex 35.1847 56.4486 36.4569 - endloop - endfacet - facet normal -0.0712363 0.381711 0.921532 - outer loop - vertex 50 39.3934 39.3934 - vertex 50 50 35 - vertex 37.135 46.7259 35.3617 - endloop - endfacet - facet normal 0.08531 0.983511 -0.15946 - outer loop - vertex 38.773 37.2567 57.9126 - vertex 50 35 50 - vertex 39.5601 35.3693 46.6922 - endloop - endfacet - facet normal -0.140805 -0.510153 -0.84848 - outer loop - vertex 38.7482 50.1971 64.9987 - vertex 27.5 60.6066 60.6066 - vertex 38.6605 63.1428 57.2297 - endloop - endfacet - facet normal -0.139866 -0.989431 -0.038264 - outer loop - vertex 36.8547 63.896 44.352 - vertex 38.6605 63.1428 57.2297 - vertex 27.5 65 50 - endloop - endfacet - facet normal 0.0937393 -0.919811 -0.380998 - outer loop - vertex 38.6605 63.1428 57.2297 - vertex 27.5 60.6066 60.6066 - vertex 27.5 65 50 - endloop - endfacet - facet normal 0.00660064 -0.382675 -0.923859 - outer loop - vertex 38.7482 50.1971 64.9987 - vertex 27.5 50 65 - vertex 27.5 60.6066 60.6066 - endloop - endfacet - facet normal -0.00681352 0.382675 -0.923858 - outer loop - vertex 27.5 39.3934 60.6066 - vertex 27.5 50 65 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal 0.11817 0.477108 -0.870864 - outer loop - vertex 50 39.3934 60.6066 - vertex 38.773 37.2567 57.9126 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal -0.117805 0.476781 -0.871092 - outer loop - vertex 38.773 37.2567 57.9126 - vertex 27.5 39.3934 60.6066 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal 0.0833664 0.920663 -0.381351 - outer loop - vertex 27.5 35 50 - vertex 27.5 39.3934 60.6066 - vertex 38.773 37.2567 57.9126 - endloop - endfacet - facet normal -0.0768792 0.98233 -0.170639 - outer loop - vertex 27.5 35 50 - vertex 38.773 37.2567 57.9126 - vertex 39.5601 35.3693 46.6922 - endloop - endfacet - facet normal 0.0884741 0.901691 0.423233 - outer loop - vertex 27.5 35 50 - vertex 39.5601 35.3693 46.6922 - vertex 32.3647 39.5932 39.1973 - endloop - endfacet - facet normal -0.00874161 0.921644 0.387939 - outer loop - vertex 27.5 35 50 - vertex 32.3647 39.5932 39.1973 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal 0 0.92388 0.382683 - outer loop - vertex 27.5 35 50 - vertex 20 39.3934 39.3934 - vertex 20 35 50 - endloop - endfacet - facet normal 0.00847025 0.38267 0.923846 - outer loop - vertex 32.3647 39.5932 39.1973 - vertex 20 50 35 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal 0.0648869 0.438604 0.896335 - outer loop - vertex 37.135 46.7259 35.3617 - vertex 20 50 35 - vertex 32.3647 39.5932 39.1973 - endloop - endfacet - facet normal 0.0736745 -0.381643 0.921369 - outer loop - vertex 20 60.6066 39.3934 - vertex 20 50 35 - vertex 35.1847 56.4486 36.4569 - endloop - endfacet - facet normal -0.0631637 -0.719272 0.691851 - outer loop - vertex 20 60.6066 39.3934 - vertex 35.1847 56.4486 36.4569 - vertex 36.8547 63.896 44.352 - endloop - endfacet - facet normal -0.0439642 -0.120533 0.991735 - outer loop - vertex 20 50 35 - vertex 37.135 46.7259 35.3617 - vertex 35.1847 56.4486 36.4569 - endloop - endfacet - facet normal -0.00438928 0.475882 0.879498 - outer loop - vertex 32.3647 39.5932 39.1973 - vertex 50 39.3934 39.3934 - vertex 37.135 46.7259 35.3617 - endloop - endfacet - facet normal -0.0882265 0.920277 0.381191 - outer loop - vertex 39.5601 35.3693 46.6922 - vertex 50 35 50 - vertex 50 39.3934 39.3934 - endloop - endfacet - facet normal -0.0837053 0.920637 -0.38134 - outer loop - vertex 38.773 37.2567 57.9126 - vertex 50 39.3934 60.6066 - vertex 50 35 50 - endloop - endfacet - facet normal 0.00681138 0.382675 -0.923858 - outer loop - vertex 38.7482 50.1971 64.9987 - vertex 50 50 65 - vertex 50 39.3934 60.6066 - endloop - endfacet - facet normal -0.00659857 -0.382675 -0.923859 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 50 65 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -0 60.5293 0 - vertex 0 47.412 0 - vertex 20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 48.286 0 - vertex -6.99057 36.8427 0 - vertex 0 47.412 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 31.7214 0 - vertex -6.99057 36.8427 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 -64.8505 0 - vertex 20 -48.286 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 -81.4151 0 - vertex 20 -64.8505 0 - vertex 0 -71.7622 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -81.4151 0 - vertex -20 -97.9796 0 - vertex -13.3836 -99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -6.99057 -36.8427 0 - vertex -20 -31.7214 0 - vertex -20 -48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -87.0832 0 - vertex 0 -100 0 - vertex 6.70689 -99.7748 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -6.70689 -99.7748 0 - vertex 0 -100 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -6.70689 -99.7748 0 - vertex 0 -87.0832 0 - vertex -13.3836 -99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -87.0832 0 - vertex -20 -81.4151 0 - vertex -13.3836 -99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -71.7622 0 - vertex -20 -81.4151 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -64.8505 0 - vertex -20 -81.4151 0 - vertex 0 -71.7622 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -20 -64.8505 0 - vertex 0 -71.7622 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -64.8505 0 - vertex 0 -54.2451 0 - vertex -20 -48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -54.2451 0 - vertex -6.99057 -36.8427 0 - vertex -20 -48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 6.99057 -36.8427 0 - vertex -6.99057 -36.8427 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 13.3836 -99.1004 0 - vertex 20 -97.9796 0 - vertex 20 -81.4151 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 13.3836 -99.1004 0 - vertex 20 -81.4151 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 13.3836 -99.1004 0 - vertex 0 -87.0832 0 - vertex 6.70689 -99.7748 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -81.4151 0 - vertex 0 -71.7622 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -64.8505 0 - vertex 0 -54.2451 0 - vertex 0 -71.7622 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -48.286 0 - vertex 6.99057 -36.8427 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -31.7214 0 - vertex 6.99057 -36.8427 0 - vertex 20 -48.286 0 - endloop - endfacet - facet normal 0.00446811 0.872995 0.487709 - outer loop - vertex 50 39.3934 39.3934 - vertex 32.3647 39.5932 39.1973 - vertex 39.5601 35.3693 46.6922 - endloop - endfacet - facet normal 0.0716859 -0.733081 0.676353 - outer loop - vertex 36.8547 63.896 44.352 - vertex 35.1847 56.4486 36.4569 - vertex 50 60.6066 39.3934 - endloop - endfacet - facet normal -0.0865095 -0.920416 0.381249 - outer loop - vertex 36.8547 63.896 44.352 - vertex 50 60.6066 39.3934 - vertex 50 65 50 - endloop - endfacet - facet normal 0.0168795 -0.917292 0.397858 - outer loop - vertex -20 -42.9289 42.9289 - vertex -27.5 -40 50 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal -0.014886 -0.382641 0.923777 - outer loop - vertex -20 -42.9289 42.9289 - vertex -35.8862 -43.4206 42.4693 - vertex -20 -50 40 - endloop - endfacet - facet normal 0.0740257 -0.936443 0.34292 - outer loop - vertex -27.5 -40 50 - vertex -38.4021 -40.1766 51.8711 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal 0.0384378 -0.84761 -0.529225 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -37.0198 -43.8869 57.9139 - vertex -38.4021 -40.1766 51.8711 - endloop - endfacet - facet normal -0.041706 -0.380244 -0.923945 - outer loop - vertex -27.5 -50 60 - vertex -40.5084 -48.1569 59.8287 - vertex -37.0198 -43.8869 57.9139 - endloop - endfacet - facet normal -0.0423273 0.125856 -0.991145 - outer loop - vertex -38.7903 -54.4475 58.9565 - vertex -50 -50 60 - vertex -40.5084 -48.1569 59.8287 - endloop - endfacet - facet normal 0.0656897 0.381857 -0.921884 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -50 60 - vertex -38.7903 -54.4475 58.9565 - endloop - endfacet - facet normal -0.0616004 0.742535 -0.666968 - outer loop - vertex -50 -57.0711 57.0711 - vertex -38.7903 -54.4475 58.9565 - vertex -38.6088 -59.3911 53.4361 - endloop - endfacet - facet normal 0.0659079 0.921871 -0.381851 - outer loop - vertex -50 -57.0711 57.0711 - vertex -38.6088 -59.3911 53.4361 - vertex -50 -60 50 - endloop - endfacet - facet normal -0.0669819 0.996719 0.0454434 - outer loop - vertex -38.6088 -59.3911 53.4361 - vertex -36.6093 -58.8915 45.4238 - vertex -50 -60 50 - endloop - endfacet - facet normal -0.0530498 0.941221 0.333599 - outer loop - vertex -27.5 -60 50 - vertex -20 -57.0711 42.9289 - vertex -36.6093 -58.8915 45.4238 - endloop - endfacet - facet normal 0 0.92388 0.382683 - outer loop - vertex -20 -60 50 - vertex -20 -57.0711 42.9289 - vertex -27.5 -60 50 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 83.9674 19.9229 - vertex -20 97.9796 33.3333 - vertex -20 74.5519 34.028 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 97.9796 16.6667 - vertex -20 97.9796 33.3333 - vertex -20 83.9674 19.9229 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 64.8505 0 - vertex -20 68.9073 15.3707 - vertex -20 49.7152 12.4405 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 64.8505 0 - vertex -20 49.7152 12.4405 - vertex -20 48.286 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 49.7152 12.4405 - vertex -20 31.7214 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 31.7214 16.6667 - vertex -20 31.7214 0 - vertex -20 49.7152 12.4405 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 42.9289 42.9289 - vertex -20 40 50 - vertex -20 31.7214 50 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 49.7152 12.4405 - vertex -20 58.6722 27.2612 - vertex -20 43.9211 27.0189 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 58.6722 27.2612 - vertex -20 50 40 - vertex -20 43.9211 27.0189 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 74.5519 34.028 - vertex -20 57.0711 42.9289 - vertex -20 58.6722 27.2612 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 74.5519 34.028 - vertex -20 58.6722 27.2612 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 58.6722 27.2612 - vertex -20 49.7152 12.4405 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 43.9211 27.0189 - vertex -20 31.7214 16.6667 - vertex -20 49.7152 12.4405 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 31.7214 33.3333 - vertex -20 31.7214 16.6667 - vertex -20 43.9211 27.0189 - endloop - endfacet - facet normal 0.139175 -0.508876 -0.849515 - outer loop - vertex 50 60.6066 60.6066 - vertex 38.7482 50.1971 64.9987 - vertex 38.6605 63.1428 57.2297 - endloop - endfacet - facet normal -0.0922717 -0.919938 -0.381051 - outer loop - vertex 50 60.6066 60.6066 - vertex 38.6605 63.1428 57.2297 - vertex 50 65 50 - endloop - endfacet - facet normal 0.115018 -0.990598 -0.0740738 - outer loop - vertex 38.6605 63.1428 57.2297 - vertex 36.8547 63.896 44.352 - vertex 50 65 50 - endloop - endfacet - facet normal 0.0870649 -0.940636 0.32806 - outer loop - vertex 27.5 65 50 - vertex 20 60.6066 39.3934 - vertex 36.8547 63.896 44.352 - endloop - endfacet - facet normal 0 -0.92388 0.382683 - outer loop - vertex 20 65 50 - vertex 20 60.6066 39.3934 - vertex 27.5 65 50 - endloop - endfacet - facet normal -0.0644628 -0.948538 0.310034 - outer loop - vertex -38.4021 -40.1766 51.8711 - vertex -50 -40 50 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal -0.0458155 0.382282 0.922909 - outer loop - vertex -20 -50 40 - vertex -35.1456 -52.7371 40.3819 - vertex -20 -57.0711 42.9289 - endloop - endfacet - facet normal 0.0631494 -0.213415 0.974919 - outer loop - vertex -35.8862 -43.4206 42.4693 - vertex -35.1456 -52.7371 40.3819 - vertex -20 -50 40 - endloop - endfacet - facet normal -0.0661214 -0.223157 0.972537 - outer loop - vertex -50 -50 40 - vertex -35.1456 -52.7371 40.3819 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal 0.0167548 -0.38263 0.92375 - outer loop - vertex -50 -50 40 - vertex -35.8862 -43.4206 42.4693 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal -0.0197191 -0.9237 0.382609 - outer loop - vertex -35.8862 -43.4206 42.4693 - vertex -50 -40 50 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal 0.0476162 -0.922832 -0.382249 - outer loop - vertex -38.4021 -40.1766 51.8711 - vertex -50 -42.9289 57.0711 - vertex -50 -40 50 - endloop - endfacet - facet normal -0.0294432 -0.854804 -0.518115 - outer loop - vertex -37.0198 -43.8869 57.9139 - vertex -50 -42.9289 57.0711 - vertex -38.4021 -40.1766 51.8711 - endloop - endfacet - facet normal 0.0271348 -0.42739 -0.90366 - outer loop - vertex -40.5084 -48.1569 59.8287 - vertex -50 -42.9289 57.0711 - vertex -37.0198 -43.8869 57.9139 - endloop - endfacet - facet normal 0.0575385 -0.382049 -0.922349 - outer loop - vertex -50 -50 60 - vertex -50 -42.9289 57.0711 - vertex -40.5084 -48.1569 59.8287 - endloop - endfacet - facet normal 0.0620055 0.744536 -0.664697 - outer loop - vertex -38.7903 -54.4475 58.9565 - vertex -27.5 -57.0711 57.0711 - vertex -38.6088 -59.3911 53.4361 - endloop - endfacet - facet normal 0.0797698 0.993446 0.0818605 - outer loop - vertex -36.6093 -58.8915 45.4238 - vertex -38.6088 -59.3911 53.4361 - vertex -27.5 -60 50 - endloop - endfacet - facet normal -0.0675762 0.921768 -0.381809 - outer loop - vertex -38.6088 -59.3911 53.4361 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -60 50 - endloop - endfacet - facet normal -0.0652233 0.381869 -0.921912 - outer loop - vertex -38.7903 -54.4475 58.9565 - vertex -27.5 -50 60 - vertex -27.5 -57.0711 57.0711 - endloop - endfacet - facet normal 0.0337465 0.146291 -0.988666 - outer loop - vertex -40.5084 -48.1569 59.8287 - vertex -27.5 -50 60 - vertex -38.7903 -54.4475 58.9565 - endloop - endfacet - facet normal -0.0432463 -0.382325 -0.923015 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -50 60 - vertex -37.0198 -43.8869 57.9139 - endloop - endfacet - facet normal -0.0506479 -0.922694 -0.382192 - outer loop - vertex -27.5 -40 50 - vertex -27.5 -42.9289 57.0711 - vertex -38.4021 -40.1766 51.8711 - endloop - endfacet - facet normal 0.0542188 0.922521 0.382121 - outer loop - vertex -50 -57.0711 42.9289 - vertex -50 -60 50 - vertex -36.6093 -58.8915 45.4238 - endloop - endfacet - facet normal -0.055595 0.640627 0.765837 - outer loop - vertex -50 -57.0711 42.9289 - vertex -36.6093 -58.8915 45.4238 - vertex -35.1456 -52.7371 40.3819 - endloop - endfacet - facet normal 0.0467119 0.382266 0.922871 - outer loop - vertex -50 -57.0711 42.9289 - vertex -35.1456 -52.7371 40.3819 - vertex -50 -50 40 - endloop - endfacet - facet normal 0.0482791 0.626093 0.778252 - outer loop - vertex -36.6093 -58.8915 45.4238 - vertex -20 -57.0711 42.9289 - vertex -35.1456 -52.7371 40.3819 - endloop - endfacet - facet normal 0 -0.92388 0.382683 - outer loop - vertex -20 -42.9289 42.9289 - vertex -20 -40 50 - vertex -27.5 -40 50 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.2388 40.5597 - vertex 50 17.7589 37.3466 - vertex 50 28.8675 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 17.7589 37.3466 - vertex 50 9.6225 25 - vertex 50 28.8675 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 4.24366 42.6158 - vertex 50 -9.6225 25 - vertex 50 9.6225 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -12.3722 39.0134 - vertex 50 -28.8675 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -23.0532 44.8966 - vertex 50 -39.3934 39.3934 - vertex 50 -28.8675 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -35 50 - vertex 50 -39.3934 39.3934 - vertex 50 -23.0532 44.8966 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -35 50 - vertex 50 -23.0532 44.8966 - vertex 50 -22.2245 61.2431 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -35 50 - vertex 50 -22.2245 61.2431 - vertex 50 -39.3934 60.6066 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -22.2245 61.2431 - vertex 50 -28.8675 75 - vertex 50 -39.3934 60.6066 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -9.6225 75 - vertex 50 -28.8675 75 - vertex 50 -22.2245 61.2431 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -9.6225 75 - vertex 50 -22.2245 61.2431 - vertex 50 -5.58971 57.5541 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -9.6225 75 - vertex 50 -5.58971 57.5541 - vertex 50 9.6225 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -5.58971 57.5541 - vertex 50 11.8037 60.8572 - vertex 50 9.6225 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 4.24366 42.6158 - vertex 50 22.5939 54.2272 - vertex 50 11.8037 60.8572 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 17.7589 37.3466 - vertex 50 28.2388 40.5597 - vertex 50 22.5939 54.2272 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 28.8675 25 - vertex 50 39.3934 39.3934 - vertex 50 28.2388 40.5597 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 48.1125 25 - vertex 50 50 35 - vertex 50 39.3934 39.3934 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 67.3575 25 - vertex 50 50 35 - vertex 50 48.1125 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 60.6066 39.3934 - vertex 50 50 35 - vertex 50 67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 41.6667 - vertex 50 74.2906 44.8203 - vertex 50 67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 41.6667 - vertex 50 67.3575 25 - vertex 50 86.6025 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.2906 44.8203 - vertex 50 60.6066 39.3934 - vertex 50 67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 65 50 - vertex 50 60.6066 39.3934 - vertex 50 74.2906 44.8203 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 74.3415 61.8582 - vertex 50 86.6025 75 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 86.6025 75 - vertex 50 74.3415 61.8582 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 74.3415 61.8582 - vertex 50 74.2906 44.8203 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -74.3334 62.5671 - vertex 50 -60.6066 60.6066 - vertex 50 -67.3575 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -65 50 - vertex 50 -60.6066 60.6066 - vertex 50 -74.3334 62.5671 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 58.3333 - vertex 50 -75.4061 48.0166 - vertex 50 -74.3334 62.5671 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 58.3333 - vertex 50 -74.3334 62.5671 - vertex 50 -86.6025 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -75.4061 48.0166 - vertex 50 -65 50 - vertex 50 -74.3334 62.5671 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -60.6066 39.3934 - vertex 50 -65 50 - vertex 50 -75.4061 48.0166 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 25 - vertex 50 -50 35 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -60.6066 39.3934 - vertex 50 -75.1752 35.2676 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -75.1752 35.2676 - vertex 50 -86.6025 25 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -86.6025 25 - vertex 50 -75.1752 35.2676 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -75.1752 35.2676 - vertex 50 -75.4061 48.0166 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -75.4061 48.0166 - vertex 50 -86.6025 58.3333 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -75.1752 35.2676 - vertex 50 -60.6066 39.3934 - vertex 50 -75.4061 48.0166 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -67.3575 25 - vertex 50 -50 35 - vertex 50 -60.6066 39.3934 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -48.1125 25 - vertex 50 -39.3934 39.3934 - vertex 50 -50 35 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -28.8675 25 - vertex 50 -39.3934 39.3934 - vertex 50 -48.1125 25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -39.3934 60.6066 - vertex 50 -28.8675 75 - vertex 50 -48.1125 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -39.3934 60.6066 - vertex 50 -48.1125 75 - vertex 50 -50 65 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 48.1125 75 - vertex 50 50 65 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.3934 60.6066 - vertex 50 50 65 - vertex 50 48.1125 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 9.6225 75 - vertex 50 11.8037 60.8572 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 11.8037 60.8572 - vertex 50 22.5939 54.2272 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 22.5939 54.2272 - vertex 50 39.3934 60.6066 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 39.3934 60.6066 - vertex 50 48.1125 75 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 22.5939 54.2272 - vertex 50 35 50 - vertex 50 39.3934 60.6066 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 28.2388 40.5597 - vertex 50 35 50 - vertex 50 22.5939 54.2272 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.3934 39.3934 - vertex 50 35 50 - vertex 50 28.2388 40.5597 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 79.858 -27.4478 25 - vertex 77.6146 -42.5462 25 - vertex 93.9693 -34.202 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 77.6146 -42.5462 25 - vertex 86.6025 -50 25 - vertex 93.9693 -34.202 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 86.6025 -50 25 - vertex 77.6146 -42.5462 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 77.6146 -42.5462 25 - vertex 63.9444 -45.2133 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 63.9444 -45.2133 25 - vertex 61.3915 -60.3858 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 61.3915 -60.3858 25 - vertex 64.2788 -76.6044 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 61.3915 -60.3858 25 - vertex 50 -67.3575 25 - vertex 64.2788 -76.6044 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -48.1125 25 - vertex 50 -67.3575 25 - vertex 61.3915 -60.3858 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 -48.1125 25 - vertex 61.3915 -60.3858 25 - vertex 63.9444 -45.2133 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -48.1125 25 - vertex 63.9444 -45.2133 25 - vertex 50 -28.8675 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 63.9444 -45.2133 25 - vertex 67.3911 -29.0453 25 - vertex 50 -28.8675 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 77.6146 -42.5462 25 - vertex 79.858 -27.4478 25 - vertex 67.3911 -29.0453 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 -34.202 25 - vertex 87.1138 -19.2772 25 - vertex 79.858 -27.4478 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 98.4808 -17.3648 25 - vertex 91.5102 -8.75708 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 100 0 25 - vertex 85 0 25 - vertex 91.5102 -8.75708 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 98.4808 17.3648 25 - vertex 89.7303 15.4472 25 - vertex 100 0 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 89.7303 15.4472 25 - vertex 85 0 25 - vertex 100 0 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 82.0711 7.07107 25 - vertex 85 0 25 - vertex 89.7303 15.4472 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 77.6996 42.7398 25 - vertex 86.6025 50 25 - vertex 76.6044 64.2788 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 86.6025 50 25 - vertex 77.6996 42.7398 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 77.6996 42.7398 25 - vertex 78.1402 25.7865 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 78.1402 25.7865 25 - vertex 89.7303 15.4472 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 89.7303 15.4472 25 - vertex 98.4808 17.3648 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 78.1402 25.7865 25 - vertex 82.0711 7.07107 25 - vertex 89.7303 15.4472 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 75 10 25 - vertex 82.0711 7.07107 25 - vertex 78.1402 25.7865 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 64.2788 25 - vertex 61.3178 61.5265 25 - vertex 66.0812 50.3368 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 74.2906 44.8203 - vertex 50 86.6025 41.6667 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.3415 61.8582 - vertex 50 65 50 - vertex 50 74.2906 44.8203 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 65 50 - vertex 50 74.3415 61.8582 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 74.3415 61.8582 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 67.3575 75 - vertex 50 50 65 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 77.6146 -42.5462 25 - vertex 67.3911 -29.0453 25 - vertex 63.9444 -45.2133 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 78.1402 25.7865 25 - vertex 63.7764 35.8998 25 - vertex 63.1835 20.4106 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 91.5102 -8.75708 25 - vertex 82.0711 -7.07107 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 85 0 25 - vertex 82.0711 -7.07107 25 - vertex 91.5102 -8.75708 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 48.1125 25 - vertex 50 28.8675 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 28.8675 25 - vertex 63.1835 20.4106 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 9.6225 25 - vertex 63.1835 20.4106 25 - vertex 50 28.8675 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 77.6996 42.7398 25 - vertex 66.0812 50.3368 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 66.0812 50.3368 25 - vertex 50 48.1125 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 98.4808 -17.3648 25 - vertex 100 0 25 - vertex 91.5102 -8.75708 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 93.9693 -34.202 25 - vertex 98.4808 -17.3648 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -86.6025 25 - vertex 64.2788 -76.6044 25 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -9.6225 25 - vertex 65 -0 25 - vertex 50 9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 67.9289 -7.07107 25 - vertex 65 -0 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 -28.8675 25 - vertex 67.3911 -29.0453 25 - vertex 60.991 -18.0167 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -28.8675 25 - vertex 60.991 -18.0167 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 60.991 -18.0167 25 - vertex 67.9289 -7.07107 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 67.9289 -7.07107 25 - vertex 60.991 -18.0167 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 60.991 -18.0167 25 - vertex 67.3911 -29.0453 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 67.3911 -29.0453 25 - vertex 79.858 -27.4478 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 79.858 -27.4478 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 75 -10 25 - vertex 87.1138 -19.2772 25 - vertex 82.0711 -7.07107 25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -34.202 93.9693 -75 - vertex -20.4052 79.7278 -75 - vertex -37.0799 77.7597 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -34.202 93.9693 -75 - vertex -37.0799 77.7597 -75 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -20.4052 79.7278 -75 - vertex -32.8384 61.9158 -75 - vertex -37.0799 77.7597 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -12.9612 63.5763 -75 - vertex -29.95 43.1732 -75 - vertex -32.8384 61.9158 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -6.73263 49.1968 -75 - vertex -18.75 32.476 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 0 37.5 -75 - vertex -18.75 32.476 -75 - vertex -6.73263 49.1968 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -17.3648 98.4808 -75 - vertex 0 100 -75 - vertex 1.4079 82.2671 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -17.3648 98.4808 -75 - vertex 1.4079 82.2671 -75 - vertex -20.4052 79.7278 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -17.3648 98.4808 -75 - vertex -20.4052 79.7278 -75 - vertex -34.202 93.9693 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 1.4079 82.2671 -75 - vertex -12.9612 63.5763 -75 - vertex -20.4052 79.7278 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 9.37727 64.3489 -75 - vertex -6.73263 49.1968 -75 - vertex -12.9612 63.5763 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 14.8182 47.9341 -75 - vertex 0 37.5 -75 - vertex -6.73263 49.1968 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 18.75 32.476 -75 - vertex 0 37.5 -75 - vertex 14.8182 47.9341 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 17.3648 98.4808 -75 - vertex 34.202 93.9693 -75 - vertex 26.8879 77.9891 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 17.3648 98.4808 -75 - vertex 26.8879 77.9891 -75 - vertex 1.4079 82.2671 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 17.3648 98.4808 -75 - vertex 1.4079 82.2671 -75 - vertex 0 100 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 26.8879 77.9891 -75 - vertex 9.37727 64.3489 -75 - vertex 1.4079 82.2671 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 31.0341 58.4031 -75 - vertex 14.8182 47.9341 -75 - vertex 9.37727 64.3489 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 33.5608 39.2491 -75 - vertex 18.75 32.476 -75 - vertex 14.8182 47.9341 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 32.476 18.75 -75 - vertex 18.75 32.476 -75 - vertex 33.5608 39.2491 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -9.6225 -75 - vertex 37.5 -0 -75 - vertex 50 9.6225 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 86.6025 -75 - vertex 50 67.3575 -75 - vertex 26.8879 77.9891 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 86.6025 -75 - vertex 26.8879 77.9891 -75 - vertex 34.202 93.9693 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 67.3575 -75 - vertex 31.0341 58.4031 -75 - vertex 26.8879 77.9891 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 48.1125 -75 - vertex 33.5608 39.2491 -75 - vertex 31.0341 58.4031 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 28.8675 -75 - vertex 32.476 18.75 -75 - vertex 33.5608 39.2491 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 26.8879 77.9891 -75 - vertex 31.0341 58.4031 -75 - vertex 9.37727 64.3489 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 1.4079 82.2671 -75 - vertex 9.37727 64.3489 -75 - vertex -12.9612 63.5763 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -20.4052 79.7278 -75 - vertex -12.9612 63.5763 -75 - vertex -32.8384 61.9158 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 31.9366 -62.7449 -75 - vertex 16.7654 -81.8564 -75 - vertex 12.119 -63.9104 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 12.119 -63.9104 -75 - vertex -4.71315 -80.8405 -75 - vertex -10.2498 -63.5607 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 31.0341 58.4031 -75 - vertex 33.5608 39.2491 -75 - vertex 14.8182 47.9341 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 9.37727 64.3489 -75 - vertex 14.8182 47.9341 -75 - vertex -6.73263 49.1968 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -12.9612 63.5763 -75 - vertex -6.73263 49.1968 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 12.119 -63.9104 -75 - vertex 8.34963 -49.0482 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -20.3431 -50.1686 -75 - vertex -32.2308 -45.3474 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.3359 -60.5982 -75 - vertex -32.2308 -45.3474 -75 - vertex -20.3431 -50.1686 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 28.8675 -75 - vertex 50 9.6225 -75 - vertex 32.476 18.75 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 48.1125 -75 - vertex 50 28.8675 -75 - vertex 33.5608 39.2491 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 67.3575 -75 - vertex 50 48.1125 -75 - vertex 31.0341 58.4031 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -36.7316 -34.2036 -75 - vertex -50 -48.1125 -75 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -32.2308 -45.3474 -75 - vertex -50 -48.1125 -75 - vertex -36.7316 -34.2036 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -67.3575 -75 - vertex -50 -48.1125 -75 - vertex -32.3359 -60.5982 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -9.6225 -75 - vertex -50 9.6225 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 9.6225 -75 - vertex -32.476 18.75 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 28.8675 -75 - vertex -32.476 18.75 -75 - vertex -50 9.6225 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -37.0799 77.7597 -75 - vertex -50 67.3575 -75 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.8384 61.9158 -75 - vertex -50 67.3575 -75 - vertex -37.0799 77.7597 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 48.1125 -75 - vertex -50 67.3575 -75 - vertex -32.8384 61.9158 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 48.1125 -75 - vertex -32.8384 61.9158 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 48.1125 -75 - vertex -29.95 43.1732 -75 - vertex -50 28.8675 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -29.95 43.1732 -75 - vertex -32.476 18.75 -75 - vertex -50 28.8675 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -18.75 32.476 -75 - vertex -32.476 18.75 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 12.119 -63.9104 -75 - vertex 30.1879 -43.3257 -75 - vertex 31.9366 -62.7449 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 8.34963 -49.0482 -75 - vertex 18.75 -32.476 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -0 -37.5 -75 - vertex 18.75 -32.476 -75 - vertex 8.34963 -49.0482 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -0 -37.5 -75 - vertex 8.34963 -49.0482 -75 - vertex -8.17844 -47.0148 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -0 -37.5 -75 - vertex -8.17844 -47.0148 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -86.6025 -75 - vertex -50 -67.3575 -75 - vertex -27.8383 -78.2461 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -86.6025 -75 - vertex -27.8383 -78.2461 -75 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -67.3575 -75 - vertex -32.3359 -60.5982 -75 - vertex -27.8383 -78.2461 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -48.1125 -75 - vertex -32.2308 -45.3474 -75 - vertex -32.3359 -60.5982 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -36.7316 -34.2036 -75 - vertex -18.75 -32.476 -75 - vertex -32.2308 -45.3474 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -18.75 -32.476 -75 - vertex -36.7316 -34.2036 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -36.7316 -34.2036 -75 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -50 -28.8675 -75 - vertex -50 -9.6225 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -50 -9.6225 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -12.3722 39.0134 - vertex 50 -5.58971 57.5541 - vertex 50 -23.0532 44.8966 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -5.58971 57.5541 - vertex 50 -22.2245 61.2431 - vertex 50 -23.0532 44.8966 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 25 - vertex 50 48.1125 25 - vertex 50 39.3934 39.3934 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 22.5939 54.2272 - vertex 50 4.24366 42.6158 - vertex 50 17.7589 37.3466 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 4.24366 42.6158 - vertex 50 9.6225 25 - vertex 50 17.7589 37.3466 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -12.3722 39.0134 - vertex 50 -9.6225 25 - vertex 50 4.24366 42.6158 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 11.8037 60.8572 - vertex 50 -5.58971 57.5541 - vertex 50 4.24366 42.6158 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -5.58971 57.5541 - vertex 50 -12.3722 39.0134 - vertex 50 4.24366 42.6158 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -23.0532 44.8966 - vertex 50 -28.8675 25 - vertex 50 -12.3722 39.0134 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -67.3575 75 - vertex 50 -50 65 - vertex 50 -48.1125 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -60.6066 60.6066 - vertex 50 -50 65 - vertex 50 -67.3575 75 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 75 - vertex 50 -74.3334 62.5671 - vertex 50 -67.3575 75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 9.6225 -75 - vertex 37.5 -0 -75 - vertex 32.476 18.75 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 -9.6225 -75 - vertex 32.476 -18.75 -75 - vertex 37.5 -0 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -28.8675 -75 - vertex 32.476 -18.75 -75 - vertex 50 -9.6225 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 35.8735 -78.2658 -75 - vertex 50 -67.3575 -75 - vertex 50 -86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 31.9366 -62.7449 -75 - vertex 50 -67.3575 -75 - vertex 35.8735 -78.2658 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 -48.1125 -75 - vertex 50 -67.3575 -75 - vertex 31.9366 -62.7449 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 -48.1125 -75 - vertex 31.9366 -62.7449 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -48.1125 -75 - vertex 30.1879 -43.3257 -75 - vertex 50 -28.8675 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 30.1879 -43.3257 -75 - vertex 32.476 -18.75 -75 - vertex 50 -28.8675 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 18.75 -32.476 -75 - vertex 32.476 -18.75 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 0 -100 -75 - vertex -4.71315 -80.8405 -75 - vertex 16.7654 -81.8564 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -4.71315 -80.8405 -75 - vertex 12.119 -63.9104 -75 - vertex 16.7654 -81.8564 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -10.2498 -63.5607 -75 - vertex 8.34963 -49.0482 -75 - vertex 12.119 -63.9104 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -8.17844 -47.0148 -75 - vertex 8.34963 -49.0482 -75 - vertex -10.2498 -63.5607 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -8.17844 -47.0148 -75 - vertex -10.2498 -63.5607 -75 - vertex -20.3431 -50.1686 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -8.17844 -47.0148 -75 - vertex -20.3431 -50.1686 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -10.2498 -63.5607 -75 - vertex -32.3359 -60.5982 -75 - vertex -20.3431 -50.1686 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -32.3359 -60.5982 -75 - vertex -10.2498 -63.5607 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -10.2498 -63.5607 -75 - vertex -4.71315 -80.8405 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -4.71315 -80.8405 -75 - vertex -17.3648 -98.4808 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -17.3648 -98.4808 -75 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -4.71315 -80.8405 -75 - vertex 0 -100 -75 - vertex -17.3648 -98.4808 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 16.7654 -81.8564 -75 - vertex 17.3648 -98.4808 -75 - vertex 0 -100 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 34.202 -93.9693 -75 - vertex 17.3648 -98.4808 -75 - vertex 16.7654 -81.8564 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 34.202 -93.9693 -75 - vertex 16.7654 -81.8564 -75 - vertex 35.8735 -78.2658 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 34.202 -93.9693 -75 - vertex 35.8735 -78.2658 -75 - vertex 50 -86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 16.7654 -81.8564 -75 - vertex 31.9366 -62.7449 -75 - vertex 35.8735 -78.2658 -75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -28.8675 -25 - vertex -50 -39.6067 -42.3045 - vertex -50 -48.1125 -25 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -18.9388 -42.4878 - vertex -50 -29.0415 -59.9655 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -6.16398 -58.6027 - vertex -50 -9.6225 -75 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -9.6225 -25 - vertex -50 1.31775 -41.8772 - vertex -50 -18.9388 -42.4878 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -9.6225 -25 - vertex -50 -18.9388 -42.4878 - vertex -50 -28.8675 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 1.31775 -41.8772 - vertex -50 -6.16398 -58.6027 - vertex -50 -18.9388 -42.4878 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 14.0935 -58.3566 - vertex -50 9.6225 -75 - vertex -50 -6.16398 -58.6027 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 9.6225 -25 - vertex -50 20.6227 -41.5526 - vertex -50 1.31775 -41.8772 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 9.6225 -25 - vertex -50 1.31775 -41.8772 - vertex -50 -9.6225 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 20.6227 -41.5526 - vertex -50 14.0935 -58.3566 - vertex -50 1.31775 -41.8772 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 32.7919 -58.1342 - vertex -50 28.8675 -75 - vertex -50 14.0935 -58.3566 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 32.7919 -58.1342 - vertex -50 38.9141 -40.8553 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 38.9141 -40.8553 - vertex -50 56.9708 -41.6522 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 56.9708 -41.6522 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 38.9141 -40.8553 - vertex -50 48.1125 -25 - vertex -50 56.9708 -41.6522 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 -25 - vertex -50 48.1125 -25 - vertex -50 38.9141 -40.8553 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 28.8675 -25 - vertex -50 38.9141 -40.8553 - vertex -50 20.6227 -41.5526 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 28.8675 -25 - vertex -50 20.6227 -41.5526 - vertex -50 9.6225 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 38.9141 -40.8553 - vertex -50 32.7919 -58.1342 - vertex -50 20.6227 -41.5526 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 48.1125 -75 - vertex -50 32.7919 -58.1342 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 -75 - vertex -50 48.1125 -75 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 -75 - vertex -50 66.6042 -60.9663 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 66.6042 -60.9663 - vertex -50 86.6025 -58.3333 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 72.4408 -45.1781 - vertex -50 86.6025 -58.3333 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 86.6025 -41.6667 - vertex -50 86.6025 -58.3333 - vertex -50 72.4408 -45.1781 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -70.3049 -55.1289 - vertex -50 -61.0775 -40.8996 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 77.4232 -43.4472 -25 - vertex 86.6025 -50 -25 - vertex 76.6044 -64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 86.6025 -50 -25 - vertex 77.4232 -43.4472 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 77.4232 -43.4472 -25 - vertex 76.5403 -27.9427 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 76.5403 -27.9427 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 86.3348 -19.8135 -25 - vertex 98.4808 -17.3648 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 76.5403 -27.9427 -25 - vertex 75 -10 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 76.6044 -64.2788 -25 - vertex 61.2753 -61.6257 -25 - vertex 65.9129 -50.6425 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 61.2753 -61.6257 -25 - vertex 50 -48.1125 -25 - vertex 65.9129 -50.6425 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -67.3575 -25 - vertex 50 -48.1125 -25 - vertex 61.2753 -61.6257 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -67.3575 -25 - vertex 61.2753 -61.6257 -25 - vertex 64.2788 -76.6044 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -67.3575 -25 - vertex 64.2788 -76.6044 -25 - vertex 50 -86.6025 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 61.2753 -61.6257 -25 - vertex 76.6044 -64.2788 -25 - vertex 64.2788 -76.6044 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 65.9129 -50.6425 -25 - vertex 77.4232 -43.4472 -25 - vertex 76.6044 -64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 63.2012 -36.5076 -25 - vertex 76.5403 -27.9427 -25 - vertex 77.4232 -43.4472 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 62.9265 -20.6629 -25 - vertex 75 -10 -25 - vertex 76.5403 -27.9427 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 75 -10 -25 - vertex 62.9265 -20.6629 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 62.9265 -20.6629 -25 - vertex 50 -9.6225 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 50 -9.6225 -25 - vertex 65 0 -25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -18.9388 -42.4878 - vertex -50 -6.16398 -58.6027 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 1.31775 -41.8772 - vertex -50 14.0935 -58.3566 - vertex -50 -6.16398 -58.6027 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 20.6227 -41.5526 - vertex -50 32.7919 -58.1342 - vertex -50 14.0935 -58.3566 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 56.9708 -41.6522 - vertex -50 67.3575 -25 - vertex -50 72.4408 -45.1781 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.1125 -25 - vertex -50 67.3575 -25 - vertex -50 56.9708 -41.6522 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -70.3049 -55.1289 - vertex -50 -86.6025 -58.3333 - vertex -50 -86.6025 -41.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -67.3575 -75 - vertex -50 -86.6025 -58.3333 - vertex -50 -70.3049 -55.1289 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 -75 - vertex -50 -86.6025 -58.3333 - vertex -50 -67.3575 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -28.8675 -25 - vertex -50 -18.9388 -42.4878 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -87.1351 -19.2209 -25 - vertex -93.9693 -34.202 -25 - vertex -98.4808 -17.3648 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -79.8138 -27.1233 -25 - vertex -93.9693 -34.202 -25 - vertex -87.1351 -19.2209 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -63.9539 -44.7004 -25 - vertex -76.6044 -64.2788 -25 - vertex -77.4794 -42.1095 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -76.6044 -64.2788 -25 - vertex -61.418 -60.2423 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.1672 -27.2873 -25 - vertex -50 -28.8675 -25 - vertex -63.9539 -44.7004 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -61.418 -60.2423 -25 - vertex -63.9539 -44.7004 -25 - vertex -50 -48.1125 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -61.418 -60.2423 -25 - vertex -50 -48.1125 -25 - vertex -50 -67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -63.9539 -44.7004 -25 - vertex -50 -28.8675 -25 - vertex -50 -48.1125 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.1672 -27.2873 -25 - vertex -58.8409 -18.1346 -25 - vertex -50 -28.8675 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.9289 -7.07107 -25 - vertex -50 -9.6225 -25 - vertex -58.8409 -18.1346 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -50 28.8675 -25 - vertex -50 9.6225 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -50 48.1125 -25 - vertex -50 28.8675 -25 - vertex -63.77 35.8952 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -61.3177 61.5263 -25 - vertex -50 48.1125 -25 - vertex -66.0782 50.3346 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -50 67.3575 -25 - vertex -50 48.1125 -25 - vertex -61.3177 61.5263 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -98.4808 17.3648 -25 - vertex -89.7207 15.4527 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -89.7207 15.4527 -25 - vertex -85 0 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -82.0711 7.07107 -25 - vertex -85 0 -25 - vertex -89.7207 15.4527 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -77.6899 42.7319 -25 - vertex -86.6025 50 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -86.6025 50 -25 - vertex -77.6899 42.7319 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -77.6899 42.7319 -25 - vertex -78.1277 25.7829 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -78.1277 25.7829 -25 - vertex -89.7207 15.4527 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -89.7207 15.4527 -25 - vertex -98.4808 17.3648 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -78.1277 25.7829 -25 - vertex -82.0711 7.07107 -25 - vertex -89.7207 15.4527 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -75 10 -25 - vertex -82.0711 7.07107 -25 - vertex -78.1277 25.7829 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -66.0782 50.3346 -25 - vertex -63.77 35.8952 -25 - vertex -77.6899 42.7319 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -66.0782 50.3346 -25 - vertex -77.6899 42.7319 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -61.0775 -40.8996 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -39.6067 -42.3045 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -61.0775 -40.8996 - vertex -50 -48.1125 -25 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -67.3575 -25 - vertex -50 -48.1125 -25 - vertex -50 -61.0775 -40.8996 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -67.3575 -25 - vertex -50 -61.0775 -40.8996 - vertex -50 -86.6025 -41.6667 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -67.3575 -25 - vertex -50 -86.6025 -41.6667 - vertex -50 -86.6025 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -61.0775 -40.8996 - vertex -50 -70.3049 -55.1289 - vertex -50 -86.6025 -41.6667 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -67.3575 -75 - vertex -50 -70.3049 -55.1289 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 -75 - vertex -50 -67.3575 -75 - vertex -50 -51.7631 -58.1259 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 -75 - vertex -50 -51.7631 -58.1259 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 -75 - vertex -50 -29.0415 -59.9655 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -29.0415 -59.9655 - vertex -50 -9.6225 -75 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -6.16398 -58.6027 - vertex -50 9.6225 -75 - vertex -50 -9.6225 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 14.0935 -58.3566 - vertex -50 28.8675 -75 - vertex -50 9.6225 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 32.7919 -58.1342 - vertex -50 48.1125 -75 - vertex -50 28.8675 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 66.6042 -60.9663 - vertex -50 48.1125 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 56.9708 -41.6522 - vertex -50 72.4408 -45.1781 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 -25 - vertex -50 86.6025 -41.6667 - vertex -50 72.4408 -45.1781 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex -50 86.6025 -25 - vertex -50 86.6025 -41.6667 - vertex -50 67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -78.1277 25.7829 -25 - vertex -63.77 35.8952 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -77.4794 -42.1095 -25 - vertex -79.8138 -27.1233 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -28.8675 -25 - vertex -58.8409 -18.1346 -25 - vertex -50 -9.6225 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -75 -10 -25 - vertex -67.9289 -7.07107 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.9289 -7.07107 -25 - vertex -58.8409 -18.1346 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -87.1351 -19.2209 -25 - vertex -98.4808 -17.3648 -25 - vertex -91.5168 -8.74011 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -85 0 -25 - vertex -91.5168 -8.74011 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -91.5168 -8.74011 -25 - vertex -98.4808 -17.3648 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 14.8663 -58.4416 - vertex 50 28.8675 -75 - vertex 50 33.981 -58.2872 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 -58.3333 - vertex 50 70.779 -58.5287 - vertex 50 86.6025 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 70.779 -58.5287 - vertex 50 67.3575 -75 - vertex 50 86.6025 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 52.8706 -58.3816 - vertex 50 48.1125 -75 - vertex 50 67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 33.981 -58.2872 - vertex 50 28.8675 -75 - vertex 50 48.1125 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 14.8663 -58.4416 - vertex 50 9.6225 -75 - vertex 50 28.8675 -75 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -1.76026 -61.2305 - vertex 50 9.6225 -75 - vertex 50 14.8663 -58.4416 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -9.6225 -75 - vertex 50 9.6225 -75 - vertex 50 -1.76026 -61.2305 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 -58.3333 - vertex 50 -86.6025 -75 - vertex 50 -67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 -75 - vertex 50 -61.1182 -59.0886 - vertex 50 -67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -61.1182 -59.0886 - vertex 50 -86.6025 -58.3333 - vertex 50 -67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -70.2628 -44.8561 - vertex 50 -86.6025 -58.3333 - vertex 50 -61.1182 -59.0886 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 -41.6667 - vertex 50 -86.6025 -58.3333 - vertex 50 -70.2628 -44.8561 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -51.5177 -41.872 - vertex 50 -67.3575 -25 - vertex 50 -70.2628 -44.8561 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -67.3575 -25 - vertex 50 -51.5177 -41.872 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -51.5177 -41.872 - vertex 50 -28.0125 -40.2176 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -28.0125 -40.2176 - vertex 50 -28.8675 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -28.0125 -40.2176 - vertex 50 -9.6225 -25 - vertex 50 -28.8675 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -2.82931 -43.2484 - vertex 50 9.6225 -25 - vertex 50 -9.6225 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 19.8883 -41.7934 - vertex 50 28.8675 -25 - vertex 50 9.6225 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 39.9586 -41.6283 - vertex 50 48.1125 -25 - vertex 50 28.8675 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 58.5014 -41.5594 - vertex 50 67.3575 -25 - vertex 50 48.1125 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 74.9599 -41.2947 - vertex 50 86.6025 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 86.6025 -41.6667 - vertex 50 86.6025 -25 - vertex 50 74.9599 -41.2947 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 -41.6667 - vertex 50 74.9599 -41.2947 - vertex 50 86.6025 -58.3333 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.9599 -41.2947 - vertex 50 70.779 -58.5287 - vertex 50 86.6025 -58.3333 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 61.3178 61.5265 25 - vertex 50 48.1125 25 - vertex 66.0812 50.3368 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 67.3575 25 - vertex 50 48.1125 25 - vertex 61.3178 61.5265 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 67.3575 25 - vertex 61.3178 61.5265 25 - vertex 64.2788 76.6044 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 67.3575 25 - vertex 64.2788 76.6044 25 - vertex 50 86.6025 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 61.3178 61.5265 25 - vertex 76.6044 64.2788 25 - vertex 64.2788 76.6044 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 66.0812 50.3368 25 - vertex 77.6996 42.7398 25 - vertex 76.6044 64.2788 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 63.7764 35.8998 25 - vertex 78.1402 25.7865 25 - vertex 77.6996 42.7398 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 63.1835 20.4106 25 - vertex 75 10 25 - vertex 78.1402 25.7865 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 67.9289 7.07107 25 - vertex 75 10 25 - vertex 63.1835 20.4106 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 67.9289 7.07107 25 - vertex 63.1835 20.4106 25 - vertex 50 9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 67.9289 7.07107 25 - vertex 50 9.6225 25 - vertex 65 -0 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -61.1182 -59.0886 - vertex 50 -39.6697 -57.6908 - vertex 50 -51.5177 -41.872 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -39.6697 -57.6908 - vertex 50 -28.0125 -40.2176 - vertex 50 -51.5177 -41.872 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -1.76026 -61.2305 - vertex 50 -2.82931 -43.2484 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -2.82931 -43.2484 - vertex 50 -28.0125 -40.2176 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -28.0125 -40.2176 - vertex 50 -39.6697 -57.6908 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -2.82931 -43.2484 - vertex 50 -9.6225 -25 - vertex 50 -28.0125 -40.2176 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 14.8663 -58.4416 - vertex 50 19.8883 -41.7934 - vertex 50 -2.82931 -43.2484 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 19.8883 -41.7934 - vertex 50 9.6225 -25 - vertex 50 -2.82931 -43.2484 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 33.981 -58.2872 - vertex 50 39.9586 -41.6283 - vertex 50 19.8883 -41.7934 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.9586 -41.6283 - vertex 50 28.8675 -25 - vertex 50 19.8883 -41.7934 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 52.8706 -58.3816 - vertex 50 58.5014 -41.5594 - vertex 50 39.9586 -41.6283 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 58.5014 -41.5594 - vertex 50 48.1125 -25 - vertex 50 39.9586 -41.6283 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 70.779 -58.5287 - vertex 50 74.9599 -41.2947 - vertex 50 58.5014 -41.5594 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.9599 -41.2947 - vertex 50 67.3575 -25 - vertex 50 58.5014 -41.5594 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 52.8706 -58.3816 - vertex 50 67.3575 -75 - vertex 50 70.779 -58.5287 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 33.981 -58.2872 - vertex 50 48.1125 -75 - vertex 50 52.8706 -58.3816 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 100 0 -25 - vertex 98.4808 -17.3648 -25 - vertex 91.3679 -8.97975 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -9.6225 -25 - vertex 50 9.6225 -25 - vertex 65 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 9.6225 -25 - vertex 67.9289 7.07107 -25 - vertex 65 0 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 58.9285 18.1069 -25 - vertex 67.9289 7.07107 -25 - vertex 50 9.6225 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 61.4484 60.172 -25 - vertex 50 48.1125 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 64.1232 44.519 -25 - vertex 50 48.1125 -25 - vertex 61.4484 60.172 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 50 48.1125 -25 - vertex 64.1232 44.519 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 64.1232 44.519 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 67.5854 27.0152 -25 - vertex 58.9285 18.1069 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 58.9285 18.1069 -25 - vertex 50 9.6225 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 67.5854 27.0152 -25 - vertex 67.9289 7.07107 -25 - vertex 58.9285 18.1069 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 75 10 -25 - vertex 67.9289 7.07107 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 86.6025 -25 - vertex 64.2788 76.6044 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 64.2788 76.6044 -25 - vertex 61.4484 60.172 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 76.6044 64.2788 -25 - vertex 64.1232 44.519 -25 - vertex 61.4484 60.172 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 77.7882 41.2953 -25 - vertex 67.5854 27.0152 -25 - vertex 64.1232 44.519 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 81.2015 24.5598 -25 - vertex 75 10 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 82.0711 7.07107 -25 - vertex 75 10 -25 - vertex 81.2015 24.5598 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 86.6025 50 -25 - vertex 93.9693 34.202 -25 - vertex 77.7882 41.2953 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 86.6025 50 -25 - vertex 77.7882 41.2953 -25 - vertex 76.6044 64.2788 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 93.9693 34.202 -25 - vertex 81.2015 24.5598 -25 - vertex 77.7882 41.2953 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 90.4705 14.6652 -25 - vertex 82.0711 7.07107 -25 - vertex 81.2015 24.5598 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 85 -0 -25 - vertex 82.0711 7.07107 -25 - vertex 90.4705 14.6652 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 85 -0 -25 - vertex 90.4705 14.6652 -25 - vertex 100 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 85 -0 -25 - vertex 100 0 -25 - vertex 91.3679 -8.97975 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 85 -0 -25 - vertex 91.3679 -8.97975 -25 - vertex 82.0711 -7.07107 -25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 58.5014 -41.5594 - vertex 50 52.8706 -58.3816 - vertex 50 70.779 -58.5287 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.9586 -41.6283 - vertex 50 33.981 -58.2872 - vertex 50 52.8706 -58.3816 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 19.8883 -41.7934 - vertex 50 14.8663 -58.4416 - vertex 50 33.981 -58.2872 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -2.82931 -43.2484 - vertex 50 -1.76026 -61.2305 - vertex 50 14.8663 -58.4416 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -9.6225 -75 - vertex 50 -1.76026 -61.2305 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -28.8675 -75 - vertex 50 -9.6225 -75 - vertex 50 -19.3334 -57.7609 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -28.8675 -75 - vertex 50 -19.3334 -57.7609 - vertex 50 -39.6697 -57.6908 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -28.8675 -75 - vertex 50 -39.6697 -57.6908 - vertex 50 -48.1125 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -39.6697 -57.6908 - vertex 50 -61.1182 -59.0886 - vertex 50 -48.1125 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -51.5177 -41.872 - vertex 50 -70.2628 -44.8561 - vertex 50 -61.1182 -59.0886 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -67.3575 -25 - vertex 50 -86.6025 -41.6667 - vertex 50 -70.2628 -44.8561 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 -25 - vertex 50 -86.6025 -41.6667 - vertex 50 -67.3575 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 76.5403 -27.9427 -25 - vertex 63.2012 -36.5076 -25 - vertex 62.9265 -20.6629 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 77.7882 41.2953 -25 - vertex 81.2015 24.5598 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 100 0 -25 - vertex 90.4705 14.6652 -25 - vertex 98.4808 17.3648 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 90.4705 14.6652 -25 - vertex 93.9693 34.202 -25 - vertex 98.4808 17.3648 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 81.2015 24.5598 -25 - vertex 93.9693 34.202 -25 - vertex 90.4705 14.6652 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 64.1232 44.519 -25 - vertex 76.6044 64.2788 -25 - vertex 77.7882 41.2953 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 64.2788 76.6044 -25 - vertex 76.6044 64.2788 -25 - vertex 61.4484 60.172 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -28.8675 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -28.8675 -25 - vertex 62.9265 -20.6629 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -9.6225 -25 - vertex 62.9265 -20.6629 -25 - vertex 50 -28.8675 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 77.4232 -43.4472 -25 - vertex 65.9129 -50.6425 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 65.9129 -50.6425 -25 - vertex 50 -48.1125 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 82.0711 -7.07107 -25 - vertex 91.3679 -8.97975 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 82.0711 -7.07107 -25 - vertex 86.3348 -19.8135 -25 - vertex 75 -10 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 91.3679 -8.97975 -25 - vertex 98.4808 -17.3648 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -76.0618 33.425 - vertex 20 -60.6066 39.3934 - vertex 20 -59.5852 25.5168 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -76.0618 33.425 - vertex 20 -59.5852 25.5168 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -59.5852 25.5168 - vertex 20 -49.8517 11.8026 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -43.758 25.2531 - vertex 20 -31.7214 16.6667 - vertex 20 -49.8517 11.8026 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -31.7214 16.6667 - vertex 20 -43.758 25.2531 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -43.758 25.2531 - vertex 20 -39.3934 39.3934 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -39.3934 39.3934 - vertex 20 -31.7214 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -43.758 25.2531 - vertex 20 -50 35 - vertex 20 -39.3934 39.3934 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -59.5852 25.5168 - vertex 20 -60.6066 39.3934 - vertex 20 -50 35 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -76.0618 33.425 - vertex 20 -65 50 - vertex 20 -60.6066 39.3934 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4898 50 - vertex 20 -65 50 - vertex 20 -76.0618 33.425 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -97.9796 0 - vertex 20 -97.9796 16.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -97.9796 16.6667 - vertex 20 -84.3761 19.6041 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -84.3761 19.6041 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -69.4506 14.8283 - vertex 20 -64.8505 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -84.3761 19.6041 - vertex 20 -76.0618 33.425 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -97.9796 33.3333 - vertex 20 -81.4898 50 - vertex 20 -76.0618 33.425 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -97.9796 50 - vertex 20 -81.4898 50 - vertex 20 -97.9796 33.3333 - endloop - endfacet - facet normal -0.0651265 -0.681101 0.729288 - outer loop - vertex 36.7146 -36.3923 43.6888 - vertex 20 -39.3934 39.3934 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal -0.103417 0.715365 -0.691055 - outer loop - vertex 38.7411 -55.9092 63.787 - vertex 38.6185 -63.971 55.46 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal 0.101888 0.919072 -0.380692 - outer loop - vertex 38.6185 -63.971 55.46 - vertex 27.5 -65 50 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal -0.117753 0.991633 0.0529005 - outer loop - vertex 36.6956 -63.5667 43.6012 - vertex 27.5 -65 50 - vertex 38.6185 -63.971 55.46 - endloop - endfacet - facet normal -0.10265 0.00891066 -0.994678 - outer loop - vertex 27.5 -50 65 - vertex 38.7419 -44.3385 63.8906 - vertex 38.7411 -55.9092 63.787 - endloop - endfacet - facet normal 0.100956 0.380728 -0.919159 - outer loop - vertex 27.5 -50 65 - vertex 38.7411 -55.9092 63.787 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal 0.102496 0.00889689 -0.994694 - outer loop - vertex 38.7419 -44.3385 63.8906 - vertex 50 -50 65 - vertex 38.7411 -55.9092 63.787 - endloop - endfacet - facet normal -0.100882 -0.380731 -0.919166 - outer loop - vertex 50 -39.3934 60.6066 - vertex 50 -50 65 - vertex 38.7419 -44.3385 63.8906 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 97.9796 16.6667 - vertex 20 97.9796 0 - vertex 20 81.4151 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 64.8505 0 - vertex 20 76.0222 15.0039 - vertex 20 81.4151 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 76.0222 15.0039 - vertex 20 97.9796 16.6667 - vertex 20 81.4151 0 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 79.2233 32.1829 - vertex 20 97.9796 16.6667 - vertex 20 76.0222 15.0039 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 97.9796 33.3333 - vertex 20 97.9796 16.6667 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 65 50 - vertex 20 81.4898 50 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 81.4898 50 - vertex 20 97.9796 33.3333 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex 20 97.9796 50 - vertex 20 97.9796 33.3333 - vertex 20 81.4898 50 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex 20 35 50 - vertex 20 39.3934 39.3934 - vertex 20 31.7214 50 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 39.3934 39.3934 - vertex 20 31.7214 33.3333 - vertex 20 31.7214 50 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 45.5064 24.0211 - vertex 20 31.7214 16.6667 - vertex 20 31.7214 33.3333 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 42.9891 10.7098 - vertex 20 31.7214 0 - vertex 20 31.7214 16.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 48.286 0 - vertex 20 31.7214 0 - vertex 20 42.9891 10.7098 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 48.286 0 - vertex 20 42.9891 10.7098 - vertex 20 57.8078 12.7685 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 48.286 0 - vertex 20 57.8078 12.7685 - vertex 20 64.8505 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 57.8078 12.7685 - vertex 20 76.0222 15.0039 - vertex 20 64.8505 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 62.8929 25.7602 - vertex 20 79.2233 32.1829 - vertex 20 76.0222 15.0039 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 60.6066 39.3934 - vertex 20 65 50 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -84.3761 19.6041 - vertex 20 -97.9796 33.3333 - vertex 20 -76.0618 33.425 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -97.9796 16.6667 - vertex 20 -97.9796 33.3333 - vertex 20 -84.3761 19.6041 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -64.8505 0 - vertex 20 -69.4506 14.8283 - vertex 20 -49.8517 11.8026 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -64.8505 0 - vertex 20 -49.8517 11.8026 - vertex 20 -48.286 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -49.8517 11.8026 - vertex 20 -31.7214 0 - vertex 20 -48.286 0 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -31.7214 16.6667 - vertex 20 -31.7214 0 - vertex 20 -49.8517 11.8026 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -39.3934 39.3934 - vertex 20 -35 50 - vertex 20 -31.7214 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -49.8517 11.8026 - vertex 20 -59.5852 25.5168 - vertex 20 -43.758 25.2531 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -59.5852 25.5168 - vertex 20 -50 35 - vertex 20 -43.758 25.2531 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -97.9796 16.6667 - vertex -20 -75.6829 15.1229 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -62.1725 27.2886 - vertex -20 -57.0711 42.9289 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -50 40 - vertex -20 -57.0711 42.9289 - vertex -20 -62.1725 27.2886 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -50 40 - vertex -20 -62.1725 27.2886 - vertex -20 -45.6982 25.7885 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -50 40 - vertex -20 -45.6982 25.7885 - vertex -20 -42.9289 42.9289 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -45.6982 25.7885 - vertex -20 -31.7214 33.3333 - vertex -20 -42.9289 42.9289 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -75.6829 15.1229 - vertex -20 -57.6764 13.4257 - vertex -20 -62.1725 27.2886 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -57.6764 13.4257 - vertex -20 -45.6982 25.7885 - vertex -20 -62.1725 27.2886 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -43.0859 11.2998 - vertex -20 -31.7214 16.6667 - vertex -20 -45.6982 25.7885 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -97.9796 16.6667 - vertex -20 -97.9796 0 - vertex -20 -81.4151 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -64.8505 0 - vertex -20 -75.6829 15.1229 - vertex -20 -81.4151 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -75.6829 15.1229 - vertex -20 -97.9796 16.6667 - vertex -20 -81.4151 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -78.8495 31.6006 - vertex -20 -97.9796 33.3333 - vertex -20 -97.9796 16.6667 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -78.9898 50 - vertex -20 -97.9796 33.3333 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -97.9796 50 - vertex -20 -97.9796 33.3333 - vertex -20 -78.9898 50 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -40 50 - vertex -20 -42.9289 42.9289 - vertex -20 -31.7214 50 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -42.9289 42.9289 - vertex -20 -31.7214 33.3333 - vertex -20 -31.7214 50 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -45.6982 25.7885 - vertex -20 -31.7214 16.6667 - vertex -20 -31.7214 33.3333 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -43.0859 11.2998 - vertex -20 -31.7214 0 - vertex -20 -31.7214 16.6667 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -48.286 0 - vertex -20 -31.7214 0 - vertex -20 -43.0859 11.2998 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -48.286 0 - vertex -20 -43.0859 11.2998 - vertex -20 -57.6764 13.4257 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -48.286 0 - vertex -20 -57.6764 13.4257 - vertex -20 -64.8505 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -57.6764 13.4257 - vertex -20 -75.6829 15.1229 - vertex -20 -64.8505 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -62.1725 27.2886 - vertex -20 -78.8495 31.6006 - vertex -20 -75.6829 15.1229 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -57.0711 42.9289 - vertex -20 -78.9898 50 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -60 50 - vertex -20 -78.9898 50 - vertex -20 -57.0711 42.9289 - endloop - endfacet - facet normal -0.105554 -0.705408 -0.700898 - outer loop - vertex 27.5 -39.3934 60.6066 - vertex 38.627 -36.0851 55.6013 - vertex 38.7419 -44.3385 63.8906 - endloop - endfacet - facet normal 0.101026 -0.380725 -0.919153 - outer loop - vertex 27.5 -39.3934 60.6066 - vertex 38.7419 -44.3385 63.8906 - vertex 27.5 -50 65 - endloop - endfacet - facet normal 0.104349 -0.704043 -0.702449 - outer loop - vertex 38.627 -36.0851 55.6013 - vertex 50 -39.3934 60.6066 - vertex 38.7419 -44.3385 63.8906 - endloop - endfacet - facet normal -0.0998287 -0.919264 -0.380772 - outer loop - vertex 50 -35 50 - vertex 50 -39.3934 60.6066 - vertex 38.627 -36.0851 55.6013 - endloop - endfacet - facet normal -0.119236 -0.991858 0.0447246 - outer loop - vertex 27.5 -35 50 - vertex 36.7146 -36.3923 43.6888 - vertex 38.627 -36.0851 55.6013 - endloop - endfacet - facet normal 0.102014 -0.91906 -0.380687 - outer loop - vertex 27.5 -35 50 - vertex 38.627 -36.0851 55.6013 - vertex 27.5 -39.3934 60.6066 - endloop - endfacet - facet normal 0.0996841 -0.994972 0.00966098 - outer loop - vertex 36.7146 -36.3923 43.6888 - vertex 50 -35 50 - vertex 38.627 -36.0851 55.6013 - endloop - endfacet - facet normal -0.0846643 -0.920562 0.381309 - outer loop - vertex 50 -39.3934 39.3934 - vertex 50 -35 50 - vertex 36.7146 -36.3923 43.6888 - endloop - endfacet - facet normal 0 -0.92388 0.382683 - outer loop - vertex 20 -35 50 - vertex 20 -39.3934 39.3934 - vertex 27.5 -35 50 - endloop - endfacet - facet normal 0.0839941 -0.940216 0.330058 - outer loop - vertex 20 -39.3934 39.3934 - vertex 36.7146 -36.3923 43.6888 - vertex 27.5 -35 50 - endloop - endfacet - facet normal 0.0739662 -0.695508 0.714701 - outer loop - vertex 35.0929 -44.3639 36.0991 - vertex 50 -39.3934 39.3934 - vertex 36.7146 -36.3923 43.6888 - endloop - endfacet - facet normal -0.0763432 -0.381567 0.921183 - outer loop - vertex 50 -50 35 - vertex 50 -39.3934 39.3934 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal -0.0717881 -0.00226715 0.997417 - outer loop - vertex 20 -50 35 - vertex 35.0899 -55.5723 36.0734 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal 0.0754083 -0.381594 0.921249 - outer loop - vertex 20 -50 35 - vertex 35.0929 -44.3639 36.0991 - vertex 20 -39.3934 39.3934 - endloop - endfacet - facet normal 0.0726638 -0.00230644 0.997354 - outer loop - vertex 35.0899 -55.5723 36.0734 - vertex 50 -50 35 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal -0.0762829 0.381568 0.921188 - outer loop - vertex 50 -60.6066 39.3934 - vertex 50 -50 35 - vertex 35.0899 -55.5723 36.0734 - endloop - endfacet - facet normal -0.0646641 0.677189 0.732962 - outer loop - vertex 20 -60.6066 39.3934 - vertex 36.6956 -63.5667 43.6012 - vertex 35.0899 -55.5723 36.0734 - endloop - endfacet - facet normal 0.0753793 0.381595 0.921251 - outer loop - vertex 20 -60.6066 39.3934 - vertex 35.0899 -55.5723 36.0734 - vertex 20 -50 35 - endloop - endfacet - facet normal 0.0734483 0.691467 0.718664 - outer loop - vertex 36.6956 -63.5667 43.6012 - vertex 50 -60.6066 39.3934 - vertex 35.0899 -55.5723 36.0734 - endloop - endfacet - facet normal -0.0842222 0.920597 0.381324 - outer loop - vertex 50 -65 50 - vertex 50 -60.6066 39.3934 - vertex 36.6956 -63.5667 43.6012 - endloop - endfacet - facet normal -0 0.92388 0.382683 - outer loop - vertex 20 -65 50 - vertex 27.5 -65 50 - vertex 20 -60.6066 39.3934 - endloop - endfacet - facet normal 0.0834023 0.940134 0.330442 - outer loop - vertex 27.5 -65 50 - vertex 36.6956 -63.5667 43.6012 - vertex 20 -60.6066 39.3934 - endloop - endfacet - facet normal 0.0985613 0.994969 0.0179403 - outer loop - vertex 38.6185 -63.971 55.46 - vertex 50 -65 50 - vertex 36.6956 -63.5667 43.6012 - endloop - endfacet - facet normal -0.0995564 0.91929 -0.380782 - outer loop - vertex 50 -60.6066 60.6066 - vertex 50 -65 50 - vertex 38.6185 -63.971 55.46 - endloop - endfacet - facet normal 0.102194 0.713943 -0.692706 - outer loop - vertex 50 -60.6066 60.6066 - vertex 38.6185 -63.971 55.46 - vertex 38.7411 -55.9092 63.787 - endloop - endfacet - facet normal -0.100798 0.380734 -0.919174 - outer loop - vertex 50 -60.6066 60.6066 - vertex 38.7411 -55.9092 63.787 - vertex 50 -50 65 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -43.0859 11.2998 - vertex -20 -45.6982 25.7885 - vertex -20 -57.6764 13.4257 - endloop - endfacet - facet normal -0.981072 0.190565 -0.0343998 - outer loop - vertex -98.4808 17.3648 25 - vertex -95.8872 28.3838 12.0748 - vertex -99.534 9.64234 12.2585 - endloop - endfacet - facet normal -0.995761 0.0871178 0.0295126 - outer loop - vertex -98.4808 17.3648 25 - vertex -99.534 9.64234 12.2585 - vertex -100 0 25 - endloop - endfacet - facet normal -0.980864 0.191221 0.0366081 - outer loop - vertex -95.8872 28.3838 12.0748 - vertex -98.004 19.8799 -0.222364 - vertex -99.534 9.64234 12.2585 - endloop - endfacet - facet normal -0.95354 0.298208 0.0428128 - outer loop - vertex -91.9278 39.3609 -0.583074 - vertex -95.6263 29.2507 -12.5369 - vertex -98.004 19.8799 -0.222364 - endloop - endfacet - facet normal -0.916652 0.398038 0.0362548 - outer loop - vertex -86.8061 49.6458 -13.4447 - vertex -93.9693 34.202 -25 - vertex -95.6263 29.2507 -12.5369 - endloop - endfacet - facet normal -0.212595 -0.97714 0 - outer loop - vertex -20 -97.9796 33.3333 - vertex -20 -97.9796 50 - vertex -22.5155 -97.4323 50 - endloop - endfacet - facet normal -0.237676 -0.971336 -0.00397595 - outer loop - vertex -20 -97.9796 33.3333 - vertex -22.5155 -97.4323 50 - vertex -25.016 -96.8204 50 - endloop - endfacet - facet normal -0.262583 -0.964836 -0.0119242 - outer loop - vertex -20 -97.9796 33.3333 - vertex -25.016 -96.8204 50 - vertex -27.5 -96.1444 50 - endloop - endfacet - facet normal -0.291664 -0.956169 -0.0259648 - outer loop - vertex -20 -97.9796 33.3333 - vertex -27.5 -96.1444 50 - vertex -37.053 -92.882 37.1703 - endloop - endfacet - facet normal -0.285573 -0.958349 0.00399969 - outer loop - vertex -20 -97.9796 33.3333 - vertex -37.053 -92.882 37.1703 - vertex -36.323 -93.17 20.3068 - endloop - endfacet - facet normal -0.28264 -0.959226 -0 - outer loop - vertex -20 -97.9796 33.3333 - vertex -36.323 -93.17 20.3068 - vertex -20 -97.9796 16.6667 - endloop - endfacet - facet normal -0.281846 -0.959452 0.00385819 - outer loop - vertex -36.323 -93.17 20.3068 - vertex -35.6133 -93.4435 4.12026 - vertex -20 -97.9796 16.6667 - endloop - endfacet - facet normal -0.440758 -0.897117 0.0302299 - outer loop - vertex -53.0109 -84.7929 7.17859 - vertex -47.479 -88.0099 -7.63341 - vertex -35.6133 -93.4435 4.12026 - endloop - endfacet - facet normal -0.546997 -0.837055 0.0115702 - outer loop - vertex -61.2739 -79.0286 -10.0423 - vertex -50 -86.6025 -25 - vertex -47.479 -88.0099 -7.63341 - endloop - endfacet - facet normal -0.573488 -0.819026 -0.0175256 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -50 -86.6025 -25 - vertex -61.2739 -79.0286 -10.0423 - endloop - endfacet - facet normal -0.695721 -0.71793 0.0234142 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -61.2739 -79.0286 -10.0423 - vertex -76.661 -64.2113 -12.9207 - endloop - endfacet - facet normal -0.707107 -0.707107 0.000638364 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -76.661 -64.2113 -12.9207 - vertex -76.6044 -64.2788 -25 - endloop - endfacet - facet normal -0.819152 -0.573576 -0.000631922 - outer loop - vertex -76.661 -64.2113 -12.9207 - vertex -86.6025 -50 -25 - vertex -76.6044 -64.2788 -25 - endloop - endfacet - facet normal -0.906047 -0.422496 -0.0240066 - outer loop - vertex -88.8886 -45.8128 -12.411 - vertex -93.9693 -34.202 -25 - vertex -86.6025 -50 -25 - endloop - endfacet - facet normal -0.96552 -0.25871 -0.0289694 - outer loop - vertex -96.131 -27.5468 -12.3849 - vertex -98.4808 -17.3648 -25 - vertex -93.9693 -34.202 -25 - endloop - endfacet - facet normal -0.995744 -0.0871163 -0.0300868 - outer loop - vertex -99.5881 -9.06697 -12.3787 - vertex -100 0 -25 - vertex -98.4808 -17.3648 -25 - endloop - endfacet - facet normal -0.995757 0.0871174 -0.0296553 - outer loop - vertex -99.5096 9.89181 -12.4091 - vertex -98.4808 17.3648 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal -0.965609 0.258734 -0.0255966 - outer loop - vertex -95.6263 29.2507 -12.5369 - vertex -93.9693 34.202 -25 - vertex -98.4808 17.3648 -25 - endloop - endfacet - facet normal -0.906304 0.422616 -0.00300955 - outer loop - vertex -86.8061 49.6458 -13.4447 - vertex -86.6025 50 -25 - vertex -93.9693 34.202 -25 - endloop - endfacet - facet normal -0.819148 0.573574 0.00315346 - outer loop - vertex -76.6044 64.2788 -25 - vertex -86.6025 50 -25 - vertex -86.8061 49.6458 -13.4447 - endloop - endfacet - facet normal -0.925456 0.377452 -0.0325804 - outer loop - vertex -93.9693 34.202 25 - vertex -88.3918 46.7642 12.1066 - vertex -95.8872 28.3838 12.0748 - endloop - endfacet - facet normal -0.414119 -0.910052 -0.0176057 - outer loop - vertex -50 -86.6025 -41.6667 - vertex -30.515 -95.2304 -54.0087 - vertex -34.0799 -94.0136 -33.0533 - endloop - endfacet - facet normal -0.422029 -0.906582 0 - outer loop - vertex -50 -86.6025 -41.6667 - vertex -34.0799 -94.0136 -33.0533 - vertex -50 -86.6025 -25 - endloop - endfacet - facet normal -0.726754 -0.686292 -0.0288338 - outer loop - vertex -76.6044 -64.2788 25 - vertex -79.3664 -60.8356 12.6628 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.707025 -0.707025 0.0152003 - outer loop - vertex -76.6044 -64.2788 25 - vertex -65.7797 -75.3195 14.9518 - vertex -64.2788 -76.6044 25 - endloop - endfacet - facet normal -0.731552 -0.68097 0.033322 - outer loop - vertex -79.3664 -60.8356 12.6628 - vertex -70.347 -71.0725 1.47391 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.77512 -0.630582 0.0394291 - outer loop - vertex -83.5527 -54.9449 -0.206588 - vertex -76.661 -64.2113 -12.9207 - vertex -70.347 -71.0725 1.47391 - endloop - endfacet - facet normal -0.831964 -0.55384 0.033132 - outer loop - vertex -88.8886 -45.8128 -12.411 - vertex -86.6025 -50 -25 - vertex -76.661 -64.2113 -12.9207 - endloop - endfacet - facet normal -0.847248 -0.530281 -0.0311962 - outer loop - vertex -86.6025 -50 25 - vertex -89.468 -44.6708 12.2345 - vertex -79.3664 -60.8356 12.6628 - endloop - endfacet - facet normal -0.81893 -0.573421 0.0233025 - outer loop - vertex -86.6025 -50 25 - vertex -79.3664 -60.8356 12.6628 - vertex -76.6044 -64.2788 25 - endloop - endfacet - facet normal -0.847952 -0.529002 0.0336917 - outer loop - vertex -89.468 -44.6708 12.2345 - vertex -83.5527 -54.9449 -0.206588 - vertex -79.3664 -60.8356 12.6628 - endloop - endfacet - facet normal -0.885864 -0.462081 0.0415523 - outer loop - vertex -92.8816 -37.0542 -0.137898 - vertex -88.8886 -45.8128 -12.411 - vertex -83.5527 -54.9449 -0.206588 - endloop - endfacet - facet normal -0.929004 -0.368397 0.0351541 - outer loop - vertex -96.131 -27.5468 -12.3849 - vertex -93.9693 -34.202 -25 - vertex -88.8886 -45.8128 -12.411 - endloop - endfacet - facet normal -0.932074 -0.360782 -0.0327896 - outer loop - vertex -93.9693 -34.202 25 - vertex -96.2203 -27.2335 12.3122 - vertex -89.468 -44.6708 12.2345 - endloop - endfacet - facet normal -0.905977 -0.422464 0.026997 - outer loop - vertex -93.9693 -34.202 25 - vertex -89.468 -44.6708 12.2345 - vertex -86.6025 -50 25 - endloop - endfacet - facet normal -0.931907 -0.361019 0.0348688 - outer loop - vertex -96.2203 -27.2335 12.3122 - vertex -92.8816 -37.0542 -0.137898 - vertex -89.468 -44.6708 12.2345 - endloop - endfacet - facet normal -0.959476 -0.279244 0.0377958 - outer loop - vertex -98.2656 -18.5439 -0.056713 - vertex -96.131 -27.5468 -12.3849 - vertex -92.8816 -37.0542 -0.137898 - endloop - endfacet - facet normal -0.982356 -0.183784 0.0346415 - outer loop - vertex -99.5881 -9.06697 -12.3787 - vertex -98.4808 -17.3648 -25 - vertex -96.131 -27.5468 -12.3849 - endloop - endfacet - facet normal -0.982807 -0.181491 -0.0339369 - outer loop - vertex -98.4808 -17.3648 25 - vertex -99.6002 -8.93358 12.3277 - vertex -96.2203 -27.2335 12.3122 - endloop - endfacet - facet normal -0.965514 -0.258709 0.0292048 - outer loop - vertex -98.4808 -17.3648 25 - vertex -96.2203 -27.2335 12.3122 - vertex -93.9693 -34.202 25 - endloop - endfacet - facet normal -0.982761 -0.181541 0.0349709 - outer loop - vertex -99.6002 -8.93358 12.3277 - vertex -98.2656 -18.5439 -0.056713 - vertex -96.2203 -27.2335 12.3122 - endloop - endfacet - facet normal -0.995169 -0.0910187 0.0368089 - outer loop - vertex -99.9992 0.407363 -0.064789 - vertex -99.5881 -9.06697 -12.3787 - vertex -98.2656 -18.5439 -0.056713 - endloop - endfacet - facet normal -0.999356 0.00419746 0.0356294 - outer loop - vertex -99.5096 9.89181 -12.4091 - vertex -100 0 -25 - vertex -99.5881 -9.06697 -12.3787 - endloop - endfacet - facet normal -0.999418 0.00343051 -0.0339527 - outer loop - vertex -100 0 25 - vertex -99.534 9.64234 12.2585 - vertex -99.6002 -8.93358 12.3277 - endloop - endfacet - facet normal -0.995746 -0.0871165 0.0299961 - outer loop - vertex -100 0 25 - vertex -99.6002 -8.93358 12.3277 - vertex -98.4808 -17.3648 25 - endloop - endfacet - facet normal -0.999382 0.00368732 0.0349574 - outer loop - vertex -99.534 9.64234 12.2585 - vertex -99.9992 0.407363 -0.064789 - vertex -99.6002 -8.93358 12.3277 - endloop - endfacet - facet normal -0.994 0.102161 0.0390677 - outer loop - vertex -98.004 19.8799 -0.222364 - vertex -99.5096 9.89181 -12.4091 - vertex -99.9992 0.407363 -0.064789 - endloop - endfacet - facet normal -0.97976 0.196774 0.0367353 - outer loop - vertex -95.6263 29.2507 -12.5369 - vertex -98.4808 17.3648 -25 - vertex -99.5096 9.89181 -12.4091 - endloop - endfacet - facet normal -0.114109 0.99323 -0.0217435 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -2.08806 99.9782 -37.1245 - vertex -20.4194 97.893 -36.1707 - endloop - endfacet - facet normal -0.24183 0.969965 0.0261905 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -20.4194 97.893 -36.1707 - vertex -34.6546 93.8033 -16.1476 - endloop - endfacet - facet normal -0.111912 0.993495 0.0210724 - outer loop - vertex -2.08806 99.9782 -37.1245 - vertex -8.98427 99.5956 -55.7105 - vertex -20.4194 97.893 -36.1707 - endloop - endfacet - facet normal 0.00355775 0.999738 0.0226165 - outer loop - vertex 9.68083 99.5303 -55.7605 - vertex 0 100 -75 - vertex -8.98427 99.5956 -55.7105 - endloop - endfacet - facet normal 0.0871391 0.996005 -0.0195307 - outer loop - vertex 17.3648 98.4808 -75 - vertex 0 100 -75 - vertex 9.68083 99.5303 -55.7605 - endloop - endfacet - facet normal 0.200053 0.979427 0.0264701 - outer loop - vertex 17.3648 98.4808 -75 - vertex 9.68083 99.5303 -55.7605 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.258799 0.96585 -0.0125197 - outer loop - vertex 17.3648 98.4808 -75 - vertex 30.5386 95.2229 -54.0167 - vertex 34.202 93.9693 -75 - endloop - endfacet - facet normal 0.204372 0.978508 -0.027455 - outer loop - vertex 9.68083 99.5303 -55.7605 - vertex 16.4596 98.6361 -37.1697 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.0721048 0.997182 -0.0207096 - outer loop - vertex -2.08806 99.9782 -37.1245 - vertex 4.20548 99.9115 -18.4222 - vertex 16.4596 98.6361 -37.1697 - endloop - endfacet - facet normal -0.0491445 0.998556 -0.0217011 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -6.70689 99.7748 0 - vertex 4.20548 99.9115 -18.4222 - endloop - endfacet - facet normal -0.100509 0.994935 -0.00133816 - outer loop - vertex -13.3836 99.1004 0 - vertex -6.70689 99.7748 0 - vertex -14.0535 99.0076 -18.6679 - endloop - endfacet - facet normal -0.167012 0.985954 0.00109319 - outer loop - vertex -13.3836 99.1004 0 - vertex -14.0535 99.0076 -18.6679 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.247789 0.968476 -0.0256 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -34.6546 93.8033 -16.1476 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.283645 0.958912 -0.00579578 - outer loop - vertex -20.4194 97.893 -36.1707 - vertex -36.1727 93.2284 -36.9681 - vertex -34.6546 93.8033 -16.1476 - endloop - endfacet - facet normal -0.323184 0.946292 -0.00917704 - outer loop - vertex -25.4516 96.7069 -55.8478 - vertex -38.8343 92.1515 -54.2819 - vertex -36.1727 93.2284 -36.9681 - endloop - endfacet - facet normal -0.439294 0.898134 -0.0194194 - outer loop - vertex -34.202 93.9693 -75 - vertex -50 86.6025 -58.3333 - vertex -38.8343 92.1515 -54.2819 - endloop - endfacet - facet normal -0.422618 0.906308 0 - outer loop - vertex -50 86.6025 -75 - vertex -50 86.6025 -58.3333 - vertex -34.202 93.9693 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 42.9891 10.7098 - vertex 20 45.5064 24.0211 - vertex 20 57.8078 12.7685 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 62.8929 25.7602 - vertex 20 60.6066 39.3934 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 50 35 - vertex 20 60.6066 39.3934 - vertex 20 62.8929 25.7602 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 50 35 - vertex 20 62.8929 25.7602 - vertex 20 45.5064 24.0211 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 50 35 - vertex 20 45.5064 24.0211 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 45.5064 24.0211 - vertex 20 31.7214 33.3333 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 76.0222 15.0039 - vertex 20 57.8078 12.7685 - vertex 20 62.8929 25.7602 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 57.8078 12.7685 - vertex 20 45.5064 24.0211 - vertex 20 62.8929 25.7602 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 42.9891 10.7098 - vertex 20 31.7214 16.6667 - vertex 20 45.5064 24.0211 - endloop - endfacet - facet normal -0.965578 0.258726 0.0268174 - outer loop - vertex -93.9693 34.202 25 - vertex -95.8872 28.3838 12.0748 - vertex -98.4808 17.3648 25 - endloop - endfacet - facet normal -0.92533 0.37728 0.0377358 - outer loop - vertex -88.3918 46.7642 12.1066 - vertex -91.9278 39.3609 -0.583074 - vertex -95.8872 28.3838 12.0748 - endloop - endfacet - facet normal -0.872232 0.48726 0.042303 - outer loop - vertex -81.6289 57.7643 -0.210629 - vertex -86.8061 49.6458 -13.4447 - vertex -91.9278 39.3609 -0.583074 - endloop - endfacet - facet normal -0.806892 0.589698 0.0343925 - outer loop - vertex -73.4484 67.8625 -12.4043 - vertex -76.6044 64.2788 -25 - vertex -86.8061 49.6458 -13.4447 - endloop - endfacet - facet normal -0.706903 0.706903 -0.0240088 - outer loop - vertex -64.2788 76.6044 -25 - vertex -76.6044 64.2788 -25 - vertex -73.4484 67.8625 -12.4043 - endloop - endfacet - facet normal -0.819138 0.573567 -0.00577243 - outer loop - vertex -86.6025 50 25 - vertex -76.6044 64.2788 25 - vertex -76.1193 64.8525 13.1683 - endloop - endfacet - facet normal -0.826502 0.562313 -0.0264247 - outer loop - vertex -86.6025 50 25 - vertex -76.1193 64.8525 13.1683 - vertex -88.3918 46.7642 12.1066 - endloop - endfacet - facet normal -0.906132 0.422536 0.0197044 - outer loop - vertex -86.6025 50 25 - vertex -88.3918 46.7642 12.1066 - vertex -93.9693 34.202 25 - endloop - endfacet - facet normal -0.827902 0.559086 0.0447356 - outer loop - vertex -76.1193 64.8525 13.1683 - vertex -81.6289 57.7643 -0.210629 - vertex -88.3918 46.7642 12.1066 - endloop - endfacet - facet normal -0.748899 0.661147 0.0451098 - outer loop - vertex -67.4208 73.8541 -0.150617 - vertex -73.4484 67.8625 -12.4043 - vertex -81.6289 57.7643 -0.210629 - endloop - endfacet - facet normal -0.654416 0.754651 0.0473406 - outer loop - vertex -56.9547 82.1959 -12.8877 - vertex -64.2788 76.6044 -25 - vertex -73.4484 67.8625 -12.4043 - endloop - endfacet - facet normal -0.573295 0.818751 -0.0313021 - outer loop - vertex -50 86.6025 -25 - vertex -64.2788 76.6044 -25 - vertex -56.9547 82.1959 -12.8877 - endloop - endfacet - facet normal -0.467369 0.882318 -0.0555016 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -56.9547 82.1959 -12.8877 - vertex -49.9767 86.616 -1.38088 - endloop - endfacet - facet normal -0.423376 0.905953 0.00164934 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -49.9767 86.616 -1.38088 - vertex -34.285 93.939 4.174 - endloop - endfacet - facet normal -0.272573 0.962134 -0.00146785 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -34.285 93.939 4.174 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.416075 0.909038 -0.0230409 - outer loop - vertex -49.9767 86.616 -1.38088 - vertex -46.1796 88.6986 12.2171 - vertex -34.285 93.939 4.174 - endloop - endfacet - facet normal -0.534821 0.844696 -0.0213317 - outer loop - vertex -60.486 79.6332 11.9276 - vertex -50 86.6025 25 - vertex -46.1796 88.6986 12.2171 - endloop - endfacet - facet normal -0.57342 0.818928 0.0233678 - outer loop - vertex -64.2788 76.6044 25 - vertex -50 86.6025 25 - vertex -60.486 79.6332 11.9276 - endloop - endfacet - facet normal -0.687994 0.725027 -0.0316296 - outer loop - vertex -64.2788 76.6044 25 - vertex -60.486 79.6332 11.9276 - vertex -76.1193 64.8525 13.1683 - endloop - endfacet - facet normal -0.707097 0.707097 0.00529705 - outer loop - vertex -64.2788 76.6044 25 - vertex -76.1193 64.8525 13.1683 - vertex -76.6044 64.2788 25 - endloop - endfacet - facet normal -0.684443 0.727688 0.0448035 - outer loop - vertex -60.486 79.6332 11.9276 - vertex -67.4208 73.8541 -0.150617 - vertex -76.1193 64.8525 13.1683 - endloop - endfacet - facet normal -0.587698 0.807766 0.0461062 - outer loop - vertex -49.9767 86.616 -1.38088 - vertex -56.9547 82.1959 -12.8877 - vertex -67.4208 73.8541 -0.150617 - endloop - endfacet - facet normal -0.453525 0.889012 0.063031 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -50 86.6025 -25 - vertex -56.9547 82.1959 -12.8877 - endloop - endfacet - facet normal -0.432135 0.901809 0 - outer loop - vertex -36.1727 93.2284 -36.9681 - vertex -50 86.6025 -41.6667 - vertex -50 86.6025 -25 - endloop - endfacet - facet normal -0.435117 0.900308 0.0108901 - outer loop - vertex -38.8343 92.1515 -54.2819 - vertex -50 86.6025 -41.6667 - vertex -36.1727 93.2284 -36.9681 - endloop - endfacet - facet normal -0.445037 0.895512 0 - outer loop - vertex -50 86.6025 -58.3333 - vertex -50 86.6025 -41.6667 - vertex -38.8343 92.1515 -54.2819 - endloop - endfacet - facet normal -0.0497095 0.998558 0.0202874 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex 4.20548 99.9115 -18.4222 - vertex -2.08806 99.9782 -37.1245 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex 65 -0 25 - vertex 65 0 8.33333 - vertex 67.9289 7.07107 25 - endloop - endfacet - facet normal 0.92388 0.382683 0 - outer loop - vertex 67.9289 -7.07107 8.33333 - vertex 67.9289 -7.07107 -8.33333 - vertex 65 0 8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex 75 -10 -8.33333 - vertex 75 -10 -25 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex 82.0711 -7.07107 -25 - vertex 75 -10 -25 - vertex 75 -10 -8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex 67.9289 -7.07107 25 - vertex 75 -10 8.33333 - vertex 67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 0 - outer loop - vertex 67.9289 -7.07107 25 - vertex 67.9289 -7.07107 8.33333 - vertex 65 -0 25 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex 75 -10 8.33333 - vertex 75 -10 -8.33333 - vertex 67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex 82.0711 -7.07107 -8.33333 - vertex 82.0711 -7.07107 -25 - vertex 75 -10 -8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex 85 -0 -25 - vertex 82.0711 -7.07107 -25 - vertex 82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex 75 -10 25 - vertex 82.0711 -7.07107 8.33333 - vertex 75 -10 8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex 75 -10 25 - vertex 75 -10 8.33333 - vertex 67.9289 -7.07107 25 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex 82.0711 -7.07107 8.33333 - vertex 82.0711 -7.07107 -8.33333 - vertex 75 -10 8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex 85 -0 -8.33333 - vertex 85 -0 -25 - vertex 82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex 82.0711 7.07107 -25 - vertex 85 -0 -25 - vertex 85 -0 -8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex 82.0711 -7.07107 25 - vertex 85 0 8.33333 - vertex 82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex 82.0711 -7.07107 25 - vertex 82.0711 -7.07107 8.33333 - vertex 75 -10 25 - endloop - endfacet - facet normal -0.92388 0.382683 -0 - outer loop - vertex 85 0 8.33333 - vertex 85 -0 -8.33333 - vertex 82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 -0 - outer loop - vertex 82.0711 7.07107 -8.33333 - vertex 82.0711 7.07107 -25 - vertex 85 -0 -8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex 75 10 -25 - vertex 82.0711 7.07107 -25 - vertex 82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex 75 10 -8.33333 - vertex 82.0711 7.07107 -8.33333 - vertex 82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex 75 10 -8.33333 - vertex 82.0711 7.07107 8.33333 - vertex 75 10 8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex 75 10 -8.33333 - vertex 75 10 8.33333 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex 82.0711 7.07107 8.33333 - vertex 82.0711 7.07107 25 - vertex 75 10 8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex 85 0 25 - vertex 82.0711 7.07107 25 - vertex 82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 -0 - outer loop - vertex 85 0 25 - vertex 82.0711 7.07107 8.33333 - vertex 85 0 8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex 85 0 25 - vertex 85 0 8.33333 - vertex 82.0711 -7.07107 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 25.4951 75 - vertex 27.5 36.1733 68.1145 - vertex 27.5 25.4951 62.5 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 27.5 36.1733 68.1145 - vertex 27.5 39.3934 60.6066 - vertex 27.5 25.4951 62.5 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 39.3934 60.6066 - vertex 27.5 36.1733 68.1145 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 36.1733 68.1145 - vertex 27.5 43.1574 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 43.1574 75 - vertex 27.5 60.8198 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 60.8198 75 - vertex 27.5 66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 66.2171 67.7504 - vertex 27.5 60.6066 60.6066 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex 27.5 96.1444 75 - vertex 27.5 96.1444 62.5 - vertex 27.5 78.4821 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 96.1444 62.5 - vertex 27.5 76.8004 61.1116 - vertex 27.5 78.4821 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 80.5722 50 - vertex 27.5 65 50 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex 67.9289 -7.07107 8.33333 - vertex 75 -10 -8.33333 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex 75 -10 8.33333 - vertex 82.0711 -7.07107 -8.33333 - vertex 75 -10 -8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex 82.0711 -7.07107 8.33333 - vertex 85 -0 -8.33333 - vertex 82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex 85 0 8.33333 - vertex 82.0711 7.07107 -8.33333 - vertex 85 -0 -8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex 67.9289 7.07107 8.33333 - vertex 65 0 -8.33333 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 -0 - outer loop - vertex 65 0 -8.33333 - vertex 65 0 8.33333 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex 75 10 25 - vertex 67.9289 7.07107 8.33333 - vertex 75 10 8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 -0 - outer loop - vertex 75 10 25 - vertex 75 10 8.33333 - vertex 82.0711 7.07107 25 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex 67.9289 7.07107 8.33333 - vertex 67.9289 7.07107 -8.33333 - vertex 75 10 8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex 65 0 -8.33333 - vertex 65 0 -25 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 0 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 65 0 -25 - vertex 65 0 -8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex 67.9289 7.07107 25 - vertex 65 0 8.33333 - vertex 67.9289 7.07107 8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex 67.9289 7.07107 25 - vertex 67.9289 7.07107 8.33333 - vertex 75 10 25 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex 65 0 8.33333 - vertex 65 0 -8.33333 - vertex 67.9289 7.07107 8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 0 - outer loop - vertex 67.9289 -7.07107 -8.33333 - vertex 67.9289 -7.07107 -25 - vertex 65 0 -8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex 75 -10 -25 - vertex 67.9289 -7.07107 -25 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 0 - outer loop - vertex 65 -0 25 - vertex 67.9289 -7.07107 8.33333 - vertex 65 0 8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex -82.0711 7.07107 -25 - vertex -82.0711 7.07107 -8.33333 - vertex -85 0 -25 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex -75 10 -8.33333 - vertex -75 10 8.33333 - vertex -82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex -67.9289 7.07107 8.33333 - vertex -67.9289 7.07107 25 - vertex -75 10 8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex -65 0 25 - vertex -67.9289 7.07107 25 - vertex -67.9289 7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex -75 10 -25 - vertex -67.9289 7.07107 -8.33333 - vertex -75 10 -8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex -75 10 -25 - vertex -75 10 -8.33333 - vertex -82.0711 7.07107 -25 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex -67.9289 7.07107 -8.33333 - vertex -67.9289 7.07107 8.33333 - vertex -75 10 -8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex -65 0 8.33333 - vertex -65 0 25 - vertex -67.9289 7.07107 8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex -67.9289 -7.07107 25 - vertex -65 0 25 - vertex -65 0 8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex -67.9289 7.07107 -25 - vertex -65 -0 -8.33333 - vertex -67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex -67.9289 7.07107 -25 - vertex -67.9289 7.07107 -8.33333 - vertex -75 10 -25 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex -65 -0 -8.33333 - vertex -65 0 8.33333 - vertex -67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex -67.9289 -7.07107 8.33333 - vertex -67.9289 -7.07107 25 - vertex -65 0 8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex -75 -10 25 - vertex -67.9289 -7.07107 25 - vertex -67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -67.9289 -7.07107 8.33333 - vertex -67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -67.9289 -7.07107 -8.33333 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -75 -10 -8.33333 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex -67.9289 -7.07107 -8.33333 - vertex -67.9289 -7.07107 -25 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex -65 -0 -25 - vertex -67.9289 -7.07107 -25 - vertex -67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex -65 -0 -25 - vertex -67.9289 -7.07107 -8.33333 - vertex -65 -0 -8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex -65 -0 -25 - vertex -65 -0 -8.33333 - vertex -67.9289 7.07107 -25 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex -67.9289 -7.07107 -8.33333 - vertex -67.9289 -7.07107 8.33333 - vertex -65 -0 -8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -75 -10 25 - vertex -67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex -82.0711 -7.07107 25 - vertex -75 -10 25 - vertex -75 -10 8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 0 - outer loop - vertex -82.0711 -7.07107 25 - vertex -75 -10 8.33333 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 0 - outer loop - vertex -82.0711 -7.07107 25 - vertex -82.0711 -7.07107 8.33333 - vertex -85 -0 25 - endloop - endfacet - facet normal -0.92388 -0.382683 -0 - outer loop - vertex 82.0711 7.07107 8.33333 - vertex 82.0711 7.07107 -8.33333 - vertex 85 0 8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 -0 - outer loop - vertex 75 10 -8.33333 - vertex 75 10 -25 - vertex 82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex 67.9289 7.07107 -25 - vertex 75 10 -25 - vertex 75 10 -8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex 67.9289 7.07107 -25 - vertex 75 10 -8.33333 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex 67.9289 7.07107 -25 - vertex 67.9289 7.07107 -8.33333 - vertex 65 0 -25 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex -82.0711 7.07107 -8.33333 - vertex -75 10 8.33333 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex -75 10 -8.33333 - vertex -67.9289 7.07107 8.33333 - vertex -75 10 8.33333 - endloop - endfacet - facet normal -0.92388 -0.382683 0 - outer loop - vertex -67.9289 7.07107 -8.33333 - vertex -65 0 8.33333 - vertex -67.9289 7.07107 8.33333 - endloop - endfacet - facet normal -0.92388 0.382683 0 - outer loop - vertex -65 -0 -8.33333 - vertex -67.9289 -7.07107 8.33333 - vertex -65 0 8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 -0 - outer loop - vertex -82.0711 -7.07107 -8.33333 - vertex -85 -0 8.33333 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex -85 -0 8.33333 - vertex -85 -0 -8.33333 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 -0 - outer loop - vertex -75 -10 -25 - vertex -82.0711 -7.07107 -8.33333 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal -0.382683 0.92388 0 - outer loop - vertex -75 -10 -25 - vertex -75 -10 -8.33333 - vertex -67.9289 -7.07107 -25 - endloop - endfacet - facet normal 0.382683 0.92388 -0 - outer loop - vertex -82.0711 -7.07107 -8.33333 - vertex -82.0711 -7.07107 8.33333 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 -0 - outer loop - vertex -85 -0 8.33333 - vertex -85 -0 25 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex -82.0711 7.07107 25 - vertex -85 -0 25 - vertex -85 -0 8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 -0 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -85 -0 -8.33333 - vertex -82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.382683 0.92388 -0 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -82.0711 -7.07107 -8.33333 - vertex -75 -10 -25 - endloop - endfacet - facet normal 0.92388 0.382683 -0 - outer loop - vertex -85 -0 -8.33333 - vertex -85 -0 8.33333 - vertex -82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex -82.0711 7.07107 8.33333 - vertex -82.0711 7.07107 25 - vertex -85 -0 8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex -75 10 25 - vertex -82.0711 7.07107 25 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal 0.92388 -0.382683 -0 - outer loop - vertex -85 0 -25 - vertex -82.0711 7.07107 -8.33333 - vertex -85 -0 -8.33333 - endloop - endfacet - facet normal 0.92388 0.382683 0 - outer loop - vertex -85 0 -25 - vertex -85 -0 -8.33333 - vertex -82.0711 -7.07107 -25 - endloop - endfacet - facet normal 0.92388 -0.382683 0 - outer loop - vertex -82.0711 7.07107 -8.33333 - vertex -82.0711 7.07107 8.33333 - vertex -85 -0 -8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex -75 10 8.33333 - vertex -75 10 25 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.382683 -0.92388 0 - outer loop - vertex -67.9289 7.07107 25 - vertex -75 10 25 - vertex -75 10 8.33333 - endloop - endfacet - facet normal 0.382683 -0.92388 0 - outer loop - vertex -82.0711 7.07107 -25 - vertex -75 10 -8.33333 - vertex -82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -25.4951 50 - vertex -27.5 -25.4951 62.5 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -25.4951 62.5 - vertex -27.5 -38.8384 66.7925 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -38.8384 66.7925 - vertex -27.5 -50 60 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -78.4821 75 - vertex -27.5 -73.4553 63.5117 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -73.4553 63.5117 - vertex -27.5 -55.2476 66.9116 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -43.1574 75 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -73.4553 63.5117 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -55.2476 66.9116 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -96.1444 75 - vertex -27.5 -96.1444 62.5 - vertex -27.5 -78.4821 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -96.1444 62.5 - vertex -27.5 -73.4553 63.5117 - vertex -27.5 -78.4821 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -78.0722 50 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -73.4553 63.5117 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -60 50 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -78.0722 50 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 57.0711 57.0711 - vertex -27.5 78.0722 50 - vertex -27.5 73.4553 63.5117 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 60 50 - vertex -27.5 78.0722 50 - vertex -27.5 57.0711 57.0711 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 50 60 - vertex -27.5 57.0711 57.0711 - vertex -27.5 55.2476 66.9116 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -27.5 50 60 - vertex -27.5 38.8384 66.7925 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 55.2476 66.9116 - vertex -27.5 43.1574 75 - vertex -27.5 38.8384 66.7925 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 73.4553 63.5117 - vertex -27.5 60.8198 75 - vertex -27.5 55.2476 66.9116 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 25.4951 62.5 - vertex -27.5 38.8384 66.7925 - vertex -27.5 25.4951 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 38.8384 66.7925 - vertex -27.5 43.1574 75 - vertex -27.5 25.4951 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 55.2476 66.9116 - vertex -27.5 60.8198 75 - vertex -27.5 43.1574 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 73.4553 63.5117 - vertex -27.5 78.4821 75 - vertex -27.5 60.8198 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 96.1444 62.5 - vertex -27.5 78.4821 75 - vertex -27.5 73.4553 63.5117 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 96.1444 75 - vertex -27.5 78.4821 75 - vertex -27.5 96.1444 62.5 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 25.4951 50 - vertex -27.5 40 50 - vertex -27.5 42.9289 57.0711 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 25.4951 50 - vertex -27.5 42.9289 57.0711 - vertex -27.5 25.4951 62.5 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -27.5 38.8384 66.7925 - vertex -27.5 25.4951 62.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -39.3934 60.6066 - vertex 27.5 -50 65 - vertex 27.5 -36.1733 68.1145 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -50 65 - vertex 27.5 -43.1574 75 - vertex 27.5 -36.1733 68.1145 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -25.4951 50 - vertex 27.5 -35 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -35 50 - vertex 27.5 -39.3934 60.6066 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -39.3934 60.6066 - vertex 27.5 -36.1733 68.1145 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -36.1733 68.1145 - vertex 27.5 -25.4951 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -36.1733 68.1145 - vertex 27.5 -43.1574 75 - vertex 27.5 -25.4951 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -50 65 - vertex 27.5 -60.8198 75 - vertex 27.5 -43.1574 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -66.2171 67.7504 - vertex 27.5 -60.8198 75 - vertex 27.5 -50 65 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -78.4821 75 - vertex 27.5 -60.8198 75 - vertex 27.5 -66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -60.6066 60.6066 - vertex 27.5 -76.8004 61.1116 - vertex 27.5 -66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -60.6066 60.6066 - vertex 27.5 -66.2171 67.7504 - vertex 27.5 -50 65 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -76.8004 61.1116 - vertex 27.5 -78.4821 75 - vertex 27.5 -66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -96.1444 62.5 - vertex 27.5 -78.4821 75 - vertex 27.5 -76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -96.1444 75 - vertex 27.5 -78.4821 75 - vertex 27.5 -96.1444 62.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -65 50 - vertex 27.5 -80.5722 50 - vertex 27.5 -76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -65 50 - vertex 27.5 -76.8004 61.1116 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -80.5722 50 - vertex 27.5 -96.1444 62.5 - vertex 27.5 -76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -96.1444 50 - vertex 27.5 -96.1444 62.5 - vertex 27.5 -80.5722 50 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -96.1444 62.5 - vertex -27.5 -78.0722 50 - vertex -27.5 -73.4553 63.5117 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -96.1444 50 - vertex -27.5 -78.0722 50 - vertex -27.5 -96.1444 62.5 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -50 60 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -50 60 - vertex -27.5 -38.8384 66.7925 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -38.8384 66.7925 - vertex -27.5 -43.1574 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -38.8384 66.7925 - vertex -27.5 -25.4951 75 - vertex -27.5 -43.1574 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -25.4951 62.5 - vertex -27.5 -25.4951 75 - vertex -27.5 -38.8384 66.7925 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -40 50 - vertex -27.5 -25.4951 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 20 81.4898 50 - vertex 27.5 80.5722 50 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 65 50 - vertex 27.5 80.5722 50 - vertex 20 81.4898 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 27.5 65 50 - vertex 27.5 80.5722 50 - vertex 20 65 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 35 50 - vertex 25.1837 27.7854 50 - vertex 27.5 25.4951 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 22.6774 29.8661 50 - vertex 25.1837 27.7854 50 - vertex 27.5 35 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 35 50 - vertex 20 31.7214 50 - vertex 22.6774 29.8661 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 20 35 50 - vertex 22.6774 29.8661 50 - vertex 27.5 35 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 25.1837 -27.7854 50 - vertex 22.6774 -29.8661 50 - vertex 27.5 -35 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 25.1837 -27.7854 50 - vertex 27.5 -35 50 - vertex 27.5 -25.4951 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 22.6774 -29.8661 50 - vertex 20 -35 50 - vertex 27.5 -35 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 20 -31.7214 50 - vertex 20 -35 50 - vertex 22.6774 -29.8661 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 27.5 -65 50 - vertex 20 -65 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 20 -65 50 - vertex 20 -81.4898 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 20 -81.4898 50 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 25.016 -96.8204 50 - vertex 27.5 -96.1444 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -81.4898 50 - vertex 22.5155 -97.4323 50 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -97.9796 50 - vertex 22.5155 -97.4323 50 - vertex 20 -81.4898 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 96.1444 62.5 - vertex 27.5 80.5722 50 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 96.1444 50 - vertex 27.5 80.5722 50 - vertex 27.5 96.1444 62.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 60.6066 60.6066 - vertex 27.5 66.2171 67.7504 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 60.6066 60.6066 - vertex 27.5 76.8004 61.1116 - vertex 27.5 65 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 66.2171 67.7504 - vertex 27.5 78.4821 75 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 60.8198 75 - vertex 27.5 78.4821 75 - vertex 27.5 66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 25.4951 62.5 - vertex 27.5 35 50 - vertex 27.5 25.4951 50 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 39.3934 60.6066 - vertex 27.5 35 50 - vertex 27.5 25.4951 62.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 25.4951 75 - vertex 27.5 43.1574 75 - vertex 27.5 36.1733 68.1145 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 50 60 - vertex -27.5 55.2476 66.9116 - vertex -27.5 38.8384 66.7925 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 57.0711 57.0711 - vertex -27.5 73.4553 63.5117 - vertex -27.5 55.2476 66.9116 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 78.0722 50 - vertex -27.5 96.1444 62.5 - vertex -27.5 73.4553 63.5117 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 96.1444 50 - vertex -27.5 96.1444 62.5 - vertex -27.5 78.0722 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 -78.0722 50 - vertex -27.5 -96.1444 50 - vertex -25.016 -96.8204 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -22.5155 -97.4323 50 - vertex -20 -97.9796 50 - vertex -20 -78.9898 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -22.5155 -97.4323 50 - vertex -20 -78.9898 50 - vertex -25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -78.9898 50 - vertex -27.5 -78.0722 50 - vertex -25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -60 50 - vertex -27.5 -78.0722 50 - vertex -20 -78.9898 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -27.5 -60 50 - vertex -27.5 -78.0722 50 - vertex -20 -60 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 -40 50 - vertex -25.1837 -27.7854 50 - vertex -27.5 -25.4951 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -22.6774 -29.8661 50 - vertex -25.1837 -27.7854 50 - vertex -27.5 -40 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -20 -40 50 - vertex -20 -31.7214 50 - vertex -22.6774 -29.8661 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -40 50 - vertex -22.6774 -29.8661 50 - vertex -27.5 -40 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -25.1837 27.7854 50 - vertex -22.6774 29.8661 50 - vertex -27.5 40 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -25.1837 27.7854 50 - vertex -27.5 40 50 - vertex -27.5 25.4951 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -22.6774 29.8661 50 - vertex -20 40 50 - vertex -27.5 40 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -20 31.7214 50 - vertex -20 40 50 - vertex -22.6774 29.8661 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -27.5 60 50 - vertex -20 60 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -20 60 50 - vertex -20 78.9898 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -20 78.9898 50 - vertex -25.016 96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -25.016 96.8204 50 - vertex -27.5 96.1444 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 78.9898 50 - vertex -22.5155 97.4323 50 - vertex -25.016 96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 97.9796 50 - vertex -22.5155 97.4323 50 - vertex -20 78.9898 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 27.5 80.5722 50 - vertex 27.5 96.1444 50 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 22.5155 97.4323 50 - vertex 20 97.9796 50 - vertex 20 81.4898 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 22.5155 97.4323 50 - vertex 20 81.4898 50 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal -0.0610438 0.498335 0.864833 - outer loop - vertex -35.0499 49.8411 40.0013 - vertex -50 42.9289 42.9289 - vertex -36.4184 41.5206 44.6991 - endloop - endfacet - facet normal 0.0306596 -0.964382 0.262731 - outer loop - vertex -36.2567 58.1386 44.1894 - vertex -27.5 60 50 - vertex -40.1038 59.9273 51.2039 - endloop - endfacet - facet normal -0.0266478 -0.941531 -0.335871 - outer loop - vertex -27.5 60 50 - vertex -36.9531 58.2533 55.6466 - vertex -40.1038 59.9273 51.2039 - endloop - endfacet - facet normal -0.0577751 -0.922336 -0.382044 - outer loop - vertex -27.5 57.0711 57.0711 - vertex -36.9531 58.2533 55.6466 - vertex -27.5 60 50 - endloop - endfacet - facet normal 0.0422508 -0.612903 -0.789027 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -36.9531 58.2533 55.6466 - vertex -27.5 57.0711 57.0711 - endloop - endfacet - facet normal -0.0658904 -0.381852 -0.921872 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -27.5 57.0711 57.0711 - vertex -27.5 50 60 - endloop - endfacet - facet normal 0.0612836 0.049483 -0.996893 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -27.5 50 60 - vertex -38.7364 45.8624 59.1039 - endloop - endfacet - facet normal -0.0609022 0.0501174 -0.996885 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -38.7364 45.8624 59.1039 - vertex -50 50 60 - endloop - endfacet - facet normal 0.0669213 0.381826 -0.921808 - outer loop - vertex -38.7364 45.8624 59.1039 - vertex -50 42.9289 57.0711 - vertex -50 50 60 - endloop - endfacet - facet normal 0.065109 0.921919 -0.381871 - outer loop - vertex -38.5748 40.5611 53.3026 - vertex -50 40 50 - vertex -50 42.9289 57.0711 - endloop - endfacet - facet normal 0.0458762 0.922907 0.38228 - outer loop - vertex -36.4184 41.5206 44.6991 - vertex -50 42.9289 42.9289 - vertex -50 40 50 - endloop - endfacet - facet normal 0.00399055 0.38268 0.923872 - outer loop - vertex -35.0499 49.8411 40.0013 - vertex -50 50 40 - vertex -50 42.9289 42.9289 - endloop - endfacet - facet normal -0.00414665 -0.38268 0.923872 - outer loop - vertex -50 57.0711 42.9289 - vertex -50 50 40 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal 0.0400819 -0.445583 0.894343 - outer loop - vertex -20 57.0711 42.9289 - vertex -36.2567 58.1386 44.1894 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal 0.00411914 -0.38268 0.923872 - outer loop - vertex -20 57.0711 42.9289 - vertex -35.0499 49.8411 40.0013 - vertex -20 50 40 - endloop - endfacet - facet normal -0.0461604 -0.455459 0.889059 - outer loop - vertex -36.2567 58.1386 44.1894 - vertex -50 57.0711 42.9289 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal 0.0366412 -0.923259 0.382426 - outer loop - vertex -50 60 50 - vertex -50 57.0711 42.9289 - vertex -36.2567 58.1386 44.1894 - endloop - endfacet - facet normal 0 -0.92388 0.382683 - outer loop - vertex -20 60 50 - vertex -27.5 60 50 - vertex -20 57.0711 42.9289 - endloop - endfacet - facet normal -0.0342048 -0.935646 0.351278 - outer loop - vertex -27.5 60 50 - vertex -36.2567 58.1386 44.1894 - vertex -20 57.0711 42.9289 - endloop - endfacet - facet normal -0.034992 -0.972826 0.228878 - outer loop - vertex -40.1038 59.9273 51.2039 - vertex -50 60 50 - vertex -36.2567 58.1386 44.1894 - endloop - endfacet - facet normal 0.0397317 -0.92315 -0.382381 - outer loop - vertex -50 57.0711 57.0711 - vertex -50 60 50 - vertex -40.1038 59.9273 51.2039 - endloop - endfacet - facet normal 0.0424543 -0.924624 -0.378507 - outer loop - vertex -50 57.0711 57.0711 - vertex -40.1038 59.9273 51.2039 - vertex -36.9531 58.2533 55.6466 - endloop - endfacet - facet normal -0.0335103 -0.596474 -0.801932 - outer loop - vertex -50 57.0711 57.0711 - vertex -36.9531 58.2533 55.6466 - vertex -38.6983 53.2097 59.4709 - endloop - endfacet - facet normal 0.0652896 -0.381867 -0.921908 - outer loop - vertex -50 57.0711 57.0711 - vertex -38.6983 53.2097 59.4709 - vertex -50 50 60 - endloop - endfacet - facet normal 0.00343867 0.999755 -0.0218562 - outer loop - vertex -8.98427 99.5956 -55.7105 - vertex -2.08806 99.9782 -37.1245 - vertex 9.68083 99.5303 -55.7605 - endloop - endfacet - facet normal 0.072206 0.997155 0.0216336 - outer loop - vertex -2.08806 99.9782 -37.1245 - vertex 16.4596 98.6361 -37.1697 - vertex 9.68083 99.5303 -55.7605 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 -28.8675 75 - vertex -38.9258 -37.7032 75 - vertex -40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -28.8675 75 - vertex -40.3789 -22.1533 75 - vertex -50 -9.6225 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -38.9258 -37.7032 75 - vertex -27.5 -25.4951 75 - vertex -40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -43.1574 75 - vertex -27.5 -25.4951 75 - vertex -38.9258 -37.7032 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 -48.1125 75 - vertex -38.8583 -55.5405 75 - vertex -38.9258 -37.7032 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 75 - vertex -38.9258 -37.7032 75 - vertex -50 -28.8675 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -38.8583 -55.5405 75 - vertex -27.5 -43.1574 75 - vertex -38.9258 -37.7032 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -43.1574 75 - vertex -38.8583 -55.5405 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -67.3575 75 - vertex -50 -86.6025 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 -67.3575 75 - vertex -38.6268 -74.3694 75 - vertex -38.8583 -55.5405 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -67.3575 75 - vertex -38.8583 -55.5405 75 - vertex -50 -48.1125 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -38.6268 -74.3694 75 - vertex -27.5 -60.8198 75 - vertex -38.8583 -55.5405 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -78.4821 75 - vertex -27.5 -60.8198 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -42.7684 -90.3928 75 - vertex -35.2517 -93.5805 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -42.7684 -90.3928 75 - vertex -38.6268 -74.3694 75 - vertex -50 -86.6025 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -35.2517 -93.5805 75 - vertex -27.5 -78.4821 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -96.1444 75 - vertex -27.5 -78.4821 75 - vertex -35.2517 -93.5805 75 - endloop - endfacet - facet normal -0.00396407 0.38268 0.923872 - outer loop - vertex -35.0499 49.8411 40.0013 - vertex -20 42.9289 42.9289 - vertex -20 50 40 - endloop - endfacet - facet normal 0.0526004 0.484403 0.873262 - outer loop - vertex -36.4184 41.5206 44.6991 - vertex -20 42.9289 42.9289 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal 0.0709547 0.737322 -0.671805 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -38.5748 40.5611 53.3026 - vertex -38.7364 45.8624 59.1039 - endloop - endfacet - facet normal -0.0670822 0.381821 -0.921798 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -38.7364 45.8624 59.1039 - vertex -27.5 50 60 - endloop - endfacet - facet normal -0.0698944 0.735424 -0.673993 - outer loop - vertex -38.5748 40.5611 53.3026 - vertex -50 42.9289 57.0711 - vertex -38.7364 45.8624 59.1039 - endloop - endfacet - facet normal 0.0895337 0.987127 0.132527 - outer loop - vertex -27.5 40 50 - vertex -36.4184 41.5206 44.6991 - vertex -38.5748 40.5611 53.3026 - endloop - endfacet - facet normal -0.0671594 0.921794 -0.381819 - outer loop - vertex -27.5 40 50 - vertex -38.5748 40.5611 53.3026 - vertex -27.5 42.9289 57.0711 - endloop - endfacet - facet normal -0.0753158 0.99292 0.0918542 - outer loop - vertex -36.4184 41.5206 44.6991 - vertex -50 40 50 - vertex -38.5748 40.5611 53.3026 - endloop - endfacet - facet normal 0 0.92388 0.382683 - outer loop - vertex -20 40 50 - vertex -20 42.9289 42.9289 - vertex -27.5 40 50 - endloop - endfacet - facet normal -0.0435737 0.938499 0.342522 - outer loop - vertex -20 42.9289 42.9289 - vertex -36.4184 41.5206 44.6991 - vertex -27.5 40 50 - endloop - endfacet - facet normal -0.771039 -0.635526 -0.0400865 - outer loop - vertex -79.3664 -60.8356 12.6628 - vertex -83.5527 -54.9449 -0.206588 - vertex -70.347 -71.0725 1.47391 - endloop - endfacet - facet normal -0.886053 -0.461867 -0.0398656 - outer loop - vertex -83.5527 -54.9449 -0.206588 - vertex -89.468 -44.6708 12.2345 - vertex -92.8816 -37.0542 -0.137898 - endloop - endfacet - facet normal -0.832469 -0.551901 -0.0490021 - outer loop - vertex -76.661 -64.2113 -12.9207 - vertex -83.5527 -54.9449 -0.206588 - vertex -88.8886 -45.8128 -12.411 - endloop - endfacet - facet normal -0.959583 -0.278946 -0.0372922 - outer loop - vertex -92.8816 -37.0542 -0.137898 - vertex -96.2203 -27.2335 12.3122 - vertex -98.2656 -18.5439 -0.056713 - endloop - endfacet - facet normal -0.928893 -0.368246 -0.0394114 - outer loop - vertex -88.8886 -45.8128 -12.411 - vertex -92.8816 -37.0542 -0.137898 - vertex -96.131 -27.5468 -12.3849 - endloop - endfacet - facet normal -0.954053 0.296815 -0.0410292 - outer loop - vertex -95.8872 28.3838 12.0748 - vertex -91.9278 39.3609 -0.583074 - vertex -98.004 19.8799 -0.222364 - endloop - endfacet - facet normal -0.871508 0.488564 -0.0421865 - outer loop - vertex -88.3918 46.7642 12.1066 - vertex -81.6289 57.7643 -0.210629 - vertex -91.9278 39.3609 -0.583074 - endloop - endfacet - facet normal -0.748838 0.661419 -0.0420401 - outer loop - vertex -81.6289 57.7643 -0.210629 - vertex -76.1193 64.8525 13.1683 - vertex -67.4208 73.8541 -0.150617 - endloop - endfacet - facet normal -0.804138 0.592432 -0.0488549 - outer loop - vertex -86.8061 49.6458 -13.4447 - vertex -81.6289 57.7643 -0.210629 - vertex -73.4484 67.8625 -12.4043 - endloop - endfacet - facet normal -0.427736 0.903882 0.00623025 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -36.1727 93.2284 -36.9681 - vertex -50 86.6025 -25 - endloop - endfacet - facet normal -0.656021 0.75336 -0.0456656 - outer loop - vertex -73.4484 67.8625 -12.4043 - vertex -67.4208 73.8541 -0.150617 - vertex -56.9547 82.1959 -12.8877 - endloop - endfacet - facet normal -0.591917 0.804732 -0.0451849 - outer loop - vertex -67.4208 73.8541 -0.150617 - vertex -60.486 79.6332 11.9276 - vertex -49.9767 86.616 -1.38088 - endloop - endfacet - facet normal -0.535433 0.844336 0.0201982 - outer loop - vertex -60.486 79.6332 11.9276 - vertex -46.1796 88.6986 12.2171 - vertex -49.9767 86.616 -1.38088 - endloop - endfacet - facet normal -0.979742 0.196265 -0.0398203 - outer loop - vertex -98.004 19.8799 -0.222364 - vertex -95.6263 29.2507 -12.5369 - vertex -99.5096 9.89181 -12.4091 - endloop - endfacet - facet normal -0.91751 0.394577 -0.0498417 - outer loop - vertex -91.9278 39.3609 -0.583074 - vertex -86.8061 49.6458 -13.4447 - vertex -95.6263 29.2507 -12.5369 - endloop - endfacet - facet normal 0.44583 0.895107 -0.00441463 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 36.3222 93.1703 20.308 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.440746 0.897123 0.0302132 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 53.0082 84.7946 7.18018 - vertex 47.4798 88.0095 -7.63112 - endloop - endfacet - facet normal 0.413662 0.910425 -0.00328134 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 47.4798 88.0095 -7.63112 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal 0.542972 0.839502 -0.0204506 - outer loop - vertex 53.0082 84.7946 7.18018 - vertex 61.2701 79.0315 -10.042 - vertex 47.4798 88.0095 -7.63112 - endloop - endfacet - facet normal 0.688791 0.723698 -0.0427499 - outer loop - vertex 70.3409 71.0786 1.47508 - vertex 76.6544 64.2192 -12.9205 - vertex 61.2701 79.0315 -10.042 - endloop - endfacet - facet normal 0.999342 -0.00381363 -0.0360736 - outer loop - vertex 99.9991 -0.416489 -0.064092 - vertex 99.5185 -9.80141 -12.3868 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal -0.542989 -0.839491 -0.0204667 - outer loop - vertex -53.0109 -84.7929 7.17859 - vertex -61.2739 -79.0286 -10.0423 - vertex -47.479 -88.0099 -7.63341 - endloop - endfacet - facet normal -0.995174 -0.0910505 -0.0365873 - outer loop - vertex -98.2656 -18.5439 -0.056713 - vertex -99.6002 -8.93358 12.3277 - vertex -99.9992 0.407363 -0.064789 - endloop - endfacet - facet normal -0.982317 -0.183753 -0.0358934 - outer loop - vertex -96.131 -27.5468 -12.3849 - vertex -98.2656 -18.5439 -0.056713 - vertex -99.5881 -9.06697 -12.3787 - endloop - endfacet - facet normal -0.994083 0.101541 -0.0385735 - outer loop - vertex -99.9992 0.407363 -0.064789 - vertex -99.534 9.64234 12.2585 - vertex -98.004 19.8799 -0.222364 - endloop - endfacet - facet normal -0.999325 0.00408155 -0.0365004 - outer loop - vertex -99.9992 0.407363 -0.064789 - vertex -99.5096 9.89181 -12.4091 - vertex -99.5881 -9.06697 -12.3787 - endloop - endfacet - facet normal 0.250884 0.967922 0.0135595 - outer loop - vertex 16.4596 98.6361 -37.1697 - vertex 34.1021 94.0056 -33.0557 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.414233 0.910001 -0.0175742 - outer loop - vertex 34.1021 94.0056 -33.0557 - vertex 50 86.6025 -41.6667 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.422136 0.906532 0 - outer loop - vertex 50 86.6025 -25 - vertex 50 86.6025 -41.6667 - vertex 34.1021 94.0056 -33.0557 - endloop - endfacet - facet normal 0.546982 0.837065 0.0115611 - outer loop - vertex 50 86.6025 -25 - vertex 47.4798 88.0095 -7.63112 - vertex 61.2701 79.0315 -10.042 - endloop - endfacet - facet normal 0.770968 0.635613 -0.0400547 - outer loop - vertex 79.3607 60.8431 12.6644 - vertex 83.5447 54.9571 -0.204582 - vertex 70.3409 71.0786 1.47508 - endloop - endfacet - facet normal 0.885978 0.462013 -0.0398439 - outer loop - vertex 83.5447 54.9571 -0.204582 - vertex 89.4625 44.6818 12.2368 - vertex 92.8747 37.0715 -0.1349 - endloop - endfacet - facet normal 0.832384 0.552034 -0.0489466 - outer loop - vertex 76.6544 64.2192 -12.9205 - vertex 83.5447 54.9571 -0.204582 - vertex 88.8787 45.8321 -12.4096 - endloop - endfacet - facet normal 0.959539 0.27909 -0.0373291 - outer loop - vertex 92.8747 37.0715 -0.1349 - vertex 96.2174 27.2437 12.3115 - vertex 98.264 18.5522 -0.061308 - endloop - endfacet - facet normal 0.928773 0.368557 -0.0393158 - outer loop - vertex 88.8787 45.8321 -12.4096 - vertex 92.8747 37.0715 -0.1349 - vertex 96.1185 27.5906 -12.3821 - endloop - endfacet - facet normal 0.995173 0.0910368 -0.0366559 - outer loop - vertex 98.264 18.5522 -0.061308 - vertex 99.6001 8.93394 12.3255 - vertex 99.9991 -0.416489 -0.064092 - endloop - endfacet - facet normal 0.98229 0.18384 -0.036193 - outer loop - vertex 96.1185 27.5906 -12.3821 - vertex 98.264 18.5522 -0.061308 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal 0.994149 -0.101057 -0.0381474 - outer loop - vertex 99.9991 -0.416489 -0.064092 - vertex 99.5329 -9.65377 12.257 - vertex 98.0268 -19.7673 -0.202037 - endloop - endfacet - facet normal 0.980931 -0.190919 0.036396 - outer loop - vertex 99.5329 -9.65377 12.257 - vertex 95.9067 -28.318 12.0851 - vertex 98.0268 -19.7673 -0.202037 - endloop - endfacet - facet normal 0.871782 -0.488057 -0.0423874 - outer loop - vertex 88.4105 -46.7288 12.1154 - vertex 81.6519 -57.7318 -0.197758 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.749023 -0.661202 -0.0421588 - outer loop - vertex 81.6519 -57.7318 -0.197758 - vertex 76.1299 -64.8401 13.1775 - vertex 67.4343 -73.8418 -0.134955 - endloop - endfacet - facet normal 0.804302 -0.592204 -0.0489265 - outer loop - vertex 86.8246 -49.6135 -13.4291 - vertex 81.6519 -57.7318 -0.197758 - vertex 73.4611 -67.8488 -12.3904 - endloop - endfacet - facet normal 0.656132 -0.753262 -0.045686 - outer loop - vertex 73.4611 -67.8488 -12.3904 - vertex 67.4343 -73.8418 -0.134955 - vertex 56.9654 -82.1884 -12.8692 - endloop - endfacet - facet normal 0.59203 -0.804646 -0.0452321 - outer loop - vertex 67.4343 -73.8418 -0.134955 - vertex 60.4894 -79.6306 11.9434 - vertex 49.9874 -86.6098 -1.35914 - endloop - endfacet - facet normal 0.535437 -0.844332 0.0202686 - outer loop - vertex 60.4894 -79.6306 11.9434 - vertex 46.1781 -88.6994 12.2251 - vertex 49.9874 -86.6098 -1.35914 - endloop - endfacet - facet normal 0.4193 -0.907543 0.0235196 - outer loop - vertex 46.1781 -88.6994 12.2251 - vertex 50 -86.6025 25 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.403414 -0.915018 -2.90078e-05 - outer loop - vertex 46.1781 -88.6994 12.2251 - vertex 34.3396 -93.9191 21.8686 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.425457 -0.904878 -0.0134952 - outer loop - vertex 50 -86.6025 25 - vertex 36.9775 -92.9121 37.5153 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.284306 -0.958717 -0.00564836 - outer loop - vertex 36.2141 -93.2123 -36.9311 - vertex 34.7327 -93.7744 -16.0932 - vertex 20.5118 -97.8737 -36.1001 - endloop - endfacet - facet normal 0.323441 -0.946205 -0.00908808 - outer loop - vertex 38.8506 -92.1446 -54.264 - vertex 36.2141 -93.2123 -36.9311 - vertex 25.4911 -96.6964 -55.8091 - endloop - endfacet - facet normal 0.173121 -0.984785 -0.0150866 - outer loop - vertex 25.4911 -96.6964 -55.8091 - vertex 20.5118 -97.8737 -36.1001 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal -0.125021 -0.992047 0.0145797 - outer loop - vertex -4.15257 -99.9137 -18.4073 - vertex -20.6573 -97.8431 -19.044 - vertex -16.4069 -98.6449 -37.1516 - endloop - endfacet - facet normal -0.27899 -0.960294 -0 - outer loop - vertex -20 -97.9796 16.6667 - vertex -35.6133 -93.4435 4.12026 - vertex -20 -97.9796 0 - endloop - endfacet - facet normal 0.0897033 0.993132 -0.0751103 - outer loop - vertex 7.0086 -36.8392 -18.2398 - vertex -1.8284 -37.4554 -36.9408 - vertex -13.4703 -34.9972 -18.3411 - endloop - endfacet - facet normal -0.219294 0.973238 -0.0686939 - outer loop - vertex 17.3132 -33.2642 -38.6666 - vertex 9.4897 -36.2794 -56.4108 - vertex -1.8284 -37.4554 -36.9408 - endloop - endfacet - facet normal -0.502817 0.861196 -0.0742751 - outer loop - vertex 26.8281 -26.2012 -56.9324 - vertex 18.75 -32.476 -75 - vertex 9.4897 -36.2794 -56.4108 - endloop - endfacet - facet normal -0.679647 0.729662 0.07532 - outer loop - vertex 23.2669 -29.4092 -22.2881 - vertex 32.0358 -19.4924 -39.2304 - vertex 17.3132 -33.2642 -38.6666 - endloop - endfacet - facet normal -0.426738 0.902558 -0.0573088 - outer loop - vertex 23.2669 -29.4092 -22.2881 - vertex 17.3132 -33.2642 -38.6666 - vertex 7.0086 -36.8392 -18.2398 - endloop - endfacet - facet normal -0.682747 0.726837 -0.0746024 - outer loop - vertex 32.0358 -19.4924 -39.2304 - vertex 26.8281 -26.2012 -56.9324 - vertex 17.3132 -33.2642 -38.6666 - endloop - endfacet - facet normal -0.877544 0.472894 -0.0792925 - outer loop - vertex 36.6441 -7.96625 -56.816 - vertex 32.476 -18.75 -75 - vertex 26.8281 -26.2012 -56.9324 - endloop - endfacet - facet normal -0.366295 0.930499 -0.000187345 - outer loop - vertex 6.99057 -36.8427 0 - vertex 20 -31.7214 0 - vertex 7.0086 -36.8392 -18.2398 - endloop - endfacet - facet normal 0 1 0.000187831 - outer loop - vertex 6.99057 -36.8427 0 - vertex 7.0086 -36.8392 -18.2398 - vertex -6.99057 -36.8427 0 - endloop - endfacet - facet normal -0.408219 0.912221 0.0348016 - outer loop - vertex 20 -31.7214 0 - vertex 23.2669 -29.4092 -22.2881 - vertex 7.0086 -36.8392 -18.2398 - endloop - endfacet - facet normal -0.775151 0.630971 -0.0318761 - outer loop - vertex 33.6967 -16.4554 -19.5029 - vertex 32.0358 -19.4924 -39.2304 - vertex 23.2669 -29.4092 -22.2881 - endloop - endfacet - facet normal -0.9586 0.275929 -0.0703454 - outer loop - vertex 37.4996 -0.172499 -37.9034 - vertex 36.6441 -7.96625 -56.816 - vertex 32.0358 -19.4924 -39.2304 - endloop - endfacet - facet normal -0.993959 -0.0753496 -0.0797955 - outer loop - vertex 34.9655 13.5522 -56.227 - vertex 37.5 -0 -75 - vertex 36.6441 -7.96625 -56.816 - endloop - endfacet - facet normal -0.746104 0.66583 0 - outer loop - vertex 20 -31.7214 16.6667 - vertex 33.7839 -16.2758 -0.75261 - vertex 20 -31.7214 0 - endloop - endfacet - facet normal -0.746171 0.665748 -0.00291086 - outer loop - vertex 33.7839 -16.2758 -0.75261 - vertex 33.6967 -16.4554 -19.5029 - vertex 20 -31.7214 0 - endloop - endfacet - facet normal -0.982543 0.181031 -0.0428669 - outer loop - vertex 37.3331 3.53357 -18.437 - vertex 37.4996 -0.172499 -37.9034 - vertex 33.6967 -16.4554 -19.5029 - endloop - endfacet - facet normal -0.958709 -0.274796 -0.0732416 - outer loop - vertex 31.5798 20.2229 -36.9367 - vertex 34.9655 13.5522 -56.227 - vertex 37.4996 -0.172499 -37.9034 - endloop - endfacet - facet normal -0.766131 -0.638278 -0.0751246 - outer loop - vertex 19.8668 31.805 -57.3293 - vertex 32.476 18.75 -75 - vertex 34.9655 13.5522 -56.227 - endloop - endfacet - facet normal -0.56957 0.821943 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -31.7214 50 - vertex 22.6774 -29.8661 50 - endloop - endfacet - facet normal -0.638659 0.769303 0.0169588 - outer loop - vertex 20 -31.7214 33.3333 - vertex 22.6774 -29.8661 50 - vertex 25.1837 -27.7854 50 - endloop - endfacet - facet normal -0.702209 0.710164 0.0506905 - outer loop - vertex 20 -31.7214 33.3333 - vertex 25.1837 -27.7854 50 - vertex 27.5 -25.4951 50 - endloop - endfacet - facet normal -0.757814 0.644738 0.100155 - outer loop - vertex 20 -31.7214 33.3333 - vertex 27.5 -25.4951 50 - vertex 34.274 -15.2166 35.0879 - endloop - endfacet - facet normal -0.754966 0.655362 -0.0229468 - outer loop - vertex 20 -31.7214 33.3333 - vertex 34.274 -15.2166 35.0879 - vertex 33.6503 -16.5501 17.5219 - endloop - endfacet - facet normal -0.743389 0.66886 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 33.6503 -16.5501 17.5219 - vertex 20 -31.7214 16.6667 - endloop - endfacet - facet normal -0.74351 0.668709 0.00460547 - outer loop - vertex 33.6503 -16.5501 17.5219 - vertex 33.7839 -16.2758 -0.75261 - vertex 20 -31.7214 16.6667 - endloop - endfacet - facet normal -0.983759 0.17946 0.00358158 - outer loop - vertex 37.3569 3.2728 1.15635 - vertex 37.3331 3.53357 -18.437 - vertex 33.7839 -16.2758 -0.75261 - endloop - endfacet - facet normal 0.959117 -0.283007 -0.00141723 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -33.2228 17.3925 -36.523 - vertex -33.1556 17.5202 -16.5603 - endloop - endfacet - facet normal 0.972812 -0.223351 -0.0612433 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -33.1556 17.5202 -16.5603 - vertex -37.4717 -1.45742 -15.9083 - endloop - endfacet - facet normal 0.987648 0.147301 0.0534205 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -37.4717 -1.45742 -15.9083 - vertex -34.3296 -15.0907 -36.4073 - endloop - endfacet - facet normal 0.985003 0.169337 -0.0330756 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -34.3296 -15.0907 -36.4073 - vertex -37.4964 0.521254 -50.7867 - endloop - endfacet - facet normal 0.949211 0.308879 -0.0599313 - outer loop - vertex -37.4717 -1.45742 -15.9083 - vertex -30.9723 -21.1416 -14.419 - vertex -34.3296 -15.0907 -36.4073 - endloop - endfacet - facet normal 0.953518 0.29989 0.0294975 - outer loop - vertex -37.4323 -2.25275 2.36658 - vertex -32.3394 -18.9845 7.84387 - vertex -30.9723 -21.1416 -14.419 - endloop - endfacet - facet normal 0.9596 0.281338 0.00407569 - outer loop - vertex -37.4611 -1.70839 21.1626 - vertex -32.4986 -18.7106 26.4243 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.963354 0.267081 0.0248401 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -33.3967 -17.056 43.464 - vertex -32.4986 -18.7106 26.4243 - endloop - endfacet - facet normal 0.962002 0.273021 0.00331506 - outer loop - vertex -37.3561 -3.2825 58.0705 - vertex -33.5351 -16.7824 61.0745 - vertex -33.3967 -17.056 43.464 - endloop - endfacet - facet normal 0.875445 0.476429 -0.0813178 - outer loop - vertex -36.3417 -9.24839 75 - vertex -27.5 -25.4951 75 - vertex -33.5351 -16.7824 61.0745 - endloop - endfacet - facet normal 0.755967 -0.653665 0.035144 - outer loop - vertex -24.242 28.6108 -21.0482 - vertex -33.2228 17.3925 -36.523 - vertex -21.8234 30.4957 -38.0135 - endloop - endfacet - facet normal 0.456133 -0.88927 -0.0337765 - outer loop - vertex -24.242 28.6108 -21.0482 - vertex -21.8234 30.4957 -38.0135 - vertex -8.64115 36.4908 -17.8341 - endloop - endfacet - facet normal 0.754469 -0.656335 0.000217933 - outer loop - vertex -33.2228 17.3925 -36.523 - vertex -33.2312 17.3763 -55.9708 - vertex -21.8234 30.4957 -38.0135 - endloop - endfacet - facet normal 0.969803 -0.243837 0.00510412 - outer loop - vertex -37.4964 0.521254 -50.7867 - vertex -37.5 0 -75 - vertex -33.2312 17.3763 -55.9708 - endloop - endfacet - facet normal 0.965151 0.258611 0.0400523 - outer loop - vertex -33.7446 -16.3569 -59.8798 - vertex -32.476 -18.75 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0.706131 0.706131 -0.0525098 - outer loop - vertex -18.75 -32.476 -75 - vertex -32.476 -18.75 -75 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.822051 0.569414 0 - outer loop - vertex -27.5 -25.4951 62.5 - vertex -27.5 -25.4951 50 - vertex -33.5351 -16.7824 61.0745 - endloop - endfacet - facet normal 0.822051 0.569414 -0 - outer loop - vertex -27.5 -25.4951 62.5 - vertex -33.5351 -16.7824 61.0745 - vertex -27.5 -25.4951 75 - endloop - endfacet - facet normal 0.820598 0.571501 -0.00243404 - outer loop - vertex -27.5 -25.4951 50 - vertex -33.3967 -17.056 43.464 - vertex -33.5351 -16.7824 61.0745 - endloop - endfacet - facet normal 0.728287 0.684696 -0.0281018 - outer loop - vertex -20 -31.7214 33.3333 - vertex -32.4986 -18.7106 26.4243 - vertex -33.3967 -17.056 43.464 - endloop - endfacet - facet normal 0.719626 0.694349 -0.00406726 - outer loop - vertex -20 -31.7214 16.6667 - vertex -32.3394 -18.9845 7.84387 - vertex -32.4986 -18.7106 26.4243 - endloop - endfacet - facet normal 0.71042 0.70335 -0.0245231 - outer loop - vertex -20 -31.7214 0 - vertex -30.9723 -21.1416 -14.419 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.605897 0.790549 -0.0890018 - outer loop - vertex -13.4703 -34.9972 -18.3411 - vertex -21.223 -30.9166 -34.874 - vertex -30.9723 -21.1416 -14.419 - endloop - endfacet - facet normal 0.31196 0.947495 -0.0702411 - outer loop - vertex -1.8284 -37.4554 -36.9408 - vertex -9.77074 -36.2047 -55.3444 - vertex -21.223 -30.9166 -34.874 - endloop - endfacet - facet normal 0.000234724 0.997843 -0.0656394 - outer loop - vertex 9.4897 -36.2794 -56.4108 - vertex -0 -37.5 -75 - vertex -9.77074 -36.2047 -55.3444 - endloop - endfacet - facet normal 0.089041 0.993668 0.0685262 - outer loop - vertex -6.99057 -36.8427 0 - vertex 7.0086 -36.8392 -18.2398 - vertex -13.4703 -34.9972 -18.3411 - endloop - endfacet - facet normal 0.366061 0.929904 -0.0357574 - outer loop - vertex -6.99057 -36.8427 0 - vertex -13.4703 -34.9972 -18.3411 - vertex -20 -31.7214 0 - endloop - endfacet - facet normal 0.70694 -0.70694 0.0217223 - outer loop - vertex -32.476 18.75 -75 - vertex -18.75 32.476 -75 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal 0.736973 -0.67564 -0.019524 - outer loop - vertex -32.476 18.75 -75 - vertex -20.2142 31.5854 -56.3313 - vertex -33.2312 17.3763 -55.9708 - endloop - endfacet - facet normal 0.965739 -0.258769 0.0196505 - outer loop - vertex -32.476 18.75 -75 - vertex -33.2312 17.3763 -55.9708 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -40.559 40.5083 75 - vertex -50 28.8675 75 - vertex -38.7748 25.5778 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 78.4821 75 - vertex -27.5 96.1444 75 - vertex -35.2517 93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -42.7684 90.3928 75 - vertex -50 86.6025 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -42.7684 90.3928 75 - vertex -38.6275 74.5675 75 - vertex -35.2517 93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.6275 74.5675 75 - vertex -27.5 78.4821 75 - vertex -35.2517 93.5805 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 60.8198 75 - vertex -27.5 78.4821 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -36.3417 9.24839 75 - vertex -38.7748 25.5778 75 - vertex -50 9.6225 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.7748 25.5778 75 - vertex -50 28.8675 75 - vertex -50 9.6225 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -40.559 40.5083 75 - vertex -50 48.1125 75 - vertex -50 28.8675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.9169 56.2753 75 - vertex -50 48.1125 75 - vertex -40.559 40.5083 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 67.3575 75 - vertex -50 48.1125 75 - vertex -38.9169 56.2753 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 67.3575 75 - vertex -38.9169 56.2753 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 67.3575 75 - vertex -38.6275 74.5675 75 - vertex -50 86.6025 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.9169 56.2753 75 - vertex -27.5 60.8198 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -27.5 60.8198 75 - vertex -38.9169 56.2753 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -38.9169 56.2753 75 - vertex -40.559 40.5083 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -40.559 40.5083 75 - vertex -38.7748 25.5778 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -38.7748 25.5778 75 - vertex -27.5 25.4951 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.7748 25.5778 75 - vertex -36.3417 9.24839 75 - vertex -27.5 25.4951 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 9.6225 75 - vertex -36.3417 -9.24839 75 - vertex -36.3417 9.24839 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -9.6225 75 - vertex -36.3417 -9.24839 75 - vertex -50 9.6225 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -40.3789 -22.1533 75 - vertex -36.3417 -9.24839 75 - vertex -50 -9.6225 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 -25.4951 75 - vertex -36.3417 -9.24839 75 - vertex -40.3789 -22.1533 75 - endloop - endfacet - facet normal -0.929991 -0.365358 -0.0403803 - outer loop - vertex 29.4828 23.1736 -15.3386 - vertex 31.5798 20.2229 -36.9367 - vertex 37.3331 3.53357 -18.437 - endloop - endfacet - facet normal -0.660897 -0.749075 -0.0458397 - outer loop - vertex 16.1087 33.8639 -36.7898 - vertex 19.8668 31.805 -57.3293 - vertex 31.5798 20.2229 -36.9367 - endloop - endfacet - facet normal -0.25826 -0.965861 -0.0203501 - outer loop - vertex -1.45427 37.4718 -55.7041 - vertex 18.75 32.476 -75 - vertex 19.8668 31.805 -57.3293 - endloop - endfacet - facet normal 0.366251 -0.930386 -0.0155423 - outer loop - vertex -6.99057 36.8427 0 - vertex -20 31.7214 0 - vertex -8.64115 36.4908 -17.8341 - endloop - endfacet - facet normal 0 -0.999805 0.0197245 - outer loop - vertex -6.99057 36.8427 0 - vertex -8.64115 36.4908 -17.8341 - vertex 6.99057 36.8427 0 - endloop - endfacet - facet normal 0.443373 -0.895307 0.0429598 - outer loop - vertex -20 31.7214 0 - vertex -24.242 28.6108 -21.0482 - vertex -8.64115 36.4908 -17.8341 - endloop - endfacet - facet normal 0.779729 -0.626116 0.00138242 - outer loop - vertex -33.1556 17.5202 -16.5603 - vertex -33.2228 17.3925 -36.523 - vertex -24.242 28.6108 -21.0482 - endloop - endfacet - facet normal 0.961822 -0.271662 0.0331487 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -37.4964 0.521254 -50.7867 - vertex -33.2228 17.3925 -36.523 - endloop - endfacet - facet normal 0.977554 0.210281 0.0130177 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -33.7446 -16.3569 -59.8798 - vertex -37.4964 0.521254 -50.7867 - endloop - endfacet - facet normal 0.769165 0.632962 0.0880034 - outer loop - vertex -25.0898 -27.8703 -52.7154 - vertex -18.75 -32.476 -75 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.258274 0.963891 0.0648686 - outer loop - vertex -9.77074 -36.2047 -55.3444 - vertex -0 -37.5 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal -0.25821 0.963654 0.0685405 - outer loop - vertex 9.4897 -36.2794 -56.4108 - vertex 18.75 -32.476 -75 - vertex -0 -37.5 -75 - endloop - endfacet - facet normal -0.705352 0.705352 0.0704023 - outer loop - vertex 26.8281 -26.2012 -56.9324 - vertex 32.476 -18.75 -75 - vertex 18.75 -32.476 -75 - endloop - endfacet - facet normal -0.963706 0.258224 0.0677645 - outer loop - vertex 36.6441 -7.96625 -56.816 - vertex 37.5 -0 -75 - vertex 32.476 -18.75 -75 - endloop - endfacet - facet normal -0.964391 -0.258408 0.0563453 - outer loop - vertex 34.9655 13.5522 -56.227 - vertex 32.476 18.75 -75 - vertex 37.5 -0 -75 - endloop - endfacet - facet normal -0.706994 -0.706994 0.01784 - outer loop - vertex 19.8668 31.805 -57.3293 - vertex 18.75 32.476 -75 - vertex 32.476 18.75 -75 - endloop - endfacet - facet normal -0.258762 -0.965715 -0.0209138 - outer loop - vertex -1.45427 37.4718 -55.7041 - vertex 0 37.5 -75 - vertex 18.75 32.476 -75 - endloop - endfacet - facet normal 0.258777 -0.965768 0.0180913 - outer loop - vertex -18.75 32.476 -75 - vertex 0 37.5 -75 - vertex -1.45427 37.4718 -55.7041 - endloop - endfacet - facet normal -0.822096 -0.569349 -0 - outer loop - vertex 27.5 25.4951 62.5 - vertex 27.5 25.4951 50 - vertex 33.5378 16.777 61.0519 - endloop - endfacet - facet normal -0.822096 -0.569349 0 - outer loop - vertex 27.5 25.4951 62.5 - vertex 33.5378 16.777 61.0519 - vertex 27.5 25.4951 75 - endloop - endfacet - facet normal -0.820599 -0.5715 -0.00251479 - outer loop - vertex 27.5 25.4951 50 - vertex 33.3945 17.0604 43.4034 - vertex 33.5378 16.777 61.0519 - endloop - endfacet - facet normal -0.728047 -0.684923 -0.0287843 - outer loop - vertex 20 31.7214 33.3333 - vertex 32.4669 18.7657 26.2883 - vertex 33.3945 17.0604 43.4034 - endloop - endfacet - facet normal -0.717293 -0.696717 -0.00874011 - outer loop - vertex 20 31.7214 16.6667 - vertex 32.1117 19.3672 7.48614 - vertex 32.4669 18.7657 26.2883 - endloop - endfacet - facet normal -0.702048 -0.71113 -0.0377308 - outer loop - vertex 20 31.7214 0 - vertex 29.4828 23.1736 -15.3386 - vertex 32.1117 19.3672 7.48614 - endloop - endfacet - facet normal -0.556638 -0.828156 -0.0656685 - outer loop - vertex 11.0649 35.8304 -18.8367 - vertex 16.1087 33.8639 -36.7898 - vertex 29.4828 23.1736 -15.3386 - endloop - endfacet - facet normal -0.163516 -0.985875 -0.036224 - outer loop - vertex -4.28242 37.2547 -37.0287 - vertex -1.45427 37.4718 -55.7041 - vertex 16.1087 33.8639 -36.7898 - endloop - endfacet - facet normal 0.299981 -0.953692 -0.0219679 - outer loop - vertex -20.2142 31.5854 -56.3313 - vertex -18.75 32.476 -75 - vertex -1.45427 37.4718 -55.7041 - endloop - endfacet - facet normal 0.885787 0.46223 0.0415335 - outer loop - vertex 92.8747 37.0715 -0.1349 - vertex 88.8787 45.8321 -12.4096 - vertex 83.5447 54.9571 -0.204582 - endloop - endfacet - facet normal 0.928885 0.368714 0.034979 - outer loop - vertex 96.1185 27.5906 -12.3821 - vertex 93.9693 34.202 -25 - vertex 88.8787 45.8321 -12.4096 - endloop - endfacet - facet normal 0.965522 0.258711 -0.0288999 - outer loop - vertex 98.4808 17.3648 -25 - vertex 93.9693 34.202 -25 - vertex 96.1185 27.5906 -12.3821 - endloop - endfacet - facet normal 0.932031 0.360894 -0.032779 - outer loop - vertex 93.9693 34.202 25 - vertex 96.2174 27.2437 12.3115 - vertex 89.4625 44.6818 12.2368 - endloop - endfacet - facet normal 0.905978 0.422464 0.0269758 - outer loop - vertex 93.9693 34.202 25 - vertex 89.4625 44.6818 12.2368 - vertex 86.6025 50 25 - endloop - endfacet - facet normal 0.931867 0.36112 0.0348754 - outer loop - vertex 96.2174 27.2437 12.3115 - vertex 92.8747 37.0715 -0.1349 - vertex 89.4625 44.6818 12.2368 - endloop - endfacet - facet normal 0.95944 0.279359 0.0378577 - outer loop - vertex 98.264 18.5522 -0.061308 - vertex 96.1185 27.5906 -12.3821 - vertex 92.8747 37.0715 -0.1349 - endloop - endfacet - facet normal 0.982332 0.183861 0.0349072 - outer loop - vertex 99.5907 9.03858 -12.3789 - vertex 98.4808 17.3648 -25 - vertex 96.1185 27.5906 -12.3821 - endloop - endfacet - facet normal 0.995743 0.0871163 -0.030095 - outer loop - vertex 100 0 -25 - vertex 98.4808 17.3648 -25 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal 0.982795 0.181547 -0.0339666 - outer loop - vertex 98.4808 17.3648 25 - vertex 99.6001 8.93394 12.3255 - vertex 96.2174 27.2437 12.3115 - endloop - endfacet - facet normal 0.965514 0.258709 0.0291914 - outer loop - vertex 98.4808 17.3648 25 - vertex 96.2174 27.2437 12.3115 - vertex 93.9693 34.202 25 - endloop - endfacet - facet normal 0.982751 0.181592 0.0349994 - outer loop - vertex 99.6001 8.93394 12.3255 - vertex 98.264 18.5522 -0.061308 - vertex 96.2174 27.2437 12.3115 - endloop - endfacet - facet normal 0.995165 0.0910254 0.0368805 - outer loop - vertex 99.9991 -0.416489 -0.064092 - vertex 99.5907 9.03858 -12.3789 - vertex 98.264 18.5522 -0.061308 - endloop - endfacet - facet normal 0.999374 -0.00384349 0.0351633 - outer loop - vertex 99.5185 -9.80141 -12.3868 - vertex 100 0 -25 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal 0.995756 -0.0871174 -0.0296846 - outer loop - vertex 98.4808 -17.3648 -25 - vertex 100 0 -25 - vertex 99.5185 -9.80141 -12.3868 - endloop - endfacet - facet normal 0.925652 -0.376944 -0.0328743 - outer loop - vertex 93.9693 -34.202 25 - vertex 88.4105 -46.7288 12.1154 - vertex 95.9067 -28.318 12.0851 - endloop - endfacet - facet normal 0.965574 -0.258725 0.0269749 - outer loop - vertex 93.9693 -34.202 25 - vertex 95.9067 -28.318 12.0851 - vertex 98.4808 -17.3648 25 - endloop - endfacet - facet normal 0.925529 -0.376777 0.0378927 - outer loop - vertex 88.4105 -46.7288 12.1154 - vertex 91.9574 -39.2917 -0.568089 - vertex 95.9067 -28.318 12.0851 - endloop - endfacet - facet normal 0.872506 -0.486758 0.0424358 - outer loop - vertex 81.6519 -57.7318 -0.197758 - vertex 86.8246 -49.6135 -13.4291 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.807054 -0.589481 0.0342866 - outer loop - vertex 73.4611 -67.8488 -12.3904 - vertex 76.6044 -64.2788 -25 - vertex 86.8246 -49.6135 -13.4291 - endloop - endfacet - facet normal 0.819139 -0.573567 -0.00564582 - outer loop - vertex 86.6025 -50 25 - vertex 76.6044 -64.2788 25 - vertex 76.1299 -64.8401 13.1775 - endloop - endfacet - facet normal 0.826647 -0.562086 -0.0267088 - outer loop - vertex 86.6025 -50 25 - vertex 76.1299 -64.8401 13.1775 - vertex 88.4105 -46.7288 12.1154 - endloop - endfacet - facet normal 0.906129 -0.422535 0.0198734 - outer loop - vertex 86.6025 -50 25 - vertex 88.4105 -46.7288 12.1154 - vertex 93.9693 -34.202 25 - endloop - endfacet - facet normal 0.828058 -0.558845 0.0448685 - outer loop - vertex 76.1299 -64.8401 13.1775 - vertex 81.6519 -57.7318 -0.197758 - vertex 88.4105 -46.7288 12.1154 - endloop - endfacet - facet normal 0.749092 -0.660923 0.0451827 - outer loop - vertex 67.4343 -73.8418 -0.134955 - vertex 73.4611 -67.8488 -12.3904 - vertex 81.6519 -57.7318 -0.197758 - endloop - endfacet - facet normal 0.654547 -0.754542 0.047281 - outer loop - vertex 56.9654 -82.1884 -12.8692 - vertex 64.2788 -76.6044 -25 - vertex 73.4611 -67.8488 -12.3904 - endloop - endfacet - facet normal 0.423483 0.905898 -0.00324111 - outer loop - vertex 34.7811 93.7564 -13.9596 - vertex 50 86.6025 -25 - vertex 34.1021 94.0056 -33.0557 - endloop - endfacet - facet normal 0.611534 0.790119 -0.0416859 - outer loop - vertex 65.7761 75.3227 14.953 - vertex 70.3409 71.0786 1.47508 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.628377 0.776801 0.0415016 - outer loop - vertex 70.3409 71.0786 1.47508 - vertex 61.2701 79.0315 -10.042 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.695669 0.71798 0.0234301 - outer loop - vertex 76.6544 64.2192 -12.9205 - vertex 64.2788 76.6044 -25 - vertex 61.2701 79.0315 -10.042 - endloop - endfacet - facet normal 0.573473 0.819004 -0.0190203 - outer loop - vertex 50 86.6025 25 - vertex 64.2788 76.6044 25 - vertex 65.7761 75.3227 14.953 - endloop - endfacet - facet normal 0.588853 0.808053 0.017425 - outer loop - vertex 50 86.6025 25 - vertex 65.7761 75.3227 14.953 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.437619 0.898994 -0.0173319 - outer loop - vertex 50 86.6025 25 - vertex 53.0082 84.7946 7.18018 - vertex 36.3222 93.1703 20.308 - endloop - endfacet - facet normal 0.433804 0.901001 -0.00340086 - outer loop - vertex 50 86.6025 25 - vertex 36.3222 93.1703 20.308 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.436396 0.899755 -0 - outer loop - vertex 50 86.6025 25 - vertex 37.053 92.882 37.1706 - vertex 50 86.6025 41.6667 - endloop - endfacet - facet normal 0.285572 0.958349 0.00400388 - outer loop - vertex 36.3222 93.1703 20.308 - vertex 20 97.9796 33.3333 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.282636 0.959227 -0 - outer loop - vertex 20 97.9796 16.6667 - vertex 20 97.9796 33.3333 - vertex 36.3222 93.1703 20.308 - endloop - endfacet - facet normal 0.281842 0.959453 0.00385478 - outer loop - vertex 20 97.9796 16.6667 - vertex 36.3222 93.1703 20.308 - vertex 35.6132 93.4436 4.12214 - endloop - endfacet - facet normal 0.278989 0.960294 0 - outer loop - vertex 20 97.9796 16.6667 - vertex 35.6132 93.4436 4.12214 - vertex 20 97.9796 0 - endloop - endfacet - facet normal 0.278056 0.960557 0.00382634 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 34.7811 93.7564 -13.9596 - vertex 20 97.9796 0 - endloop - endfacet - facet normal 0.41764 0.90852 -0.0129943 - outer loop - vertex 47.4798 88.0095 -7.63112 - vertex 50 86.6025 -25 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal 0.573488 0.819026 -0.0175408 - outer loop - vertex 61.2701 79.0315 -10.042 - vertex 64.2788 76.6044 -25 - vertex 50 86.6025 -25 - endloop - endfacet - facet normal 0.707107 0.707107 0.000562899 - outer loop - vertex 76.6544 64.2192 -12.9205 - vertex 76.6044 64.2788 -25 - vertex 64.2788 76.6044 -25 - endloop - endfacet - facet normal 0.819152 0.573576 -0.000558006 - outer loop - vertex 86.6025 50 -25 - vertex 76.6044 64.2788 -25 - vertex 76.6544 64.2192 -12.9205 - endloop - endfacet - facet normal 0.72671 0.686341 -0.0287829 - outer loop - vertex 76.6044 64.2788 25 - vertex 79.3607 60.8431 12.6644 - vertex 65.7761 75.3227 14.953 - endloop - endfacet - facet normal 0.707025 0.707025 0.0151698 - outer loop - vertex 76.6044 64.2788 25 - vertex 65.7761 75.3227 14.953 - vertex 64.2788 76.6044 25 - endloop - endfacet - facet normal 0.731503 0.681025 0.0332987 - outer loop - vertex 79.3607 60.8431 12.6644 - vertex 70.3409 71.0786 1.47508 - vertex 65.7761 75.3227 14.953 - endloop - endfacet - facet normal 0.775046 0.630675 0.0394035 - outer loop - vertex 83.5447 54.9571 -0.204582 - vertex 76.6544 64.2192 -12.9205 - vertex 70.3409 71.0786 1.47508 - endloop - endfacet - facet normal 0.831879 0.553975 0.0329969 - outer loop - vertex 88.8787 45.8321 -12.4096 - vertex 86.6025 50 -25 - vertex 76.6544 64.2192 -12.9205 - endloop - endfacet - facet normal 0.906048 0.422497 -0.0239357 - outer loop - vertex 93.9693 34.202 -25 - vertex 86.6025 50 -25 - vertex 88.8787 45.8321 -12.4096 - endloop - endfacet - facet normal 0.847192 0.530372 -0.0311595 - outer loop - vertex 86.6025 50 25 - vertex 89.4625 44.6818 12.2368 - vertex 79.3607 60.8431 12.6644 - endloop - endfacet - facet normal 0.81893 0.573421 0.0232729 - outer loop - vertex 86.6025 50 25 - vertex 79.3607 60.8431 12.6644 - vertex 76.6044 64.2788 25 - endloop - endfacet - facet normal 0.847894 0.529095 0.0336739 - outer loop - vertex 89.4625 44.6818 12.2368 - vertex 83.5447 54.9571 -0.204582 - vertex 79.3607 60.8431 12.6644 - endloop - endfacet - facet normal 0.979912 -0.195986 0.0369006 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 98.4808 -17.3648 -25 - vertex 99.5185 -9.80141 -12.3868 - endloop - endfacet - facet normal 0.965606 -0.258733 -0.0257511 - outer loop - vertex 93.9693 -34.202 -25 - vertex 98.4808 -17.3648 -25 - vertex 95.647 -29.1831 -12.5165 - endloop - endfacet - facet normal 0.916847 -0.397557 0.0366151 - outer loop - vertex 93.9693 -34.202 -25 - vertex 95.647 -29.1831 -12.5165 - vertex 86.8246 -49.6135 -13.4291 - endloop - endfacet - facet normal 0.906303 -0.422616 -0.00327192 - outer loop - vertex 93.9693 -34.202 -25 - vertex 86.8246 -49.6135 -13.4291 - vertex 86.6025 -50 -25 - endloop - endfacet - facet normal 0.819147 -0.573573 0.00344294 - outer loop - vertex 86.8246 -49.6135 -13.4291 - vertex 76.6044 -64.2788 -25 - vertex 86.6025 -50 -25 - endloop - endfacet - facet normal 0.706904 -0.706904 -0.0239237 - outer loop - vertex 73.4611 -67.8488 -12.3904 - vertex 64.2788 -76.6044 -25 - vertex 76.6044 -64.2788 -25 - endloop - endfacet - facet normal 0.573296 -0.818752 -0.0312595 - outer loop - vertex 56.9654 -82.1884 -12.8692 - vertex 50 -86.6025 -25 - vertex 64.2788 -76.6044 -25 - endloop - endfacet - facet normal 0.428062 -0.903729 0.00605476 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 36.2141 -93.2123 -36.9311 - vertex 50 -86.6025 -25 - endloop - endfacet - facet normal 0.285275 -0.958331 0.0148286 - outer loop - vertex 20.5118 -97.8737 -36.1001 - vertex 25.4911 -96.6964 -55.8091 - vertex 36.2141 -93.2123 -36.9311 - endloop - endfacet - facet normal 0.173395 -0.984685 0.0181307 - outer loop - vertex 9.04165 -99.5904 -55.6649 - vertex 17.3648 -98.4808 -75 - vertex 25.4911 -96.6964 -55.8091 - endloop - endfacet - facet normal 0.0871389 -0.996002 -0.0196492 - outer loop - vertex 0 -100 -75 - vertex 17.3648 -98.4808 -75 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal -0.422618 -0.906308 -0 - outer loop - vertex -50 -86.6025 -58.3333 - vertex -50 -86.6025 -75 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal 0.31402 -0.949416 0 - outer loop - vertex 27.5 -96.1444 75 - vertex 27.5 -96.1444 62.5 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0.329267 -0.944178 -0.0105292 - outer loop - vertex 27.5 -96.1444 62.5 - vertex 39.2665 -91.9681 55.9636 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0.331243 -0.943518 0.00717941 - outer loop - vertex 27.5 -96.1444 50 - vertex 36.9775 -92.9121 37.5153 - vertex 39.2665 -91.9681 55.9636 - endloop - endfacet - facet normal 0.282806 -0.959074 0.0140419 - outer loop - vertex 20 -97.9796 33.3333 - vertex 34.3396 -93.9191 21.8686 - vertex 36.9775 -92.9121 37.5153 - endloop - endfacet - facet normal 0.272444 -0.962172 3.34064e-05 - outer loop - vertex 20 -97.9796 16.6667 - vertex 34.3321 -93.9218 4.1825 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.27285 -0.962055 -0.00160311 - outer loop - vertex 20 -97.9796 0 - vertex 34.7327 -93.7744 -16.0932 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.24262 -0.969766 0.0262458 - outer loop - vertex 14.1378 -98.9956 -18.6292 - vertex 20.5118 -97.8737 -36.1001 - vertex 34.7327 -93.7744 -16.0932 - endloop - endfacet - facet normal 0.112766 -0.993399 0.0210532 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex 9.04165 -99.5904 -55.6649 - vertex 20.5118 -97.8737 -36.1001 - endloop - endfacet - facet normal -0.00305374 -0.99974 0.0226065 - outer loop - vertex -9.63293 -99.535 -55.7352 - vertex 0 -100 -75 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal -0.0871391 -0.996005 -0.0195286 - outer loop - vertex -17.3648 -98.4808 -75 - vertex 0 -100 -75 - vertex -9.63293 -99.535 -55.7352 - endloop - endfacet - facet normal -0.199712 -0.979495 0.0265558 - outer loop - vertex -17.3648 -98.4808 -75 - vertex -9.63293 -99.535 -55.7352 - vertex -30.515 -95.2304 -54.0087 - endloop - endfacet - facet normal -0.258799 -0.965849 -0.0125721 - outer loop - vertex -17.3648 -98.4808 -75 - vertex -30.515 -95.2304 -54.0087 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal -0.407939 -0.912854 0.0168078 - outer loop - vertex -30.515 -95.2304 -54.0087 - vertex -50 -86.6025 -58.3333 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal -0.40488 -0.91437 -0 - outer loop - vertex -50 -86.6025 -41.6667 - vertex -50 -86.6025 -58.3333 - vertex -30.515 -95.2304 -54.0087 - endloop - endfacet - facet normal 0.467724 -0.882143 -0.0552994 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 56.9654 -82.1884 -12.8692 - vertex 49.9874 -86.6098 -1.35914 - endloop - endfacet - facet normal 0.423698 -0.905802 0.00178586 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 49.9874 -86.6098 -1.35914 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.416356 -0.908909 -0.0230573 - outer loop - vertex 49.9874 -86.6098 -1.35914 - vertex 46.1781 -88.6994 12.2251 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.53484 -0.844683 -0.0213637 - outer loop - vertex 60.4894 -79.6306 11.9434 - vertex 50 -86.6025 25 - vertex 46.1781 -88.6994 12.2251 - endloop - endfacet - facet normal 0.57342 -0.818928 0.0233835 - outer loop - vertex 64.2788 -76.6044 25 - vertex 50 -86.6025 25 - vertex 60.4894 -79.6306 11.9434 - endloop - endfacet - facet normal 0.688062 -0.724961 -0.031667 - outer loop - vertex 64.2788 -76.6044 25 - vertex 60.4894 -79.6306 11.9434 - vertex 76.1299 -64.8401 13.1775 - endloop - endfacet - facet normal 0.707097 -0.707097 0.00519068 - outer loop - vertex 64.2788 -76.6044 25 - vertex 76.1299 -64.8401 13.1775 - vertex 76.6044 -64.2788 25 - endloop - endfacet - facet normal 0.684525 -0.727607 0.0448735 - outer loop - vertex 60.4894 -79.6306 11.9434 - vertex 67.4343 -73.8418 -0.134955 - vertex 76.1299 -64.8401 13.1775 - endloop - endfacet - facet normal 0.587831 -0.807668 0.0461252 - outer loop - vertex 49.9874 -86.6098 -1.35914 - vertex 56.9654 -82.1884 -12.8692 - vertex 67.4343 -73.8418 -0.134955 - endloop - endfacet - facet normal 0.454064 -0.888762 0.0626778 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 50 -86.6025 -25 - vertex 56.9654 -82.1884 -12.8692 - endloop - endfacet - facet normal 0.445116 -0.895473 0 - outer loop - vertex 38.8506 -92.1446 -54.264 - vertex 50 -86.6025 -58.3333 - vertex 50 -86.6025 -41.6667 - endloop - endfacet - facet normal 0.439328 -0.898116 -0.0194595 - outer loop - vertex 34.202 -93.9693 -75 - vertex 50 -86.6025 -58.3333 - vertex 38.8506 -92.1446 -54.264 - endloop - endfacet - facet normal 0.422618 -0.906308 0 - outer loop - vertex 50 -86.6025 -75 - vertex 50 -86.6025 -58.3333 - vertex 34.202 -93.9693 -75 - endloop - endfacet - facet normal 0.432336 -0.901713 0 - outer loop - vertex 50 -86.6025 -25 - vertex 36.2141 -93.2123 -36.9311 - vertex 50 -86.6025 -41.6667 - endloop - endfacet - facet normal 0.435314 -0.900214 0.0107618 - outer loop - vertex 36.2141 -93.2123 -36.9311 - vertex 38.8506 -92.1446 -54.264 - vertex 50 -86.6025 -41.6667 - endloop - endfacet - facet normal 0.321322 -0.946903 0.0112878 - outer loop - vertex 25.4911 -96.6964 -55.8091 - vertex 34.202 -93.9693 -75 - vertex 38.8506 -92.1446 -54.264 - endloop - endfacet - facet normal 0.258768 -0.965737 -0.0197822 - outer loop - vertex 17.3648 -98.4808 -75 - vertex 34.202 -93.9693 -75 - vertex 25.4911 -96.6964 -55.8091 - endloop - endfacet - facet normal 0.979898 -0.195468 -0.0399108 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 99.5185 -9.80141 -12.3868 - vertex 98.0268 -19.7673 -0.202037 - endloop - endfacet - facet normal 0.953812 -0.297311 0.0430005 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 98.0268 -19.7673 -0.202037 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.917721 -0.394066 -0.0500009 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 91.9574 -39.2917 -0.568089 - vertex 86.8246 -49.6135 -13.4291 - endloop - endfacet - facet normal 0.95433 -0.295893 -0.0412457 - outer loop - vertex 98.0268 -19.7673 -0.202037 - vertex 95.9067 -28.318 12.0851 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.98113 -0.190308 -0.0341499 - outer loop - vertex 99.5329 -9.65377 12.257 - vertex 98.4808 -17.3648 25 - vertex 95.9067 -28.318 12.0851 - endloop - endfacet - facet normal 0.995761 -0.0871178 0.0295007 - outer loop - vertex 100 0 25 - vertex 98.4808 -17.3648 25 - vertex 99.5329 -9.65377 12.257 - endloop - endfacet - facet normal 0.999416 -0.00348743 -0.0339894 - outer loop - vertex 100 0 25 - vertex 99.5329 -9.65377 12.257 - vertex 99.6001 8.93394 12.3255 - endloop - endfacet - facet normal 0.995747 0.0871166 0.0299908 - outer loop - vertex 100 0 25 - vertex 99.6001 8.93394 12.3255 - vertex 98.4808 17.3648 25 - endloop - endfacet - facet normal 0.99938 -0.00374159 0.0350091 - outer loop - vertex 99.5329 -9.65377 12.257 - vertex 99.9991 -0.416489 -0.064092 - vertex 99.6001 8.93394 12.3255 - endloop - endfacet - facet normal 0.994076 -0.101596 0.038603 - outer loop - vertex 98.0268 -19.7673 -0.202037 - vertex 99.5185 -9.80141 -12.3868 - vertex 99.9991 -0.416489 -0.064092 - endloop - endfacet - facet normal 0.262583 -0.964836 -0.0119242 - outer loop - vertex 20 -97.9796 33.3333 - vertex 27.5 -96.1444 50 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal 0.291797 -0.956126 -0.0260295 - outer loop - vertex 36.9775 -92.9121 37.5153 - vertex 27.5 -96.1444 50 - vertex 20 -97.9796 33.3333 - endloop - endfacet - facet normal 0.334485 -0.942401 0 - outer loop - vertex 27.5 -96.1444 62.5 - vertex 27.5 -96.1444 50 - vertex 39.2665 -91.9681 55.9636 - endloop - endfacet - facet normal 0.464229 -0.885715 0 - outer loop - vertex 50 -86.6025 58.3333 - vertex 50 -86.6025 75 - vertex 42.7684 -90.3928 75 - endloop - endfacet - facet normal 0.390422 -0.920626 0.00436352 - outer loop - vertex 35.2517 -93.5805 75 - vertex 39.2665 -91.9681 55.9636 - vertex 42.7684 -90.3928 75 - endloop - endfacet - facet normal 0.448636 -0.893673 -0.00857562 - outer loop - vertex 39.2665 -91.9681 55.9636 - vertex 50 -86.6025 58.3333 - vertex 42.7684 -90.3928 75 - endloop - endfacet - facet normal 0.447138 -0.894465 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -86.6025 58.3333 - vertex 39.2665 -91.9681 55.9636 - endloop - endfacet - facet normal 0.438176 -0.89885 -0.00837458 - outer loop - vertex 50 -86.6025 41.6667 - vertex 39.2665 -91.9681 55.9636 - vertex 36.9775 -92.9121 37.5153 - endloop - endfacet - facet normal 0.43603 -0.899932 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 36.9775 -92.9121 37.5153 - vertex 50 -86.6025 25 - endloop - endfacet - facet normal 0.438629 0.898632 -0.00799847 - outer loop - vertex 39.2656 91.9685 55.8745 - vertex 50 86.6025 41.6667 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.447134 0.894467 0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 86.6025 41.6667 - vertex 39.2656 91.9685 55.8745 - endloop - endfacet - facet normal 0.31402 0.949416 -0 - outer loop - vertex 27.5 96.1444 62.5 - vertex 27.5 96.1444 75 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal 0.464229 0.885715 0 - outer loop - vertex 42.7684 90.3928 75 - vertex 50 86.6025 75 - vertex 50 86.6025 58.3333 - endloop - endfacet - facet normal 0.448684 0.89365 -0.00854957 - outer loop - vertex 42.7684 90.3928 75 - vertex 50 86.6025 58.3333 - vertex 39.2656 91.9685 55.8745 - endloop - endfacet - facet normal 0.390422 0.920626 0.00434332 - outer loop - vertex 42.7684 90.3928 75 - vertex 39.2656 91.9685 55.8745 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal 0.32921 0.944198 -0.0104901 - outer loop - vertex 39.2656 91.9685 55.8745 - vertex 27.5 96.1444 62.5 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal 0.33448 0.942403 -0 - outer loop - vertex 27.5 96.1444 50 - vertex 27.5 96.1444 62.5 - vertex 39.2656 91.9685 55.8745 - endloop - endfacet - facet normal 0.331423 0.943457 0.00687286 - outer loop - vertex 27.5 96.1444 50 - vertex 39.2656 91.9685 55.8745 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.291664 0.956168 -0.025965 - outer loop - vertex 27.5 96.1444 50 - vertex 37.053 92.882 37.1706 - vertex 20 97.9796 33.3333 - endloop - endfacet - facet normal 0.262583 0.964836 -0.0119242 - outer loop - vertex 27.5 96.1444 50 - vertex 20 97.9796 33.3333 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0.237676 0.971336 -0.00397595 - outer loop - vertex 20 97.9796 33.3333 - vertex 22.5155 97.4323 50 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0.212595 0.97714 0 - outer loop - vertex 20 97.9796 50 - vertex 22.5155 97.4323 50 - vertex 20 97.9796 33.3333 - endloop - endfacet - facet normal 0.277202 0.960808 0.00267716 - outer loop - vertex 34.1021 94.0056 -33.0557 - vertex 20.6881 97.8366 -19.0489 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal 0.277161 0.960819 0.0028001 - outer loop - vertex 20.6881 97.8366 -19.0489 - vertex 20 97.9796 0 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal 0.167012 0.985954 -0.00136756 - outer loop - vertex 13.3836 99.1004 0 - vertex 20 97.9796 0 - vertex 20.6881 97.8366 -19.0489 - endloop - endfacet - facet normal -0.212595 0.97714 0 - outer loop - vertex -20 97.9796 50 - vertex -20 97.9796 33.3333 - vertex -22.5155 97.4323 50 - endloop - endfacet - facet normal -0.417593 -0.908541 -0.0130081 - outer loop - vertex -47.479 -88.0099 -7.63341 - vertex -50 -86.6025 -25 - vertex -34.7716 -93.76 -13.9625 - endloop - endfacet - facet normal -0.413626 -0.910441 -0.00331964 - outer loop - vertex -47.479 -88.0099 -7.63341 - vertex -34.7716 -93.76 -13.9625 - vertex -35.6133 -93.4435 4.12026 - endloop - endfacet - facet normal -0.278047 -0.96056 0.0038683 - outer loop - vertex -34.7716 -93.76 -13.9625 - vertex -20 -97.9796 0 - vertex -35.6133 -93.4435 4.12026 - endloop - endfacet - facet normal 0.115023 -0.993123 -0.0218062 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex 20.5118 -97.8737 -36.1001 - vertex 14.1378 -98.9956 -18.6292 - endloop - endfacet - facet normal 0.0503733 -0.998522 0.0204123 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex 14.1378 -98.9956 -18.6292 - vertex -4.15257 -99.9137 -18.4073 - endloop - endfacet - facet normal -0.0713934 -0.997231 -0.020831 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex -4.15257 -99.9137 -18.4073 - vertex -16.4069 -98.6449 -37.1516 - endloop - endfacet - facet normal -0.0715566 -0.997201 0.0216777 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex -16.4069 -98.6449 -37.1516 - vertex -9.63293 -99.535 -55.7352 - endloop - endfacet - facet normal -0.00288645 -0.999757 -0.0218322 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex -9.63293 -99.535 -55.7352 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal -0.203993 -0.978586 -0.0274886 - outer loop - vertex -16.4069 -98.6449 -37.1516 - vertex -30.515 -95.2304 -54.0087 - vertex -9.63293 -99.535 -55.7352 - endloop - endfacet - facet normal -0.25052 -0.968016 0.0135915 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -30.515 -95.2304 -54.0087 - vertex -16.4069 -98.6449 -37.1516 - endloop - endfacet - facet normal -0.257274 -0.966178 -0.0176097 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -16.4069 -98.6449 -37.1516 - vertex -20.6573 -97.8431 -19.044 - endloop - endfacet - facet normal -0.276988 -0.96087 0.00272984 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -20.6573 -97.8431 -19.044 - vertex -34.7716 -93.76 -13.9625 - endloop - endfacet - facet normal -0.423401 -0.905936 -0.00330525 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -34.7716 -93.76 -13.9625 - vertex -50 -86.6025 -25 - endloop - endfacet - facet normal -0.277006 -0.960864 0.00267528 - outer loop - vertex -20.6573 -97.8431 -19.044 - vertex -20 -97.9796 0 - vertex -34.7716 -93.76 -13.9625 - endloop - endfacet - facet normal -0.167012 -0.985954 -0.00130114 - outer loop - vertex -13.3836 -99.1004 0 - vertex -20 -97.9796 0 - vertex -20.6573 -97.8431 -19.044 - endloop - endfacet - facet normal -0.123768 -0.992144 -0.0182266 - outer loop - vertex -13.3836 -99.1004 0 - vertex -20.6573 -97.8431 -19.044 - vertex -4.15257 -99.9137 -18.4073 - endloop - endfacet - facet normal -0.100507 -0.994916 -0.00643894 - outer loop - vertex -13.3836 -99.1004 0 - vertex -4.15257 -99.9137 -18.4073 - vertex -6.70689 -99.7748 0 - endloop - endfacet - facet normal -0.0335533 -0.999433 0.00288605 - outer loop - vertex -4.15257 -99.9137 -18.4073 - vertex 0 -100 0 - vertex -6.70689 -99.7748 0 - endloop - endfacet - facet normal 0.0335509 -0.999362 -0.0122519 - outer loop - vertex 6.70689 -99.7748 0 - vertex 0 -100 0 - vertex -4.15257 -99.9137 -18.4073 - endloop - endfacet - facet normal 0.0498599 -0.998517 -0.0218798 - outer loop - vertex 6.70689 -99.7748 0 - vertex -4.15257 -99.9137 -18.4073 - vertex 14.1378 -98.9956 -18.6292 - endloop - endfacet - facet normal 0.100509 -0.994935 -0.001527 - outer loop - vertex 6.70689 -99.7748 0 - vertex 14.1378 -98.9956 -18.6292 - vertex 13.3836 -99.1004 0 - endloop - endfacet - facet normal 0.167012 -0.985954 0.0012159 - outer loop - vertex 14.1378 -98.9956 -18.6292 - vertex 20 -97.9796 0 - vertex 13.3836 -99.1004 0 - endloop - endfacet - facet normal 0.248604 -0.968272 -0.0254237 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 20 -97.9796 0 - vertex 14.1378 -98.9956 -18.6292 - endloop - endfacet - facet normal 0.272417 -0.962179 0 - outer loop - vertex 20 -97.9796 16.6667 - vertex 20 -97.9796 0 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.272455 -0.962168 0 - outer loop - vertex 20 -97.9796 33.3333 - vertex 20 -97.9796 16.6667 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.212595 -0.97714 0 - outer loop - vertex 22.5155 -97.4323 50 - vertex 20 -97.9796 50 - vertex 20 -97.9796 33.3333 - endloop - endfacet - facet normal 0.237676 -0.971336 -0.00397595 - outer loop - vertex 22.5155 -97.4323 50 - vertex 20 -97.9796 33.3333 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal -0.390422 -0.920626 0.00434332 - outer loop - vertex -35.2517 -93.5805 75 - vertex -42.7684 -90.3928 75 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.33448 -0.942403 0 - outer loop - vertex -27.5 -96.1444 50 - vertex -27.5 -96.1444 62.5 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.32921 -0.944198 -0.0104901 - outer loop - vertex -27.5 -96.1444 62.5 - vertex -35.2517 -93.5805 75 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.31402 -0.949416 -0 - outer loop - vertex -27.5 -96.1444 75 - vertex -35.2517 -93.5805 75 - vertex -27.5 -96.1444 62.5 - endloop - endfacet - facet normal -0.445846 -0.895099 -0.00441914 - outer loop - vertex -35.6133 -93.4435 4.12026 - vertex -36.323 -93.17 20.3068 - vertex -53.0109 -84.7929 7.17859 - endloop - endfacet - facet normal -0.437628 -0.898989 -0.0173471 - outer loop - vertex -36.323 -93.17 20.3068 - vertex -50 -86.6025 25 - vertex -53.0109 -84.7929 7.17859 - endloop - endfacet - facet normal -0.433807 -0.901 -0.00339705 - outer loop - vertex -37.053 -92.882 37.1703 - vertex -50 -86.6025 25 - vertex -36.323 -93.17 20.3068 - endloop - endfacet - facet normal -0.436396 -0.899755 -0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -50 -86.6025 25 - vertex -37.053 -92.882 37.1703 - endloop - endfacet - facet normal -0.43863 -0.898632 -0.00799833 - outer loop - vertex -50 -86.6025 41.6667 - vertex -37.053 -92.882 37.1703 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.447134 -0.894467 0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -39.2656 -91.9685 55.8744 - vertex -50 -86.6025 58.3333 - endloop - endfacet - facet normal -0.331423 -0.943457 0.00687268 - outer loop - vertex -37.053 -92.882 37.1703 - vertex -27.5 -96.1444 50 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.321028 0.947002 0.0113107 - outer loop - vertex -25.4516 96.7069 -55.8478 - vertex -34.202 93.9693 -75 - vertex -38.8343 92.1515 -54.2819 - endloop - endfacet - facet normal -0.258768 0.965736 -0.0198131 - outer loop - vertex -17.3648 98.4808 -75 - vertex -34.202 93.9693 -75 - vertex -25.4516 96.7069 -55.8478 - endloop - endfacet - facet normal -0.172641 0.984867 -0.0152194 - outer loop - vertex -20.4194 97.893 -36.1707 - vertex -8.98427 99.5956 -55.7105 - vertex -25.4516 96.7069 -55.8478 - endloop - endfacet - facet normal -0.284586 0.958533 0.0149968 - outer loop - vertex -20.4194 97.893 -36.1707 - vertex -25.4516 96.7069 -55.8478 - vertex -36.1727 93.2284 -36.9681 - endloop - endfacet - facet normal -0.172903 0.984771 0.0182055 - outer loop - vertex -8.98427 99.5956 -55.7105 - vertex -17.3648 98.4808 -75 - vertex -25.4516 96.7069 -55.8478 - endloop - endfacet - facet normal -0.0871388 0.996001 -0.0197047 - outer loop - vertex 0 100 -75 - vertex -17.3648 98.4808 -75 - vertex -8.98427 99.5956 -55.7105 - endloop - endfacet - facet normal 0.422618 0.906308 0 - outer loop - vertex 50 86.6025 -58.3333 - vertex 50 86.6025 -75 - vertex 34.202 93.9693 -75 - endloop - endfacet - facet normal 0.408031 0.912815 0.0167028 - outer loop - vertex 50 86.6025 -58.3333 - vertex 34.202 93.9693 -75 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.404993 0.91432 -0 - outer loop - vertex 50 86.6025 -58.3333 - vertex 30.5386 95.2229 -54.0167 - vertex 50 86.6025 -41.6667 - endloop - endfacet - facet normal -0.0335508 0.999359 -0.0124583 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex -6.70689 99.7748 0 - vertex 0 100 0 - endloop - endfacet - facet normal 0.0335533 0.999433 0.00286007 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 0 100 0 - vertex 6.70689 99.7748 0 - endloop - endfacet - facet normal 0.100507 0.994917 -0.00626455 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 6.70689 99.7748 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0.124198 0.992091 -0.0181921 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 13.3836 99.1004 0 - vertex 20.6881 97.8366 -19.0489 - endloop - endfacet - facet normal 0.125429 0.991997 0.0144983 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 20.6881 97.8366 -19.0489 - vertex 16.4596 98.6361 -37.1697 - endloop - endfacet - facet normal 0.257643 0.966082 -0.0174971 - outer loop - vertex 20.6881 97.8366 -19.0489 - vertex 34.1021 94.0056 -33.0557 - vertex 16.4596 98.6361 -37.1697 - endloop - endfacet - facet normal -0.237676 0.971336 -0.00397595 - outer loop - vertex -20 97.9796 33.3333 - vertex -25.016 96.8204 50 - vertex -22.5155 97.4323 50 - endloop - endfacet - facet normal -0.262583 0.964836 -0.0119242 - outer loop - vertex -27.5 96.1444 50 - vertex -25.016 96.8204 50 - vertex -20 97.9796 33.3333 - endloop - endfacet - facet normal -0.282796 0.959076 0.014097 - outer loop - vertex -36.9782 92.9119 37.517 - vertex -20 97.9796 33.3333 - vertex -34.3293 93.9228 21.8746 - endloop - endfacet - facet normal -0.425411 0.904899 -0.0135552 - outer loop - vertex -36.9782 92.9119 37.517 - vertex -34.3293 93.9228 21.8746 - vertex -50 86.6025 25 - endloop - endfacet - facet normal -0.419262 0.907561 0.0235134 - outer loop - vertex -34.3293 93.9228 21.8746 - vertex -46.1796 88.6986 12.2171 - vertex -50 86.6025 25 - endloop - endfacet - facet normal -0.403273 0.91508 -0.000172616 - outer loop - vertex -34.285 93.939 4.174 - vertex -46.1796 88.6986 12.2171 - vertex -34.3293 93.9228 21.8746 - endloop - endfacet - facet normal -0.272336 0.962202 0.000197802 - outer loop - vertex -34.285 93.939 4.174 - vertex -34.3293 93.9228 21.8746 - vertex -20 97.9796 16.6667 - endloop - endfacet - facet normal -0.272176 0.962247 0 - outer loop - vertex -34.285 93.939 4.174 - vertex -20 97.9796 16.6667 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.272403 0.962183 0 - outer loop - vertex -34.3293 93.9228 21.8746 - vertex -20 97.9796 33.3333 - vertex -20 97.9796 16.6667 - endloop - endfacet - facet normal -0.291803 0.956124 -0.0260327 - outer loop - vertex -36.9782 92.9119 37.517 - vertex -27.5 96.1444 50 - vertex -20 97.9796 33.3333 - endloop - endfacet - facet normal -0.331244 0.943518 0.00717843 - outer loop - vertex -39.2668 91.968 55.9654 - vertex -27.5 96.1444 50 - vertex -36.9782 92.9119 37.517 - endloop - endfacet - facet normal -0.334487 0.942401 0 - outer loop - vertex -27.5 96.1444 62.5 - vertex -27.5 96.1444 50 - vertex -39.2668 91.968 55.9654 - endloop - endfacet - facet normal -0.464229 0.885715 0 - outer loop - vertex -50 86.6025 58.3333 - vertex -50 86.6025 75 - vertex -42.7684 90.3928 75 - endloop - endfacet - facet normal -0.31402 0.949416 0 - outer loop - vertex -35.2517 93.5805 75 - vertex -27.5 96.1444 75 - vertex -27.5 96.1444 62.5 - endloop - endfacet - facet normal -0.329269 0.944177 -0.0105308 - outer loop - vertex -35.2517 93.5805 75 - vertex -27.5 96.1444 62.5 - vertex -39.2668 91.968 55.9654 - endloop - endfacet - facet normal -0.390422 0.920626 0.00436389 - outer loop - vertex -35.2517 93.5805 75 - vertex -39.2668 91.968 55.9654 - vertex -42.7684 90.3928 75 - endloop - endfacet - facet normal -0.448636 0.893673 -0.00857553 - outer loop - vertex -39.2668 91.968 55.9654 - vertex -50 86.6025 58.3333 - vertex -42.7684 90.3928 75 - endloop - endfacet - facet normal -0.44714 0.894464 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -50 86.6025 58.3333 - vertex -39.2668 91.968 55.9654 - endloop - endfacet - facet normal -0.438178 0.898849 -0.00837238 - outer loop - vertex -50 86.6025 41.6667 - vertex -39.2668 91.968 55.9654 - vertex -36.9782 92.9119 37.517 - endloop - endfacet - facet normal -0.436034 0.89993 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -36.9782 92.9119 37.517 - vertex -50 86.6025 25 - endloop - endfacet - facet normal -0.573472 -0.819003 -0.0190692 - outer loop - vertex -50 -86.6025 25 - vertex -64.2788 -76.6044 25 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.688844 -0.723646 -0.0427743 - outer loop - vertex -70.347 -71.0725 1.47391 - vertex -76.661 -64.2113 -12.9207 - vertex -61.2739 -79.0286 -10.0423 - endloop - endfacet - facet normal -0.628423 -0.776762 0.0415239 - outer loop - vertex -70.347 -71.0725 1.47391 - vertex -61.2739 -79.0286 -10.0423 - vertex -53.0109 -84.7929 7.17859 - endloop - endfacet - facet normal -0.611576 -0.790085 -0.041717 - outer loop - vertex -70.347 -71.0725 1.47391 - vertex -53.0109 -84.7929 7.17859 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.588878 -0.808033 0.0174423 - outer loop - vertex -53.0109 -84.7929 7.17859 - vertex -50 -86.6025 25 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.464229 -0.885715 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -42.7684 -90.3928 75 - vertex -50 -86.6025 75 - endloop - endfacet - facet normal -0.448684 -0.89365 -0.00854954 - outer loop - vertex -39.2656 -91.9685 55.8744 - vertex -42.7684 -90.3928 75 - vertex -50 -86.6025 58.3333 - endloop - endfacet -endsolid patch0 diff --git a/tutorials/socketOctree/socket1.stl b/tutorials/socketOctree/socket1.stl deleted file mode 100644 index 6378b676fddf39c2280050e5838ac4b6e70b3ce9..0000000000000000000000000000000000000000 --- a/tutorials/socketOctree/socket1.stl +++ /dev/null @@ -1,11930 +0,0 @@ -solid patch - facet normal 0 0 1 - outer loop - vertex -98.4808 17.3648 25 - vertex -100 0 25 - vertex -90.472 14.6634 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -58.9291 18.1066 25 - vertex -67.9289 7.07107 25 - vertex -50 9.6225 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -76.6044 -64.2788 25 - vertex -64.2788 -76.6044 25 - vertex -61.2753 -61.6257 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 25 - vertex -61.2753 -61.6257 25 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -82.0711 7.07107 25 - vertex -81.203 24.5589 25 - vertex -90.472 14.6634 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -98.4808 17.3648 25 - vertex -90.472 14.6634 25 - vertex -93.9693 34.202 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -67.5886 27.0128 25 - vertex -67.9289 7.07107 25 - vertex -58.9291 18.1066 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 28.8675 25 - vertex -58.9291 18.1066 25 - vertex -50 9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -61.2753 -61.6257 25 - vertex -64.2788 -76.6044 25 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -82.0711 7.07107 25 - vertex -75 10 25 - vertex -81.203 24.5589 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 34.202 25 - vertex -90.472 14.6634 25 - vertex -81.203 24.5589 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 28.8675 25 - vertex -67.5886 27.0128 25 - vertex -58.9291 18.1066 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -75 10 25 - vertex -67.9289 7.07107 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -67.3575 25 - vertex -64.2788 -76.6044 25 - vertex -50 -86.6025 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -81.203 24.5589 25 - vertex -75 10 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -93.9693 34.202 25 - vertex -81.203 24.5589 25 - vertex -77.7885 41.2952 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 28.8675 25 - vertex -64.1254 44.5169 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -77.7885 41.2952 25 - vertex -81.203 24.5589 25 - vertex -67.5886 27.0128 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 34.202 25 - vertex -77.7885 41.2952 25 - vertex -86.6025 50 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -50 28.8675 25 - vertex -50 48.1125 25 - vertex -64.1254 44.5169 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -77.7885 41.2952 25 - vertex -67.5886 27.0128 25 - vertex -64.1254 44.5169 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -77.7885 41.2952 25 - vertex -76.6044 64.2788 25 - vertex -86.6025 50 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.1254 44.5169 25 - vertex -50 48.1125 25 - vertex -61.4482 60.1728 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.1254 44.5169 25 - vertex -76.6044 64.2788 25 - vertex -77.7885 41.2952 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -61.4482 60.1728 25 - vertex -50 48.1125 25 - vertex -50 67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -76.6044 64.2788 25 - vertex -64.1254 44.5169 25 - vertex -61.4482 60.1728 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.2788 76.6044 25 - vertex -61.4482 60.1728 25 - vertex -50 67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -64.2788 76.6044 25 - vertex -76.6044 64.2788 25 - vertex -61.4482 60.1728 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 86.6025 25 - vertex -64.2788 76.6044 25 - vertex -50 67.3575 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -75 -10 25 - vertex -86.3348 -19.8135 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -62.9265 -20.6629 25 - vertex -75 -10 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -75 -10 25 - vertex -82.0711 -7.07107 25 - vertex -86.3348 -19.8135 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -76.5403 -27.9427 25 - vertex -86.3348 -19.8135 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -62.9265 -20.6629 25 - vertex -67.9289 -7.07107 25 - vertex -75 -10 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -63.2012 -36.5076 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -86.3348 -19.8135 25 - vertex -82.0711 -7.07107 25 - vertex -91.3679 -8.97974 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -77.4233 -43.4472 25 - vertex -76.5403 -27.9427 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -86.3348 -19.8135 25 - vertex -98.4808 -17.3648 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -9.6225 25 - vertex -67.9289 -7.07107 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -76.5403 -27.9427 25 - vertex -77.4233 -43.4472 25 - vertex -63.2012 -36.5076 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -63.2012 -36.5076 25 - vertex -50 -28.8675 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -82.0711 -7.07107 25 - vertex -85 0 25 - vertex -91.3679 -8.97974 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -98.4808 -17.3648 25 - vertex -86.3348 -19.8135 25 - vertex -91.3679 -8.97974 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -93.9693 -34.202 25 - vertex -86.6025 -50 25 - vertex -77.4233 -43.4472 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -82.0711 7.07107 25 - vertex -90.472 14.6634 25 - vertex -85 0 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 25 - vertex -65.9129 -50.6425 25 - vertex -61.2753 -61.6257 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -65.9129 -50.6425 25 - vertex -76.6044 -64.2788 25 - vertex -61.2753 -61.6257 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 9.6225 25 - vertex -67.9289 7.07107 25 - vertex -65 0 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -100 0 25 - vertex -85 0 25 - vertex -90.472 14.6634 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 25 - vertex -63.2012 -36.5076 25 - vertex -65.9129 -50.6425 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -65.9129 -50.6425 25 - vertex -77.4233 -43.4472 25 - vertex -76.6044 -64.2788 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 9.6225 25 - vertex -65 0 25 - vertex -50 -9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -77.4233 -43.4472 25 - vertex -86.6025 -50 25 - vertex -76.6044 -64.2788 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -98.4808 -17.3648 25 - vertex -91.3679 -8.97974 25 - vertex -100 0 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -91.3679 -8.97974 25 - vertex -85 0 25 - vertex -100 0 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -50 -48.1125 25 - vertex -50 -28.8675 25 - vertex -63.2012 -36.5076 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -63.2012 -36.5076 25 - vertex -77.4233 -43.4472 25 - vertex -65.9129 -50.6425 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -50 -28.8675 25 - vertex -50 -9.6225 25 - vertex -62.9265 -20.6629 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -9.6225 25 - vertex -65 0 25 - vertex -67.9289 -7.07107 25 - endloop - endfacet -endsolid patch -solid patch000 - facet normal -0 0 1 - outer loop - vertex 38.6275 74.5675 75 - vertex 50 67.3575 75 - vertex 50 86.6025 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 78.4821 75 - vertex 27.5 60.8198 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.8583 -55.5402 75 - vertex 27.5 -60.8198 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -67.3575 75 - vertex 38.8583 -55.5402 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 38.9169 56.2753 75 - vertex 50 67.3575 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 60.8198 75 - vertex 38.9169 56.2753 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -43.1574 75 - vertex 27.5 -60.8198 75 - vertex 38.8583 -55.5402 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 50 -67.3575 75 - vertex 50 -48.1125 75 - vertex 38.8583 -55.5402 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 38.9169 56.2753 75 - vertex 50 48.1125 75 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 60.8198 75 - vertex 27.5 43.1574 75 - vertex 38.9169 56.2753 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -67.3575 75 - vertex 38.6268 -74.3693 75 - vertex 50 -86.6025 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -60.8198 75 - vertex 27.5 -78.4821 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 78.4821 75 - vertex 38.6275 74.5675 75 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 42.7684 90.3928 75 - vertex 38.6275 74.5675 75 - vertex 50 86.6025 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 42.7684 -90.3928 75 - vertex 50 -86.6025 75 - vertex 38.6268 -74.3693 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.6268 -74.3693 75 - vertex 27.5 -78.4821 75 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 42.7684 90.3928 75 - vertex 35.2517 93.5805 75 - vertex 38.6275 74.5675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 96.1444 75 - vertex 27.5 78.4821 75 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 42.7684 -90.3928 75 - vertex 38.6268 -74.3693 75 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -78.4821 75 - vertex 27.5 -96.1444 75 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 36.3417 9.24839 75 - vertex 36.3417 -9.24839 75 - vertex 50 9.6225 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 36.3417 -9.24839 75 - vertex 50 -9.6225 75 - vertex 50 9.6225 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 36.3417 9.24839 75 - vertex 50 9.6225 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 40.3789 -22.1533 75 - vertex 50 -9.6225 75 - vertex 36.3417 -9.24839 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 50 9.6225 75 - vertex 50 28.8675 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 25.4951 75 - vertex 36.3417 9.24839 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 40.3789 -22.1533 75 - vertex 50 -28.8675 75 - vertex 50 -9.6225 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -25.4951 75 - vertex 40.3789 -22.1533 75 - vertex 36.3417 -9.24839 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.7748 25.5778 75 - vertex 50 28.8675 75 - vertex 40.559 40.5083 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 25.4951 75 - vertex 38.7748 25.5778 75 - vertex 27.5 43.1574 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.9258 -37.7032 75 - vertex 50 -28.8675 75 - vertex 40.3789 -22.1533 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 -25.4951 75 - vertex 38.9258 -37.7032 75 - vertex 40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 40.559 40.5083 75 - vertex 27.5 43.1574 75 - vertex 38.7748 25.5778 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 50 28.8675 75 - vertex 50 48.1125 75 - vertex 40.559 40.5083 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 38.9258 -37.7032 75 - vertex 50 -48.1125 75 - vertex 50 -28.8675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -43.1574 75 - vertex 38.9258 -37.7032 75 - vertex 27.5 -25.4951 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 43.1574 75 - vertex 40.559 40.5083 75 - vertex 38.9169 56.2753 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 40.559 40.5083 75 - vertex 50 48.1125 75 - vertex 38.9169 56.2753 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 38.8583 -55.5402 75 - vertex 50 -48.1125 75 - vertex 38.9258 -37.7032 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 27.5 -43.1574 75 - vertex 38.8583 -55.5402 75 - vertex 38.9258 -37.7032 75 - endloop - endfacet -endsolid patch000 -solid patch001 - facet normal 0 0 1 - outer loop - vertex -20 81.4151 0 - vertex -20 64.8505 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 64.8505 0 - vertex 20 81.4151 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -13.3836 99.1004 0 - vertex -20 81.4151 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 80.0149 0 - vertex 20 81.4151 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -13.3836 99.1004 0 - vertex -20 97.9796 0 - vertex -20 81.4151 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -13.3836 99.1004 0 - vertex 0 80.0149 0 - vertex -6.70689 99.7748 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 81.4151 0 - vertex 20 97.9796 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 6.70689 99.7748 0 - vertex 0 80.0149 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 0 80.0149 0 - vertex 0 100 0 - vertex -6.70689 99.7748 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 6.70689 99.7748 0 - vertex 0 100 0 - vertex 0 80.0149 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 0 47.412 0 - vertex 0 60.5293 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 60.5293 0 - vertex 0 47.412 0 - vertex 20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 60.5293 0 - vertex -20 64.8505 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 48.286 0 - vertex -6.99057 36.8427 0 - vertex 0 47.412 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 0 47.412 0 - vertex 6.99057 36.8427 0 - vertex 20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 64.8505 0 - vertex 0 60.5293 0 - vertex 20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 80.0149 0 - vertex -20 64.8505 0 - vertex 0 60.5293 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -6.99057 36.8427 0 - vertex 6.99057 36.8427 0 - vertex 0 47.412 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 31.7214 0 - vertex -6.99057 36.8427 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 48.286 0 - vertex 6.99057 36.8427 0 - vertex 20 31.7214 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 64.8505 0 - vertex 0 80.0149 0 - vertex 0 60.5293 0 - endloop - endfacet -endsolid patch001 -solid patch002 - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -50 -67.3575 25 - vertex -50 -86.6025 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -50 -72.7398 45.1315 - vertex -50 -86.6025 41.6667 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 50 60 - vertex -50 42.9289 57.0711 - vertex -50 38.1931 66.569 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 75 - vertex -50 48.1125 75 - vertex -50 38.1931 66.569 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -72.4016 61.5374 - vertex -50 -86.6025 75 - vertex -50 -67.3575 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -60 50 - vertex -50 -72.4016 61.5374 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.1125 25 - vertex -50 50 40 - vertex -50 67.3575 25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -60 50 - vertex -50 -57.0711 42.9289 - vertex -50 -72.7398 45.1315 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -50 -72.7398 45.1315 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 38.1931 66.569 - vertex -50 42.9289 57.0711 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 28.8675 75 - vertex -50 38.1931 66.569 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -72.4016 61.5374 - vertex -50 -67.3575 75 - vertex -50 -59.3991 66.7554 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -72.4016 61.5374 - vertex -50 -59.3991 66.7554 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 50 40 - vertex -50 48.1125 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -72.7398 45.1315 - vertex -50 -57.0711 42.9289 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 40 50 - vertex -50 24.777 61.2904 - vertex -50 42.9289 57.0711 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.6225 75 - vertex -50 28.8675 75 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 58.3333 - vertex -50 67.3575 75 - vertex -50 86.6025 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -50 72.7615 54.9694 - vertex -50 86.6025 58.3333 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 86.6025 58.3333 - vertex -50 72.7615 54.9694 - vertex -50 67.3575 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 72.7615 54.9694 - vertex -50 60 50 - vertex -50 57.0711 57.0711 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -50 72.9043 38.7048 - vertex -50 72.7615 54.9694 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 72.7615 54.9694 - vertex -50 57.0711 57.0711 - vertex -50 67.3575 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 72.9043 38.7048 - vertex -50 60 50 - vertex -50 72.7615 54.9694 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 25 - vertex -50 72.9043 38.7048 - vertex -50 86.6025 41.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 75 - vertex -50 57.0711 57.0711 - vertex -50 50 60 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 72.9043 38.7048 - vertex -50 57.0711 42.9289 - vertex -50 60 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 86.6025 25 - vertex -50 67.3575 25 - vertex -50 72.9043 38.7048 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.1125 75 - vertex -50 67.3575 75 - vertex -50 50 60 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 25 - vertex -50 57.0711 42.9289 - vertex -50 72.9043 38.7048 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -50 -72.4016 61.5374 - vertex -50 -72.7398 45.1315 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 48.1125 75 - vertex -50 50 60 - vertex -50 38.1931 66.569 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -50 -86.6025 75 - vertex -50 -72.4016 61.5374 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 25 - vertex -50 50 40 - vertex -50 57.0711 42.9289 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -72.4016 61.5374 - vertex -50 -60 50 - vertex -50 -72.7398 45.1315 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 25 - vertex -50 9.6225 25 - vertex -50 9.31671 41.8755 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 25 - vertex -50 -48.1125 25 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 75 - vertex -50 -9.6225 75 - vertex -50 -9.20725 58.1596 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.31671 41.8755 - vertex -50 -9.20725 58.1596 - vertex -50 7.72654 59.5349 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 57.0711 - vertex -50 -28.8675 75 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.6225 25 - vertex -50 -7.54086 40.5115 - vertex -50 9.31671 41.8755 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 25 - vertex -50 -42.9289 42.9289 - vertex -50 -24.3141 38.9123 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -28.8675 75 - vertex -50 -9.20725 58.1596 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.20725 58.1596 - vertex -50 9.31671 41.8755 - vertex -50 -7.54086 40.5115 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 57.0711 - vertex -50 -24.3431 54.6496 - vertex -50 -40 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 42.9289 - vertex -50 -40 50 - vertex -50 -24.3141 38.9123 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 9.6225 25 - vertex -50 -9.6225 25 - vertex -50 -7.54086 40.5115 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 25 - vertex -50 -28.8675 25 - vertex -50 -24.3141 38.9123 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -7.54086 40.5115 - vertex -50 -24.3431 54.6496 - vertex -50 -9.20725 58.1596 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -24.3141 38.9123 - vertex -50 -40 50 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 25 - vertex -50 -24.3141 38.9123 - vertex -50 -7.54086 40.5115 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -7.54086 40.5115 - vertex -50 -24.3141 38.9123 - vertex -50 -24.3431 54.6496 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -59.3991 66.7554 - vertex -50 -67.3575 75 - vertex -50 -48.1125 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -59.3991 66.7554 - vertex -50 -50 60 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 24.425 45.4369 - vertex -50 40 50 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 48.1125 25 - vertex -50 28.8675 25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -57.0711 42.9289 - vertex -50 -50 40 - vertex -50 -67.3575 25 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 40 50 - vertex -50 24.425 45.4369 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 9.6225 75 - vertex -50 24.777 61.2904 - vertex -50 7.72654 59.5349 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -50 60 - vertex -50 -59.3991 66.7554 - vertex -50 -48.1125 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 42.9289 42.9289 - vertex -50 28.8675 25 - vertex -50 24.425 45.4369 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -67.3575 25 - vertex -50 -50 40 - vertex -50 -48.1125 25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 24.425 45.4369 - vertex -50 7.72654 59.5349 - vertex -50 24.777 61.2904 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 75 - vertex -50 9.6225 75 - vertex -50 7.72654 59.5349 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -50 60 - vertex -50 -48.1125 75 - vertex -50 -42.9289 57.0711 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 25 - vertex -50 9.31671 41.8755 - vertex -50 24.425 45.4369 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 25 - vertex -50 -50 40 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 7.72654 59.5349 - vertex -50 24.425 45.4369 - vertex -50 9.31671 41.8755 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -9.6225 75 - vertex -50 7.72654 59.5349 - vertex -50 -9.20725 58.1596 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -42.9289 57.0711 - vertex -50 -48.1125 75 - vertex -50 -28.8675 75 - endloop - endfacet -endsolid patch002 -solid patch003 - facet normal -0 0 -1 - outer loop - vertex -79.8138 -27.1233 -25 - vertex -93.9693 -34.202 -25 - vertex -87.1351 -19.2209 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -87.1351 -19.2209 -25 - vertex -75 -10 -25 - vertex -79.8138 -27.1233 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -75 -10 -25 - vertex -67.9289 -7.07107 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.1672 -27.2873 -25 - vertex -58.8409 -18.1346 -25 - vertex -50 -28.8675 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -87.1351 -19.2209 -25 - vertex -93.9693 -34.202 -25 - vertex -98.4808 -17.3648 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -75 -10 -25 - vertex -87.1351 -19.2209 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.9289 -7.07107 -25 - vertex -58.8409 -18.1346 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -28.8675 -25 - vertex -58.8409 -18.1346 -25 - vertex -50 -9.6225 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -87.1351 -19.2209 -25 - vertex -98.4808 -17.3648 -25 - vertex -91.5168 -8.74011 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -87.1351 -19.2209 -25 - vertex -91.5168 -8.74011 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.9289 -7.07107 -25 - vertex -50 -9.6225 -25 - vertex -58.8409 -18.1346 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -91.5168 -8.74011 -25 - vertex -98.4808 -17.3648 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -91.5168 -8.74011 -25 - vertex -85 0 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -65 0 -25 - vertex -50 -9.6225 -25 - vertex -67.9289 -7.07107 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.1672 -27.2873 -25 - vertex -50 -28.8675 -25 - vertex -63.9539 -44.7004 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -79.8138 -27.1233 -25 - vertex -75 -10 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 -34.202 -25 - vertex -79.8138 -27.1233 -25 - vertex -77.4794 -42.1095 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -77.4794 -42.1095 -25 - vertex -67.1672 -27.2873 -25 - vertex -63.9539 -44.7004 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -63.9539 -44.7004 -25 - vertex -50 -28.8675 -25 - vertex -50 -48.1125 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -77.4794 -42.1095 -25 - vertex -79.8138 -27.1233 -25 - vertex -67.1672 -27.2873 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -86.6025 -50 -25 - vertex -93.9693 -34.202 -25 - vertex -77.4794 -42.1095 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -63.9539 -44.7004 -25 - vertex -76.6044 -64.2788 -25 - vertex -77.4794 -42.1095 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -61.418 -60.2423 -25 - vertex -63.9539 -44.7004 -25 - vertex -50 -48.1125 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -86.6025 -50 -25 - vertex -77.4794 -42.1095 -25 - vertex -76.6044 -64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -76.6044 -64.2788 -25 - vertex -63.9539 -44.7004 -25 - vertex -61.418 -60.2423 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -61.418 -60.2423 -25 - vertex -50 -48.1125 -25 - vertex -50 -67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -76.6044 -64.2788 -25 - vertex -61.418 -60.2423 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -61.418 -60.2423 -25 - vertex -50 -67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -86.6025 -25 - vertex -64.2788 -76.6044 -25 - vertex -50 -67.3575 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -63.77 35.8952 -25 - vertex -78.1277 25.7829 -25 - vertex -77.6899 42.7319 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -78.1277 25.7829 -25 - vertex -63.77 35.8952 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -77.6899 42.7319 -25 - vertex -78.1277 25.7829 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -66.0782 50.3346 -25 - vertex -63.77 35.8952 -25 - vertex -77.6899 42.7319 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -63.1721 20.406 -25 - vertex -75 10 -25 - vertex -78.1277 25.7829 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -50 28.8675 -25 - vertex -63.1721 20.406 -25 - vertex -63.77 35.8952 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -86.6025 50 -25 - vertex -77.6899 42.7319 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -78.1277 25.7829 -25 - vertex -89.7207 15.4527 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -50 48.1125 -25 - vertex -63.77 35.8952 -25 - vertex -66.0782 50.3346 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -66.0782 50.3346 -25 - vertex -77.6899 42.7319 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -67.9289 7.07107 -25 - vertex -75 10 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -75 10 -25 - vertex -82.0711 7.07107 -25 - vertex -78.1277 25.7829 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -50 28.8675 -25 - vertex -50 9.6225 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -50 48.1125 -25 - vertex -50 28.8675 -25 - vertex -63.77 35.8952 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -77.6899 42.7319 -25 - vertex -86.6025 50 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 76.6044 -25 - vertex -50 86.6025 -25 - vertex -50 67.3575 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -85 0 -25 - vertex -91.5168 -8.74011 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -65 0 -25 - vertex -50 9.6225 -25 - vertex -50 -9.6225 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -64.2788 76.6044 -25 - vertex -50 67.3575 -25 - vertex -61.3177 61.5263 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -89.7207 15.4527 -25 - vertex -85 0 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -65 0 -25 - vertex -67.9289 7.07107 -25 - vertex -50 9.6225 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -64.2788 76.6044 -25 - vertex -61.3177 61.5263 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -50 67.3575 -25 - vertex -50 48.1125 -25 - vertex -61.3177 61.5263 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -98.4808 17.3648 -25 - vertex -89.7207 15.4527 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -82.0711 7.07107 -25 - vertex -85 0 -25 - vertex -89.7207 15.4527 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -50 9.6225 -25 - vertex -67.9289 7.07107 -25 - vertex -63.1721 20.406 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -61.3177 61.5263 -25 - vertex -66.0782 50.3346 -25 - vertex -76.6044 64.2788 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -61.3177 61.5263 -25 - vertex -50 48.1125 -25 - vertex -66.0782 50.3346 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -93.9693 34.202 -25 - vertex -89.7207 15.4527 -25 - vertex -98.4808 17.3648 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -78.1277 25.7829 -25 - vertex -82.0711 7.07107 -25 - vertex -89.7207 15.4527 -25 - endloop - endfacet -endsolid patch003 -solid patch004 - facet normal -0.95892 -0.280658 0.0412783 - outer loop - vertex 33.5378 16.777 61.0519 - vertex 37.3559 3.28438 58.0102 - vertex 36.3417 9.24839 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 76.0222 15.0039 - vertex 20 97.9796 16.6667 - vertex 20 81.4151 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 62.8929 25.7602 - vertex 20 60.6066 39.3934 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 79.2233 32.1829 - vertex 20 97.9796 16.6667 - vertex 20 76.0222 15.0039 - endloop - endfacet - facet normal -0.569566 -0.821946 0 - outer loop - vertex 22.6774 29.8661 50 - vertex 20 31.7214 50 - vertex 20 31.7214 33.3333 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 25.4951 62.5 - vertex 27.5 35 50 - vertex 27.5 25.4951 50 - endloop - endfacet - facet normal -0.822095 -0.56935 0 - outer loop - vertex 27.5 25.4951 62.5 - vertex 33.5378 16.777 61.0519 - vertex 27.5 25.4951 75 - endloop - endfacet - facet normal 0.875444 0.47643 -0.0813186 - outer loop - vertex -36.3417 -9.24839 75 - vertex -27.5 -25.4951 75 - vertex -33.5351 -16.7824 61.0745 - endloop - endfacet - facet normal 0.82205 0.569416 0 - outer loop - vertex -27.5 -25.4951 62.5 - vertex -27.5 -25.4951 50 - vertex -33.5351 -16.7824 61.0745 - endloop - endfacet - facet normal 0.638663 0.7693 0.0169606 - outer loop - vertex -22.6774 -29.8661 50 - vertex -20 -31.7214 33.3333 - vertex -25.1837 -27.7854 50 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -40 50 - vertex -20 -42.9289 42.9289 - vertex -20 -31.7214 50 - endloop - endfacet - facet normal -0.638663 0.7693 0.0169606 - outer loop - vertex 20 -31.7214 33.3333 - vertex 22.6774 -29.8661 50 - vertex 25.1837 -27.7854 50 - endloop - endfacet - facet normal -0.99382 0.108984 0.0210676 - outer loop - vertex 35.6194 -11.7263 53.7453 - vertex 36.3417 -9.24839 75 - vertex 37.3559 3.28438 58.0102 - endloop - endfacet - facet normal -0.861384 0.507954 0 - outer loop - vertex 27.5 -25.4951 50 - vertex 27.5 -25.4951 62.5 - vertex 35.6194 -11.7263 53.7453 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -39.3934 39.3934 - vertex 20 -31.7214 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -43.758 25.2531 - vertex 20 -50 35 - vertex 20 -39.3934 39.3934 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -64.8505 0 - vertex 20 -49.8517 11.8026 - vertex 20 -48.286 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -49.8517 11.8026 - vertex 20 -59.5852 25.5168 - vertex 20 -43.758 25.2531 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 97.9796 50 - vertex -20 78.9898 50 - vertex -20 97.9796 33.3333 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -27.5 50 60 - vertex -27.5 38.8384 66.7925 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 25.4951 62.5 - vertex -27.5 38.8384 66.7925 - vertex -27.5 25.4951 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -57.6764 13.4257 - vertex -20 -75.6829 15.1229 - vertex -20 -64.8505 0 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -62.1725 27.2886 - vertex -20 -57.0711 42.9289 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 0.569566 0.821946 0 - outer loop - vertex -22.6774 -29.8661 50 - vertex -20 -31.7214 50 - vertex -20 -31.7214 33.3333 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -25.4951 50 - vertex -27.5 -25.4951 62.5 - endloop - endfacet - facet normal 0.82205 0.569416 -0 - outer loop - vertex -27.5 -25.4951 62.5 - vertex -33.5351 -16.7824 61.0745 - vertex -27.5 -25.4951 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 25.4951 75 - vertex 27.5 36.1733 68.1145 - vertex 27.5 25.4951 62.5 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 39.3934 60.6066 - vertex 27.5 35 50 - vertex 27.5 25.4951 62.5 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 97.9796 33.3333 - vertex 20 97.9796 16.6667 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 60.6066 39.3934 - vertex 20 65 50 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 97.9796 16.6667 - vertex 20 97.9796 0 - vertex 20 81.4151 0 - endloop - endfacet - facet normal -0.875454 -0.476435 -0.0811729 - outer loop - vertex 33.5378 16.777 61.0519 - vertex 36.3417 9.24839 75 - vertex 27.5 25.4951 75 - endloop - endfacet - facet normal -0.569566 0.821946 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -31.7214 50 - vertex 22.6774 -29.8661 50 - endloop - endfacet - facet normal -0.998223 0 -0.0595885 - outer loop - vertex 37.3559 3.28438 58.0102 - vertex 36.3417 -9.24839 75 - vertex 36.3417 9.24839 75 - endloop - endfacet - facet normal -0.868764 0.494428 -0.0281179 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 36.3417 -9.24839 75 - vertex 35.6194 -11.7263 53.7453 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -25.4951 50 - vertex 27.5 -35 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -39.3934 39.3934 - vertex 20 -35 50 - vertex 20 -31.7214 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -64.8505 0 - vertex 20 -69.4506 14.8283 - vertex 20 -49.8517 11.8026 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -59.5852 25.5168 - vertex 20 -50 35 - vertex 20 -43.758 25.2531 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -59.5852 25.5168 - vertex 20 -49.8517 11.8026 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 50 60 - vertex -27.5 55.2476 66.9116 - vertex -27.5 38.8384 66.7925 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 38.8384 66.7925 - vertex -27.5 43.1574 75 - vertex -27.5 25.4951 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -64.8505 0 - vertex -20 -75.6829 15.1229 - vertex -20 -81.4151 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -62.1725 27.2886 - vertex -20 -78.8495 31.6006 - vertex -20 -75.6829 15.1229 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -50 40 - vertex -20 -57.0711 42.9289 - vertex -20 -62.1725 27.2886 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 97.9796 16.6667 - vertex -20 97.9796 33.3333 - vertex -20 83.9674 19.9229 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 81.4151 0 - vertex -20 97.9796 0 - vertex -20 97.9796 16.6667 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -27.5 38.8384 66.7925 - vertex -27.5 25.4951 62.5 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 25.4951 50 - vertex -27.5 40 50 - vertex -27.5 42.9289 57.0711 - endloop - endfacet - facet normal 0.878353 -0.478013 0 - outer loop - vertex -27.5 25.4951 62.5 - vertex -27.5 25.4951 75 - vertex -36.3417 9.24839 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -48.286 0 - vertex -20 -57.6764 13.4257 - vertex -20 -64.8505 0 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -57.6764 13.4257 - vertex -20 -45.6982 25.7885 - vertex -20 -62.1725 27.2886 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -45.6982 25.7885 - vertex -20 -31.7214 33.3333 - vertex -20 -42.9289 42.9289 - endloop - endfacet - facet normal 0.771236 0.626434 0.113034 - outer loop - vertex -33.3967 -17.056 43.464 - vertex -27.5 -25.4951 50 - vertex -20 -31.7214 33.3333 - endloop - endfacet - facet normal 0.962002 0.273023 0.00331845 - outer loop - vertex -37.3561 -3.2825 58.0705 - vertex -33.5351 -16.7824 61.0745 - vertex -33.3967 -17.056 43.464 - endloop - endfacet - facet normal 0.993785 -0.109255 0.0213217 - outer loop - vertex -35.6139 11.743 53.8604 - vertex -36.3417 9.24839 75 - vertex -37.3561 -3.2825 58.0705 - endloop - endfacet - facet normal -0.820598 -0.5715 -0.0025142 - outer loop - vertex 27.5 25.4951 50 - vertex 33.3945 17.0604 43.4034 - vertex 33.5378 16.777 61.0519 - endloop - endfacet - facet normal -0.702201 -0.710172 0.0506857 - outer loop - vertex 20 31.7214 33.3333 - vertex 27.5 25.4951 50 - vertex 25.1837 27.7854 50 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 76.0222 15.0039 - vertex 20 57.8078 12.7685 - vertex 20 62.8929 25.7602 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 50 35 - vertex 20 62.8929 25.7602 - vertex 20 45.5064 24.0211 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 50 35 - vertex 20 45.5064 24.0211 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 39.3934 39.3934 - vertex 20 31.7214 33.3333 - vertex 20 31.7214 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 57.8078 12.7685 - vertex 20 76.0222 15.0039 - vertex 20 64.8505 0 - endloop - endfacet - facet normal -0.964297 -0.26455 0.0120159 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 37.4402 2.11676 39.0684 - vertex 37.3559 3.28438 58.0102 - endloop - endfacet - facet normal -0.757813 0.644739 0.100155 - outer loop - vertex 20 -31.7214 33.3333 - vertex 27.5 -25.4951 50 - vertex 34.274 -15.2166 35.0879 - endloop - endfacet - facet normal -0.984519 0.170875 0.0390285 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 35.6194 -11.7263 53.7453 - vertex 37.4402 2.11676 39.0684 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -31.7214 16.6667 - vertex 20 -43.758 25.2531 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -75.6829 15.1229 - vertex -20 -57.6764 13.4257 - vertex -20 -62.1725 27.2886 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -50 40 - vertex -20 -62.1725 27.2886 - vertex -20 -45.6982 25.7885 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -42.9289 42.9289 - vertex -20 -31.7214 33.3333 - vertex -20 -31.7214 50 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -50 40 - vertex -20 -45.6982 25.7885 - vertex -20 -42.9289 42.9289 - endloop - endfacet - facet normal 0.702201 0.710172 0.0506857 - outer loop - vertex -20 -31.7214 33.3333 - vertex -27.5 -25.4951 50 - vertex -25.1837 -27.7854 50 - endloop - endfacet - facet normal 0.820599 0.5715 -0.00243 - outer loop - vertex -27.5 -25.4951 50 - vertex -33.3967 -17.056 43.464 - vertex -33.5351 -16.7824 61.0745 - endloop - endfacet - facet normal 0.95892 0.280632 0.0414363 - outer loop - vertex -33.5351 -16.7824 61.0745 - vertex -37.3561 -3.2825 58.0705 - vertex -36.3417 -9.24839 75 - endloop - endfacet - facet normal 0.99821 0 -0.0598116 - outer loop - vertex -37.3561 -3.2825 58.0705 - vertex -36.3417 9.24839 75 - vertex -36.3417 -9.24839 75 - endloop - endfacet - facet normal -0.822095 -0.56935 -0 - outer loop - vertex 27.5 25.4951 62.5 - vertex 27.5 25.4951 50 - vertex 33.5378 16.777 61.0519 - endloop - endfacet - facet normal -0.638663 -0.7693 0.0169606 - outer loop - vertex 22.6774 29.8661 50 - vertex 20 31.7214 33.3333 - vertex 25.1837 27.7854 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 62.8929 25.7602 - vertex 20 79.2233 32.1829 - vertex 20 76.0222 15.0039 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 50 35 - vertex 20 60.6066 39.3934 - vertex 20 62.8929 25.7602 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex 20 35 50 - vertex 20 39.3934 39.3934 - vertex 20 31.7214 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 64.8505 0 - vertex 20 76.0222 15.0039 - vertex 20 81.4151 0 - endloop - endfacet - facet normal -0.962008 -0.272999 0.00342733 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 37.3559 3.28438 58.0102 - vertex 33.5378 16.777 61.0519 - endloop - endfacet - facet normal -0.702201 0.710172 0.0506857 - outer loop - vertex 20 -31.7214 33.3333 - vertex 25.1837 -27.7854 50 - vertex 27.5 -25.4951 50 - endloop - endfacet - facet normal -0.992922 0.118191 -0.0117046 - outer loop - vertex 37.4402 2.11676 39.0684 - vertex 35.6194 -11.7263 53.7453 - vertex 37.3559 3.28438 58.0102 - endloop - endfacet - facet normal -0.856739 0.514596 -0.0344869 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 27.5 -25.4951 50 - vertex 35.6194 -11.7263 53.7453 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 20 -43.758 25.2531 - vertex 20 -39.3934 39.3934 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -49.8517 11.8026 - vertex 20 -31.7214 0 - vertex 20 -48.286 0 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -43.758 25.2531 - vertex 20 -31.7214 16.6667 - vertex 20 -49.8517 11.8026 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 78.9898 50 - vertex -20 60 50 - vertex -20 74.5519 34.028 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 97.9796 33.3333 - vertex -20 78.9898 50 - vertex -20 74.5519 34.028 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 60.6066 60.6066 - vertex 27.5 66.2171 67.7504 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 66.2171 67.7504 - vertex 27.5 78.4821 75 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -66.2171 67.7504 - vertex 27.5 -60.8198 75 - vertex 27.5 -50 65 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 96.1444 75 - vertex -27.5 78.4821 75 - vertex -27.5 96.1444 62.5 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -73.4553 63.5117 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -55.2476 66.9116 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -73.4553 63.5117 - vertex -27.5 -55.2476 66.9116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 66.2171 67.7504 - vertex 27.5 60.6066 60.6066 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 60.8198 75 - vertex 27.5 78.4821 75 - vertex 27.5 66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -50 65 - vertex 27.5 -60.8198 75 - vertex 27.5 -43.1574 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -97.9796 50 - vertex 20 -81.4898 50 - vertex 20 -97.9796 33.3333 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 96.1444 50 - vertex -27.5 96.1444 62.5 - vertex -27.5 78.0722 50 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 96.1444 62.5 - vertex -27.5 78.4821 75 - vertex -27.5 73.4553 63.5117 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -50 60 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -43.1574 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 60.8198 75 - vertex 27.5 66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -50 65 - vertex 27.5 -43.1574 75 - vertex 27.5 -36.1733 68.1145 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -97.9796 0 - vertex 20 -97.9796 16.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -97.9796 16.6667 - vertex 20 -97.9796 33.3333 - vertex 20 -84.3761 19.6041 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -97.9796 33.3333 - vertex 20 -81.4898 50 - vertex 20 -76.0618 33.425 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4898 50 - vertex 20 -65 50 - vertex 20 -76.0618 33.425 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 78.0722 50 - vertex -27.5 96.1444 62.5 - vertex -27.5 73.4553 63.5117 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 60 50 - vertex -27.5 78.0722 50 - vertex -27.5 57.0711 57.0711 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -96.1444 50 - vertex 27.5 -96.1444 62.5 - vertex 27.5 -80.5722 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -65 50 - vertex 27.5 -80.5722 50 - vertex 27.5 -76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -80.5722 50 - vertex 27.5 -96.1444 62.5 - vertex 27.5 -76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -96.1444 75 - vertex 27.5 -78.4821 75 - vertex 27.5 -96.1444 62.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 96.1444 50 - vertex 27.5 80.5722 50 - vertex 27.5 96.1444 62.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -65 50 - vertex 27.5 -76.8004 61.1116 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -96.1444 62.5 - vertex 27.5 -78.4821 75 - vertex 27.5 -76.8004 61.1116 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -96.1444 50 - vertex -27.5 -78.0722 50 - vertex -27.5 -96.1444 62.5 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -96.1444 75 - vertex -27.5 -96.1444 62.5 - vertex -27.5 -78.4821 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 80.5722 50 - vertex 27.5 65 50 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 96.1444 62.5 - vertex 27.5 80.5722 50 - vertex 27.5 76.8004 61.1116 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex 27.5 96.1444 75 - vertex 27.5 96.1444 62.5 - vertex 27.5 78.4821 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -60.6066 60.6066 - vertex 27.5 -76.8004 61.1116 - vertex 27.5 -66.2171 67.7504 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -76.8004 61.1116 - vertex 27.5 -78.4821 75 - vertex 27.5 -66.2171 67.7504 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -96.1444 62.5 - vertex -27.5 -78.0722 50 - vertex -27.5 -73.4553 63.5117 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -60 50 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -78.0722 50 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -96.1444 62.5 - vertex -27.5 -73.4553 63.5117 - vertex -27.5 -78.4821 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 60.6066 60.6066 - vertex 27.5 76.8004 61.1116 - vertex 27.5 65 50 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 96.1444 62.5 - vertex 27.5 76.8004 61.1116 - vertex 27.5 78.4821 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -60.6066 60.6066 - vertex 27.5 -66.2171 67.7504 - vertex 27.5 -50 65 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -78.4821 75 - vertex 27.5 -60.8198 75 - vertex 27.5 -66.2171 67.7504 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -78.0722 50 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -73.4553 63.5117 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -78.4821 75 - vertex -27.5 -73.4553 63.5117 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -76.0618 33.425 - vertex 20 -60.6066 39.3934 - vertex 20 -59.5852 25.5168 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 57.0711 57.0711 - vertex -27.5 73.4553 63.5117 - vertex -27.5 55.2476 66.9116 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 55.2476 66.9116 - vertex -27.5 60.8198 75 - vertex -27.5 43.1574 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -97.9796 16.6667 - vertex -20 -97.9796 0 - vertex -20 -81.4151 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -78.8495 31.6006 - vertex -20 -97.9796 33.3333 - vertex -20 -97.9796 16.6667 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -57.0711 42.9289 - vertex -20 -78.9898 50 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -25.4951 62.5 - vertex -27.5 -38.8384 66.7925 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -40 50 - vertex -27.5 -25.4951 50 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -25.4951 62.5 - vertex -27.5 -25.4951 75 - vertex -27.5 -38.8384 66.7925 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 25.4951 75 - vertex 27.5 43.1574 75 - vertex 27.5 36.1733 68.1145 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 27.5 36.1733 68.1145 - vertex 27.5 39.3934 60.6066 - vertex 27.5 25.4951 62.5 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 81.4898 50 - vertex 20 97.9796 33.3333 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 65 50 - vertex 20 81.4898 50 - vertex 20 79.2233 32.1829 - endloop - endfacet - facet normal -0.878353 0.478013 0 - outer loop - vertex 27.5 -25.4951 75 - vertex 36.3417 -9.24839 75 - vertex 27.5 -25.4951 62.5 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -35 50 - vertex 27.5 -39.3934 60.6066 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -69.4506 14.8283 - vertex 20 -64.8505 0 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -59.5852 25.5168 - vertex 20 -60.6066 39.3934 - vertex 20 -50 35 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -76.0618 33.425 - vertex 20 -59.5852 25.5168 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 50 60 - vertex -27.5 57.0711 57.0711 - vertex -27.5 55.2476 66.9116 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 55.2476 66.9116 - vertex -27.5 43.1574 75 - vertex -27.5 38.8384 66.7925 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -75.6829 15.1229 - vertex -20 -97.9796 16.6667 - vertex -20 -81.4151 0 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -97.9796 16.6667 - vertex -20 -75.6829 15.1229 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 73.4553 63.5117 - vertex -27.5 78.4821 75 - vertex -27.5 60.8198 75 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -97.9796 50 - vertex -20 -97.9796 33.3333 - vertex -20 -78.9898 50 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -50 60 - vertex -27.5 -38.8384 66.7925 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 -55.2476 66.9116 - vertex -27.5 -38.8384 66.7925 - vertex -27.5 -43.1574 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 43.1574 75 - vertex 27.5 60.8198 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -36.1733 68.1145 - vertex 27.5 -43.1574 75 - vertex 27.5 -25.4951 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -39.3934 60.6066 - vertex 27.5 -50 65 - vertex 27.5 -36.1733 68.1145 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -97.9796 16.6667 - vertex 20 -84.3761 19.6041 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -84.3761 19.6041 - vertex 20 -97.9796 33.3333 - vertex 20 -76.0618 33.425 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -76.0618 33.425 - vertex 20 -65 50 - vertex 20 -60.6066 39.3934 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -27.5 57.0711 57.0711 - vertex -27.5 78.0722 50 - vertex -27.5 73.4553 63.5117 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 73.4553 63.5117 - vertex -27.5 60.8198 75 - vertex -27.5 55.2476 66.9116 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -60 50 - vertex -20 -78.9898 50 - vertex -20 -57.0711 42.9289 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -78.9898 50 - vertex -20 -97.9796 33.3333 - vertex -20 -78.8495 31.6006 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -38.8384 66.7925 - vertex -27.5 -50 60 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -27.5 -38.8384 66.7925 - vertex -27.5 -25.4951 75 - vertex -27.5 -43.1574 75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 36.1733 68.1145 - vertex 27.5 43.1574 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 50 65 - vertex 27.5 39.3934 60.6066 - vertex 27.5 36.1733 68.1145 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex 20 97.9796 50 - vertex 20 97.9796 33.3333 - vertex 20 81.4898 50 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -36.1733 68.1145 - vertex 27.5 -25.4951 75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 27.5 -25.4951 62.5 - vertex 27.5 -39.3934 60.6066 - vertex 27.5 -36.1733 68.1145 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -81.4151 0 - vertex 20 -84.3761 19.6041 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 -84.3761 19.6041 - vertex 20 -76.0618 33.425 - vertex 20 -69.4506 14.8283 - endloop - endfacet - facet normal -0.964392 -0.258406 0.0563422 - outer loop - vertex 34.9655 13.5522 -56.227 - vertex 32.476 18.75 -75 - vertex 37.5 0 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 43.9211 27.0189 - vertex -20 31.7214 16.6667 - vertex -20 49.7152 12.4405 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 49.7152 12.4405 - vertex -20 31.7214 0 - vertex -20 48.286 0 - endloop - endfacet - facet normal 0.739817 -0.672808 0 - outer loop - vertex -20 31.7214 16.6667 - vertex -20 31.7214 33.3333 - vertex -33.4723 16.9073 18.2472 - endloop - endfacet - facet normal 0.470975 0.880836 -0.0480593 - outer loop - vertex -18.75 -32.476 -75 - vertex -25.0898 -27.8703 -52.7154 - vertex -9.77074 -36.2047 -55.3444 - endloop - endfacet - facet normal 0.483316 0.874313 0.044533 - outer loop - vertex -21.223 -30.9166 -34.874 - vertex -9.77074 -36.2047 -55.3444 - vertex -25.0898 -27.8703 -52.7154 - endloop - endfacet - facet normal 0.953517 0.299892 0.0294956 - outer loop - vertex -37.4323 -2.25275 2.36658 - vertex -32.3394 -18.9845 7.84387 - vertex -30.9723 -21.1416 -14.419 - endloop - endfacet - facet normal 0.605899 0.790548 -0.0890009 - outer loop - vertex -13.4703 -34.9972 -18.3411 - vertex -21.223 -30.9166 -34.874 - vertex -30.9723 -21.1416 -14.419 - endloop - endfacet - facet normal 0.978844 -0.204592 0.002756 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -37.4323 -2.25275 2.36658 - vertex -33.3888 17.0715 0.780048 - endloop - endfacet - facet normal -0.702047 -0.711131 -0.0377326 - outer loop - vertex 20 31.7214 0 - vertex 29.4828 23.1736 -15.3386 - vertex 32.1117 19.3672 7.48614 - endloop - endfacet - facet normal -0.929992 -0.365356 -0.0403803 - outer loop - vertex 29.4828 23.1736 -15.3386 - vertex 31.5798 20.2229 -36.9367 - vertex 37.3331 3.53357 -18.437 - endloop - endfacet - facet normal -0.958709 -0.274796 -0.0732401 - outer loop - vertex 31.5798 20.2229 -36.9367 - vertex 34.9655 13.5522 -56.227 - vertex 37.4996 -0.172499 -37.9034 - endloop - endfacet - facet normal -0.76613 -0.638279 -0.0751275 - outer loop - vertex 19.8668 31.805 -57.3293 - vertex 32.476 18.75 -75 - vertex 34.9655 13.5522 -56.227 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 31.7214 16.6667 - vertex -20 31.7214 0 - vertex -20 49.7152 12.4405 - endloop - endfacet - facet normal 0.739666 -0.672968 -0.00279033 - outer loop - vertex -20 31.7214 16.6667 - vertex -33.4723 16.9073 18.2472 - vertex -33.3888 17.0715 0.780048 - endloop - endfacet - facet normal 0.769168 0.632958 0.088005 - outer loop - vertex -25.0898 -27.8703 -52.7154 - vertex -18.75 -32.476 -75 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.771631 0.633319 -0.0591021 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -21.223 -30.9166 -34.874 - vertex -25.0898 -27.8703 -52.7154 - endloop - endfacet - facet normal 0.94925 0.314307 0.0116323 - outer loop - vertex -30.9723 -21.1416 -14.419 - vertex -37.4717 -1.45742 -15.9083 - vertex -37.4323 -2.25275 2.36658 - endloop - endfacet - facet normal 0.765996 0.640114 0.0591943 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -30.9723 -21.1416 -14.419 - vertex -21.223 -30.9166 -34.874 - endloop - endfacet - facet normal 0.97856 -0.205667 -0.0110603 - outer loop - vertex -37.4323 -2.25275 2.36658 - vertex -37.4717 -1.45742 -15.9083 - vertex -33.3888 17.0715 0.780048 - endloop - endfacet - facet normal -0.57608 -0.811713 0.0961956 - outer loop - vertex 29.4828 23.1736 -15.3386 - vertex 20 31.7214 0 - vertex 11.0649 35.8304 -18.8367 - endloop - endfacet - facet normal -0.660661 -0.749708 0.0382792 - outer loop - vertex 29.4828 23.1736 -15.3386 - vertex 16.1087 33.8639 -36.7898 - vertex 31.5798 20.2229 -36.9367 - endloop - endfacet - facet normal -0.717291 -0.696718 -0.00873804 - outer loop - vertex 20 31.7214 16.6667 - vertex 32.1117 19.3672 7.48614 - vertex 32.4669 18.7657 26.2883 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 42.9891 10.7098 - vertex 20 31.7214 0 - vertex 20 31.7214 16.6667 - endloop - endfacet - facet normal -0.952482 -0.304182 -0.0158508 - outer loop - vertex 37.4483 1.96876 20.689 - vertex 32.1117 19.3672 7.48614 - vertex 37.3569 3.2728 1.15635 - endloop - endfacet - facet normal -0.983759 0.179457 0.00358338 - outer loop - vertex 37.3569 3.2728 1.15635 - vertex 37.3331 3.53357 -18.437 - vertex 33.7839 -16.2758 -0.75261 - endloop - endfacet - facet normal -0.982543 0.18103 -0.042869 - outer loop - vertex 37.3331 3.53357 -18.437 - vertex 37.4996 -0.172499 -37.9034 - vertex 33.6967 -16.4554 -19.5029 - endloop - endfacet - facet normal -0.9586 0.27593 -0.0703473 - outer loop - vertex 37.4996 -0.172499 -37.9034 - vertex 36.6441 -7.96625 -56.816 - vertex 32.0358 -19.4924 -39.2304 - endloop - endfacet - facet normal -0.993959 -0.0753521 -0.0797956 - outer loop - vertex 34.9655 13.5522 -56.227 - vertex 37.5 0 -75 - vertex 36.6441 -7.96625 -56.816 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 49.7152 12.4405 - vertex -20 58.6722 27.2612 - vertex -20 43.9211 27.0189 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 64.8505 0 - vertex -20 49.7152 12.4405 - vertex -20 48.286 0 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 31.7214 33.3333 - vertex -20 31.7214 16.6667 - vertex -20 43.9211 27.0189 - endloop - endfacet - facet normal 0.753546 -0.6568 -0.0279797 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -20 31.7214 33.3333 - vertex -34.2369 15.2998 35.3898 - endloop - endfacet - facet normal 0.258272 0.963892 0.0648658 - outer loop - vertex -9.77074 -36.2047 -55.3444 - vertex 0 -37.5 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal 0.311959 0.947496 -0.070239 - outer loop - vertex -1.8284 -37.4554 -36.9408 - vertex -9.77074 -36.2047 -55.3444 - vertex -21.223 -30.9166 -34.874 - endloop - endfacet - facet normal 0.710419 0.703351 -0.0245244 - outer loop - vertex -20 -31.7214 0 - vertex -30.9723 -21.1416 -14.419 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.957269 0.289118 -0.00690645 - outer loop - vertex -37.4323 -2.25275 2.36658 - vertex -37.4611 -1.70839 21.1626 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.630222 0.771575 0.0865614 - outer loop - vertex -30.9723 -21.1416 -14.419 - vertex -20 -31.7214 0 - vertex -13.4703 -34.9972 -18.3411 - endloop - endfacet - facet normal 0.326069 0.941989 0.0795966 - outer loop - vertex -13.4703 -34.9972 -18.3411 - vertex -1.8284 -37.4554 -36.9408 - vertex -21.223 -30.9166 -34.874 - endloop - endfacet - facet normal 0.978019 -0.208381 0.00753363 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -37.4611 -1.70839 21.1626 - vertex -37.4323 -2.25275 2.36658 - endloop - endfacet - facet normal -0.71408 -0.700064 -0 - outer loop - vertex 20 31.7214 16.6667 - vertex 20 31.7214 0 - vertex 32.1117 19.3672 7.48614 - endloop - endfacet - facet normal -0.942973 -0.328487 0.0538287 - outer loop - vertex 37.3569 3.2728 1.15635 - vertex 32.1117 19.3672 7.48614 - vertex 29.4828 23.1736 -15.3386 - endloop - endfacet - facet normal -0.92877 -0.370638 -0.00380469 - outer loop - vertex 37.3331 3.53357 -18.437 - vertex 37.3569 3.2728 1.15635 - vertex 29.4828 23.1736 -15.3386 - endloop - endfacet - facet normal -0.958808 -0.280438 0.0451896 - outer loop - vertex 37.3331 3.53357 -18.437 - vertex 31.5798 20.2229 -36.9367 - vertex 37.4996 -0.172499 -37.9034 - endloop - endfacet - facet normal -0.993784 -0.0796515 0.077777 - outer loop - vertex 37.4996 -0.172499 -37.9034 - vertex 34.9655 13.5522 -56.227 - vertex 36.6441 -7.96625 -56.816 - endloop - endfacet - facet normal 0.443371 -0.895308 0.042957 - outer loop - vertex -20 31.7214 0 - vertex -24.242 28.6108 -21.0482 - vertex -8.64115 36.4908 -17.8341 - endloop - endfacet - facet normal 0.766101 -0.63993 -0.0598262 - outer loop - vertex -20 31.7214 0 - vertex -33.1556 17.5202 -16.5603 - vertex -24.242 28.6108 -21.0482 - endloop - endfacet - facet normal 0.975603 0.219488 -0.00487014 - outer loop - vertex -37.5 0 -75 - vertex -37.4964 0.521254 -50.7867 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.985003 0.169336 -0.0330777 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -34.3296 -15.0907 -36.4073 - vertex -37.4964 0.521254 -50.7867 - endloop - endfacet - facet normal 0.959118 -0.283003 -0.00141828 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -33.2228 17.3925 -36.523 - vertex -33.1556 17.5202 -16.5603 - endloop - endfacet - facet normal -0.0358883 -0.998208 -0.0478759 - outer loop - vertex -8.64115 36.4908 -17.8341 - vertex -4.28242 37.2547 -37.0287 - vertex 11.0649 35.8304 -18.8367 - endloop - endfacet - facet normal -0.163515 -0.985876 -0.0362231 - outer loop - vertex -4.28242 37.2547 -37.0287 - vertex -1.45427 37.4718 -55.7041 - vertex 16.1087 33.8639 -36.7898 - endloop - endfacet - facet normal 0.29998 -0.953693 -0.0219689 - outer loop - vertex -20.2142 31.5854 -56.3313 - vertex -18.75 32.476 -75 - vertex -1.45427 37.4718 -55.7041 - endloop - endfacet - facet normal 0.45613 -0.889272 -0.0337744 - outer loop - vertex -24.242 28.6108 -21.0482 - vertex -21.8234 30.4957 -38.0135 - vertex -8.64115 36.4908 -17.8341 - endloop - endfacet - facet normal 0.779729 -0.626116 0.00138047 - outer loop - vertex -33.1556 17.5202 -16.5603 - vertex -33.2228 17.3925 -36.523 - vertex -24.242 28.6108 -21.0482 - endloop - endfacet - facet normal 0.969802 -0.24384 0.00510505 - outer loop - vertex -37.4964 0.521254 -50.7867 - vertex -37.5 0 -75 - vertex -33.2312 17.3763 -55.9708 - endloop - endfacet - facet normal 0.961823 -0.271659 0.0331462 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -37.4964 0.521254 -50.7867 - vertex -33.2228 17.3925 -36.523 - endloop - endfacet - facet normal 0.35706 -0.933047 0.0439485 - outer loop - vertex -8.64115 36.4908 -17.8341 - vertex -21.8234 30.4957 -38.0135 - vertex -4.28242 37.2547 -37.0287 - endloop - endfacet - facet normal 0.298173 -0.953904 0.0340653 - outer loop - vertex -1.45427 37.4718 -55.7041 - vertex -4.28242 37.2547 -37.0287 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal 0.96574 -0.258767 0.0196466 - outer loop - vertex -32.476 18.75 -75 - vertex -33.2312 17.3763 -55.9708 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0.70694 -0.70694 0.0217208 - outer loop - vertex -32.476 18.75 -75 - vertex -18.75 32.476 -75 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal 0.755964 -0.653669 0.0351467 - outer loop - vertex -24.242 28.6108 -21.0482 - vertex -33.2228 17.3925 -36.523 - vertex -21.8234 30.4957 -38.0135 - endloop - endfacet - facet normal 0.969427 -0.245381 -0.000214327 - outer loop - vertex -33.2228 17.3925 -36.523 - vertex -37.4964 0.521254 -50.7867 - vertex -33.2312 17.3763 -55.9708 - endloop - endfacet - facet normal 0.360618 -0.93241 -0.0237878 - outer loop - vertex -4.28242 37.2547 -37.0287 - vertex -21.8234 30.4957 -38.0135 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal 0.736974 -0.675639 -0.0195259 - outer loop - vertex -32.476 18.75 -75 - vertex -20.2142 31.5854 -56.3313 - vertex -33.2312 17.3763 -55.9708 - endloop - endfacet - facet normal 0.754466 -0.656339 0.000220828 - outer loop - vertex -33.2228 17.3925 -36.523 - vertex -33.2312 17.3763 -55.9708 - vertex -21.8234 30.4957 -38.0135 - endloop - endfacet - facet normal 0.737448 -0.674954 0.0246321 - outer loop - vertex -21.8234 30.4957 -38.0135 - vertex -33.2312 17.3763 -55.9708 - vertex -20.2142 31.5854 -56.3313 - endloop - endfacet - facet normal -0.770324 -0.632174 0.0834076 - outer loop - vertex 31.5798 20.2229 -36.9367 - vertex 19.8668 31.805 -57.3293 - vertex 34.9655 13.5522 -56.227 - endloop - endfacet - facet normal -0.706994 -0.706994 0.0178362 - outer loop - vertex 19.8668 31.805 -57.3293 - vertex 18.75 32.476 -75 - vertex 32.476 18.75 -75 - endloop - endfacet - facet normal 0.738164 -0.674621 0 - outer loop - vertex -20 31.7214 16.6667 - vertex -33.3888 17.0715 0.780048 - vertex -20 31.7214 0 - endloop - endfacet - facet normal 0.706131 0.706131 -0.0525157 - outer loop - vertex -18.75 -32.476 -75 - vertex -32.476 -18.75 -75 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.802896 0.595995 -0.0121398 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -25.0898 -27.8703 -52.7154 - vertex -33.7446 -16.3569 -59.8798 - endloop - endfacet - facet normal 0.949211 0.30888 -0.0599313 - outer loop - vertex -37.4717 -1.45742 -15.9083 - vertex -30.9723 -21.1416 -14.419 - vertex -34.3296 -15.0907 -36.4073 - endloop - endfacet - facet normal 0.975128 -0.221521 0.00738184 - outer loop - vertex -33.3888 17.0715 0.780048 - vertex -37.4717 -1.45742 -15.9083 - vertex -33.1556 17.5202 -16.5603 - endloop - endfacet - facet normal 0 -0.999805 0.0197281 - outer loop - vertex -6.99057 36.8427 0 - vertex -8.64115 36.4908 -17.8341 - vertex 6.99057 36.8427 0 - endloop - endfacet - facet normal -0.366144 -0.9301 -0.0292115 - outer loop - vertex 11.0649 35.8304 -18.8367 - vertex 20 31.7214 0 - vertex 6.99057 36.8427 0 - endloop - endfacet - facet normal -0.556637 -0.828156 -0.0656709 - outer loop - vertex 11.0649 35.8304 -18.8367 - vertex 16.1087 33.8639 -36.7898 - vertex 29.4828 23.1736 -15.3386 - endloop - endfacet - facet normal -0.660899 -0.749073 -0.0458366 - outer loop - vertex 16.1087 33.8639 -36.7898 - vertex 19.8668 31.805 -57.3293 - vertex 31.5798 20.2229 -36.9367 - endloop - endfacet - facet normal -0.258262 -0.965861 -0.0203539 - outer loop - vertex -1.45427 37.4718 -55.7041 - vertex 18.75 32.476 -75 - vertex 19.8668 31.805 -57.3293 - endloop - endfacet - facet normal -0.25876 -0.965715 -0.0209132 - outer loop - vertex -1.45427 37.4718 -55.7041 - vertex 0 37.5 -75 - vertex 18.75 32.476 -75 - endloop - endfacet - facet normal 0.366256 -0.930384 -0.0155394 - outer loop - vertex -6.99057 36.8427 0 - vertex -20 31.7214 0 - vertex -8.64115 36.4908 -17.8341 - endloop - endfacet - facet normal 0.737943 -0.674821 -0.00753754 - outer loop - vertex -20 31.7214 0 - vertex -33.3888 17.0715 0.780048 - vertex -33.1556 17.5202 -16.5603 - endloop - endfacet - facet normal 0.965152 0.258609 0.0400465 - outer loop - vertex -33.7446 -16.3569 -59.8798 - vertex -32.476 -18.75 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0.977554 0.210283 0.01302 - outer loop - vertex -34.3296 -15.0907 -36.4073 - vertex -33.7446 -16.3569 -59.8798 - vertex -37.4964 0.521254 -50.7867 - endloop - endfacet - facet normal 0.987648 0.147299 0.0534231 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -37.4717 -1.45742 -15.9083 - vertex -34.3296 -15.0907 -36.4073 - endloop - endfacet - facet normal 0.972812 -0.223352 -0.0612403 - outer loop - vertex -37.3461 3.39372 -31.6059 - vertex -33.1556 17.5202 -16.5603 - vertex -37.4717 -1.45742 -15.9083 - endloop - endfacet - facet normal -0.0310715 -0.998415 0.0469351 - outer loop - vertex -8.64115 36.4908 -17.8341 - vertex 11.0649 35.8304 -18.8367 - vertex 6.99057 36.8427 0 - endloop - endfacet - facet normal -0.164426 -0.984462 0.0616389 - outer loop - vertex 11.0649 35.8304 -18.8367 - vertex -4.28242 37.2547 -37.0287 - vertex 16.1087 33.8639 -36.7898 - endloop - endfacet - facet normal -0.252935 -0.966161 0.0505694 - outer loop - vertex 16.1087 33.8639 -36.7898 - vertex -1.45427 37.4718 -55.7041 - vertex 19.8668 31.805 -57.3293 - endloop - endfacet - facet normal 0.258774 -0.965768 0.0180917 - outer loop - vertex -18.75 32.476 -75 - vertex 0 37.5 -75 - vertex -1.45427 37.4718 -55.7041 - endloop - endfacet - facet normal -0.746101 0.665833 0 - outer loop - vertex 20 -31.7214 16.6667 - vertex 33.7839 -16.2758 -0.75261 - vertex 20 -31.7214 0 - endloop - endfacet - facet normal -0.772989 0.632625 -0.0476722 - outer loop - vertex 33.6967 -16.4554 -19.5029 - vertex 23.2669 -29.4092 -22.2881 - vertex 20 -31.7214 0 - endloop - endfacet - facet normal -0.679652 0.729658 0.0753189 - outer loop - vertex 23.2669 -29.4092 -22.2881 - vertex 32.0358 -19.4924 -39.2304 - vertex 17.3132 -33.2642 -38.6666 - endloop - endfacet - facet normal -0.705352 0.705352 0.0704001 - outer loop - vertex 26.8281 -26.2012 -56.9324 - vertex 32.476 -18.75 -75 - vertex 18.75 -32.476 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 74.5519 34.028 - vertex -20 57.0711 42.9289 - vertex -20 58.6722 27.2612 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 83.9674 19.9229 - vertex -20 74.5519 34.028 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 81.4151 0 - vertex -20 83.9674 19.9229 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 42.9289 42.9289 - vertex -20 40 50 - vertex -20 31.7214 50 - endloop - endfacet - facet normal 0.638663 -0.7693 0.0169606 - outer loop - vertex -20 31.7214 33.3333 - vertex -22.6774 29.8661 50 - vertex -25.1837 27.7854 50 - endloop - endfacet - facet normal 0.861265 -0.508156 0 - outer loop - vertex -27.5 25.4951 50 - vertex -27.5 25.4951 62.5 - vertex -35.6139 11.743 53.8604 - endloop - endfacet - facet normal -0.502817 0.861196 -0.0742779 - outer loop - vertex 26.8281 -26.2012 -56.9324 - vertex 18.75 -32.476 -75 - vertex 9.4897 -36.2794 -56.4108 - endloop - endfacet - facet normal -0.499519 0.863174 0.0735647 - outer loop - vertex 17.3132 -33.2642 -38.6666 - vertex 26.8281 -26.2012 -56.9324 - vertex 9.4897 -36.2794 -56.4108 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -48.286 0 - vertex -20 -31.7214 0 - vertex -20 -43.0859 11.2998 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -43.0859 11.2998 - vertex -20 -31.7214 16.6667 - vertex -20 -45.6982 25.7885 - endloop - endfacet - facet normal 0.721159 0.692769 0 - outer loop - vertex -20 -31.7214 33.3333 - vertex -20 -31.7214 16.6667 - vertex -32.4986 -18.7106 26.4243 - endloop - endfacet - facet normal 0.963354 0.267082 0.0248405 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -33.3967 -17.056 43.464 - vertex -32.4986 -18.7106 26.4243 - endloop - endfacet - facet normal 0 1 0.000191992 - outer loop - vertex 6.99057 -36.8427 0 - vertex 7.0086 -36.8392 -18.2398 - vertex -6.99057 -36.8427 0 - endloop - endfacet - facet normal -0.426737 0.902558 -0.0573125 - outer loop - vertex 23.2669 -29.4092 -22.2881 - vertex 17.3132 -33.2642 -38.6666 - vertex 7.0086 -36.8392 -18.2398 - endloop - endfacet - facet normal 0.984152 -0.172729 0.0401078 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -34.2369 15.2998 35.3898 - vertex -35.6139 11.743 53.8604 - endloop - endfacet - facet normal -0.728045 -0.684924 -0.0287854 - outer loop - vertex 20 31.7214 33.3333 - vertex 32.4669 18.7657 26.2883 - vertex 33.3945 17.0604 43.4034 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 42.9891 10.7098 - vertex 20 45.5064 24.0211 - vertex 20 57.8078 12.7685 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex 20 45.5064 24.0211 - vertex 20 31.7214 16.6667 - vertex 20 31.7214 33.3333 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex 20 -31.7214 16.6667 - vertex 20 -31.7214 0 - vertex 20 -49.8517 11.8026 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 74.5519 34.028 - vertex -20 60 50 - vertex -20 57.0711 42.9289 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 83.9674 19.9229 - vertex -20 97.9796 33.3333 - vertex -20 74.5519 34.028 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 81.4151 0 - vertex -20 97.9796 16.6667 - vertex -20 83.9674 19.9229 - endloop - endfacet - facet normal 0.569566 -0.821946 0 - outer loop - vertex -20 31.7214 50 - vertex -22.6774 29.8661 50 - vertex -20 31.7214 33.3333 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -27.5 25.4951 50 - vertex -27.5 42.9289 57.0711 - vertex -27.5 25.4951 62.5 - endloop - endfacet - facet normal 0.86864 -0.494626 -0.0284632 - outer loop - vertex -35.6139 11.743 53.8604 - vertex -27.5 25.4951 62.5 - vertex -36.3417 9.24839 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 -48.286 0 - vertex -20 -43.0859 11.2998 - vertex -20 -57.6764 13.4257 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 -43.0859 11.2998 - vertex -20 -45.6982 25.7885 - vertex -20 -57.6764 13.4257 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -45.6982 25.7885 - vertex -20 -31.7214 16.6667 - vertex -20 -31.7214 33.3333 - endloop - endfacet - facet normal 0.728288 0.684695 -0.0281003 - outer loop - vertex -20 -31.7214 33.3333 - vertex -32.4986 -18.7106 26.4243 - vertex -33.3967 -17.056 43.464 - endloop - endfacet - facet normal 0.964461 0.263928 0.0125606 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -37.3561 -3.2825 58.0705 - vertex -33.3967 -17.056 43.464 - endloop - endfacet - facet normal -0.3663 0.930497 -0.000183442 - outer loop - vertex 6.99057 -36.8427 0 - vertex 20 -31.7214 0 - vertex 7.0086 -36.8392 -18.2398 - endloop - endfacet - facet normal -0.408217 0.912221 0.0348003 - outer loop - vertex 20 -31.7214 0 - vertex 23.2669 -29.4092 -22.2881 - vertex 7.0086 -36.8392 -18.2398 - endloop - endfacet - facet normal 0.992874 -0.118545 -0.0122112 - outer loop - vertex -37.4428 -2.06999 39.2501 - vertex -35.6139 11.743 53.8604 - vertex -37.3561 -3.2825 58.0705 - endloop - endfacet - facet normal -0.770909 -0.626893 0.112715 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 27.5 25.4951 50 - vertex 20 31.7214 33.3333 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 57.8078 12.7685 - vertex 20 45.5064 24.0211 - vertex 20 62.8929 25.7602 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 45.5064 24.0211 - vertex 20 31.7214 33.3333 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 48.286 0 - vertex 20 57.8078 12.7685 - vertex 20 64.8505 0 - endloop - endfacet - facet normal -0.963049 -0.268118 0.0254806 - outer loop - vertex 33.3945 17.0604 43.4034 - vertex 32.4669 18.7657 26.2883 - vertex 37.4402 2.11676 39.0684 - endloop - endfacet - facet normal -0.754965 0.655363 -0.0229452 - outer loop - vertex 20 -31.7214 33.3333 - vertex 34.274 -15.2166 35.0879 - vertex 33.6503 -16.5501 17.5219 - endloop - endfacet - facet normal -0.983645 0.18011 -0.00188376 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 37.4402 2.11676 39.0684 - vertex 37.4483 1.96876 20.689 - endloop - endfacet - facet normal -0.743388 0.66886 0 - outer loop - vertex 20 -31.7214 33.3333 - vertex 33.6503 -16.5501 17.5219 - vertex 20 -31.7214 16.6667 - endloop - endfacet - facet normal -0.720569 -0.693383 -0 - outer loop - vertex 20 31.7214 33.3333 - vertex 20 31.7214 16.6667 - vertex 32.4669 18.7657 26.2883 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 42.9891 10.7098 - vertex 20 31.7214 16.6667 - vertex 20 45.5064 24.0211 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 48.286 0 - vertex 20 31.7214 0 - vertex 20 42.9891 10.7098 - endloop - endfacet - facet normal -0.957876 -0.287044 0.00891288 - outer loop - vertex 37.4483 1.96876 20.689 - vertex 32.4669 18.7657 26.2883 - vertex 32.1117 19.3672 7.48614 - endloop - endfacet - facet normal -0.98005 0.197952 0.0178017 - outer loop - vertex 33.6503 -16.5501 17.5219 - vertex 37.4483 1.96876 20.689 - vertex 37.3569 3.2728 1.15635 - endloop - endfacet - facet normal -0.983616 0.180219 -0.00448599 - outer loop - vertex 33.6503 -16.5501 17.5219 - vertex 37.3569 3.2728 1.15635 - vertex 33.7839 -16.2758 -0.75261 - endloop - endfacet - facet normal -0.983875 0.178834 0.00286265 - outer loop - vertex 33.7839 -16.2758 -0.75261 - vertex 37.3331 3.53357 -18.437 - vertex 33.6967 -16.4554 -19.5029 - endloop - endfacet - facet normal -0.962215 0.269405 0.0395367 - outer loop - vertex 33.6967 -16.4554 -19.5029 - vertex 37.4996 -0.172499 -37.9034 - vertex 32.0358 -19.4924 -39.2304 - endloop - endfacet - facet normal -0.877962 0.472106 0.0793636 - outer loop - vertex 32.0358 -19.4924 -39.2304 - vertex 36.6441 -7.96625 -56.816 - vertex 26.8281 -26.2012 -56.9324 - endloop - endfacet - facet normal -0.963706 0.258222 0.0677642 - outer loop - vertex 36.6441 -7.96625 -56.816 - vertex 37.5 0 -75 - vertex 32.476 -18.75 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 58.6722 27.2612 - vertex -20 50 40 - vertex -20 43.9211 27.0189 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 58.6722 27.2612 - vertex -20 49.7152 12.4405 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 64.8505 0 - vertex -20 68.9073 15.3707 - vertex -20 49.7152 12.4405 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 31.7214 33.3333 - vertex -20 43.9211 27.0189 - vertex -20 42.9289 42.9289 - endloop - endfacet - facet normal 0.757951 -0.644556 0.100286 - outer loop - vertex -27.5 25.4951 50 - vertex -34.2369 15.2998 35.3898 - vertex -20 31.7214 33.3333 - endloop - endfacet - facet normal 0.000235671 0.997843 -0.0656405 - outer loop - vertex 9.4897 -36.2794 -56.4108 - vertex 0 -37.5 -75 - vertex -9.77074 -36.2047 -55.3444 - endloop - endfacet - facet normal 0.00744701 0.997883 0.0646017 - outer loop - vertex -1.8284 -37.4554 -36.9408 - vertex 9.4897 -36.2794 -56.4108 - vertex -9.77074 -36.2047 -55.3444 - endloop - endfacet - facet normal 0.718225 0.695811 0 - outer loop - vertex -20 -31.7214 16.6667 - vertex -20 -31.7214 0 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.959599 0.281343 0.00407455 - outer loop - vertex -37.4611 -1.70839 21.1626 - vertex -32.4986 -18.7106 26.4243 - vertex -32.3394 -18.9845 7.84387 - endloop - endfacet - facet normal 0.366066 0.929902 -0.0357597 - outer loop - vertex -6.99057 -36.8427 0 - vertex -13.4703 -34.9972 -18.3411 - vertex -20 -31.7214 0 - endloop - endfacet - facet normal 0.0897 0.993133 -0.0751108 - outer loop - vertex 7.0086 -36.8392 -18.2398 - vertex -1.8284 -37.4554 -36.9408 - vertex -13.4703 -34.9972 -18.3411 - endloop - endfacet - facet normal 0.97829 -0.205808 0.0243349 - outer loop - vertex -33.4723 16.9073 18.2472 - vertex -34.2369 15.2998 35.3898 - vertex -37.4611 -1.70839 21.1626 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex 20 48.286 0 - vertex 20 42.9891 10.7098 - vertex 20 57.8078 12.7685 - endloop - endfacet - facet normal -0.958556 -0.284899 0.00187177 - outer loop - vertex 37.4402 2.11676 39.0684 - vertex 32.4669 18.7657 26.2883 - vertex 37.4483 1.96876 20.689 - endloop - endfacet - facet normal -0.980079 0.197617 0.0197969 - outer loop - vertex 34.274 -15.2166 35.0879 - vertex 37.4483 1.96876 20.689 - vertex 33.6503 -16.5501 17.5219 - endloop - endfacet - facet normal -0.74351 0.66871 0.00460162 - outer loop - vertex 33.6503 -16.5501 17.5219 - vertex 33.7839 -16.2758 -0.75261 - vertex 20 -31.7214 16.6667 - endloop - endfacet - facet normal -0.746168 0.665751 -0.00290677 - outer loop - vertex 33.7839 -16.2758 -0.75261 - vertex 33.6967 -16.4554 -19.5029 - vertex 20 -31.7214 0 - endloop - endfacet - facet normal -0.775152 0.63097 -0.0318745 - outer loop - vertex 33.6967 -16.4554 -19.5029 - vertex 32.0358 -19.4924 -39.2304 - vertex 23.2669 -29.4092 -22.2881 - endloop - endfacet - facet normal -0.68275 0.726833 -0.0746028 - outer loop - vertex 32.0358 -19.4924 -39.2304 - vertex 26.8281 -26.2012 -56.9324 - vertex 17.3132 -33.2642 -38.6666 - endloop - endfacet - facet normal -0.877544 0.472894 -0.079294 - outer loop - vertex 36.6441 -7.96625 -56.816 - vertex 32.476 -18.75 -75 - vertex 26.8281 -26.2012 -56.9324 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 58.6722 27.2612 - vertex -20 57.0711 42.9289 - vertex -20 50 40 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 74.5519 34.028 - vertex -20 58.6722 27.2612 - vertex -20 68.9073 15.3707 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 81.4151 0 - vertex -20 68.9073 15.3707 - vertex -20 64.8505 0 - endloop - endfacet - facet normal 0.983195 -0.182498 -0.00464335 - outer loop - vertex -37.4611 -1.70839 21.1626 - vertex -34.2369 15.2998 35.3898 - vertex -37.4428 -2.06999 39.2501 - endloop - endfacet - facet normal -0.207741 0.975954 0.0660086 - outer loop - vertex 7.0086 -36.8392 -18.2398 - vertex 17.3132 -33.2642 -38.6666 - vertex -1.8284 -37.4554 -36.9408 - endloop - endfacet - facet normal 0.0890377 0.993668 0.0685278 - outer loop - vertex -6.99057 -36.8427 0 - vertex 7.0086 -36.8392 -18.2398 - vertex -13.4703 -34.9972 -18.3411 - endloop - endfacet - facet normal 0.959548 0.281508 0.00465685 - outer loop - vertex -32.4986 -18.7106 26.4243 - vertex -37.4611 -1.70839 21.1626 - vertex -37.4428 -2.06999 39.2501 - endloop - endfacet - facet normal 0.719627 0.694349 -0.00406983 - outer loop - vertex -20 -31.7214 16.6667 - vertex -32.3394 -18.9845 7.84387 - vertex -32.4986 -18.7106 26.4243 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex -20 -43.0859 11.2998 - vertex -20 -31.7214 0 - vertex -20 -31.7214 16.6667 - endloop - endfacet - facet normal -0.219291 0.973238 -0.068692 - outer loop - vertex 17.3132 -33.2642 -38.6666 - vertex 9.4897 -36.2794 -56.4108 - vertex -1.8284 -37.4554 -36.9408 - endloop - endfacet - facet normal -0.258208 0.963655 0.0685387 - outer loop - vertex 9.4897 -36.2794 -56.4108 - vertex 18.75 -32.476 -75 - vertex 0 -37.5 -75 - endloop - endfacet - facet normal 0.85635 -0.515184 -0.035365 - outer loop - vertex -27.5 25.4951 50 - vertex -35.6139 11.743 53.8604 - vertex -34.2369 15.2998 35.3898 - endloop - endfacet - facet normal 0.702201 -0.710172 0.0506857 - outer loop - vertex -27.5 25.4951 50 - vertex -20 31.7214 33.3333 - vertex -25.1837 27.7854 50 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex -20 43.9211 27.0189 - vertex -20 50 40 - vertex -20 42.9289 42.9289 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex -20 31.7214 33.3333 - vertex -20 42.9289 42.9289 - vertex -20 31.7214 50 - endloop - endfacet -endsolid patch004 -solid patch005 - facet normal 0.0884709 0.901692 0.423231 - outer loop - vertex 27.5 35 50 - vertex 39.5601 35.3693 46.6922 - vertex 32.3647 39.5932 39.1973 - endloop - endfacet - facet normal -0.0882236 0.920277 0.381191 - outer loop - vertex 39.5601 35.3693 46.6922 - vertex 50 35 50 - vertex 50 39.3934 39.3934 - endloop - endfacet - facet normal -0.00874042 0.921644 0.387938 - outer loop - vertex 27.5 35 50 - vertex 32.3647 39.5932 39.1973 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal 0.0937439 -0.919811 -0.380998 - outer loop - vertex 38.6605 63.1428 57.2297 - vertex 27.5 60.6066 60.6066 - vertex 27.5 65 50 - endloop - endfacet - facet normal 0.139172 -0.508872 -0.849518 - outer loop - vertex 50 60.6066 60.6066 - vertex 38.7482 50.1971 64.9987 - vertex 38.6605 63.1428 57.2297 - endloop - endfacet - facet normal -0.076881 0.982331 -0.170632 - outer loop - vertex 27.5 35 50 - vertex 38.773 37.2567 57.9126 - vertex 39.5601 35.3693 46.6922 - endloop - endfacet - facet normal 0.0853123 0.983512 -0.159453 - outer loop - vertex 38.773 37.2567 57.9126 - vertex 50 35 50 - vertex 39.5601 35.3693 46.6922 - endloop - endfacet - facet normal 0 0.92388 0.382683 - outer loop - vertex 27.5 35 50 - vertex 20 39.3934 39.3934 - vertex 20 35 50 - endloop - endfacet - facet normal -0.140801 -0.510148 -0.848483 - outer loop - vertex 38.7482 50.1971 64.9987 - vertex 27.5 60.6066 60.6066 - vertex 38.6605 63.1428 57.2297 - endloop - endfacet - facet normal -0.00659696 -0.382675 -0.923859 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 50 65 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal 0.0833692 0.920663 -0.381351 - outer loop - vertex 27.5 35 50 - vertex 27.5 39.3934 60.6066 - vertex 38.773 37.2567 57.9126 - endloop - endfacet - facet normal -0.0837084 0.920637 -0.38134 - outer loop - vertex 38.773 37.2567 57.9126 - vertex 50 39.3934 60.6066 - vertex 50 35 50 - endloop - endfacet - facet normal 0.00659907 -0.382675 -0.923859 - outer loop - vertex 38.7482 50.1971 64.9987 - vertex 27.5 50 65 - vertex 27.5 60.6066 60.6066 - endloop - endfacet - facet normal 0.00680993 0.382675 -0.923858 - outer loop - vertex 38.7482 50.1971 64.9987 - vertex 50 50 65 - vertex 50 39.3934 60.6066 - endloop - endfacet - facet normal -0.117803 0.47678 -0.871093 - outer loop - vertex 38.773 37.2567 57.9126 - vertex 27.5 39.3934 60.6066 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal 0.118168 0.477108 -0.870864 - outer loop - vertex 50 39.3934 60.6066 - vertex 38.773 37.2567 57.9126 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal -0.00681211 0.382675 -0.923858 - outer loop - vertex 27.5 39.3934 60.6066 - vertex 27.5 50 65 - vertex 38.7482 50.1971 64.9987 - endloop - endfacet - facet normal -0.075501 -0.381591 0.921243 - outer loop - vertex 35.1847 56.4486 36.4569 - vertex 50 50 35 - vertex 50 60.6066 39.3934 - endloop - endfacet - facet normal 0.0536692 -0.101138 0.993424 - outer loop - vertex 37.135 46.7259 35.3617 - vertex 50 50 35 - vertex 35.1847 56.4486 36.4569 - endloop - endfacet - facet normal 0.0716869 -0.733084 0.67635 - outer loop - vertex 36.8547 63.896 44.352 - vertex 35.1847 56.4486 36.4569 - vertex 50 60.6066 39.3934 - endloop - endfacet - facet normal -0.0712355 0.381711 0.921532 - outer loop - vertex 50 39.3934 39.3934 - vertex 50 50 35 - vertex 37.135 46.7259 35.3617 - endloop - endfacet - facet normal -0.0439652 -0.120532 0.991735 - outer loop - vertex 20 50 35 - vertex 37.135 46.7259 35.3617 - vertex 35.1847 56.4486 36.4569 - endloop - endfacet - facet normal -0.0631646 -0.719275 0.691848 - outer loop - vertex 20 60.6066 39.3934 - vertex 35.1847 56.4486 36.4569 - vertex 36.8547 63.896 44.352 - endloop - endfacet - facet normal -0.0865065 -0.920416 0.381249 - outer loop - vertex 36.8547 63.896 44.352 - vertex 50 60.6066 39.3934 - vertex 50 65 50 - endloop - endfacet - facet normal -0.00438809 0.475884 0.879497 - outer loop - vertex 32.3647 39.5932 39.1973 - vertex 50 39.3934 39.3934 - vertex 37.135 46.7259 35.3617 - endloop - endfacet - facet normal 0.0648871 0.438607 0.896334 - outer loop - vertex 37.135 46.7259 35.3617 - vertex 20 50 35 - vertex 32.3647 39.5932 39.1973 - endloop - endfacet - facet normal 0.0736743 -0.381643 0.921369 - outer loop - vertex 20 60.6066 39.3934 - vertex 20 50 35 - vertex 35.1847 56.4486 36.4569 - endloop - endfacet - facet normal 0.0870615 -0.940636 0.328062 - outer loop - vertex 27.5 65 50 - vertex 20 60.6066 39.3934 - vertex 36.8547 63.896 44.352 - endloop - endfacet - facet normal 0.115019 -0.990598 -0.0740676 - outer loop - vertex 38.6605 63.1428 57.2297 - vertex 36.8547 63.896 44.352 - vertex 50 65 50 - endloop - endfacet - facet normal 0.00446766 0.872997 0.487706 - outer loop - vertex 50 39.3934 39.3934 - vertex 32.3647 39.5932 39.1973 - vertex 39.5601 35.3693 46.6922 - endloop - endfacet - facet normal 0.00846817 0.38267 0.923846 - outer loop - vertex 32.3647 39.5932 39.1973 - vertex 20 50 35 - vertex 20 39.3934 39.3934 - endloop - endfacet - facet normal -0.139867 -0.989431 -0.0382575 - outer loop - vertex 36.8547 63.896 44.352 - vertex 38.6605 63.1428 57.2297 - vertex 27.5 65 50 - endloop - endfacet - facet normal 0 -0.92388 0.382683 - outer loop - vertex 20 65 50 - vertex 20 60.6066 39.3934 - vertex 27.5 65 50 - endloop - endfacet - facet normal -0.0922768 -0.919938 -0.381051 - outer loop - vertex 50 60.6066 60.6066 - vertex 38.6605 63.1428 57.2297 - vertex 50 65 50 - endloop - endfacet -endsolid patch005 -solid patch006 - facet normal 0 0 1 - outer loop - vertex -6.99057 -36.8427 0 - vertex -20 -31.7214 0 - vertex -20 -48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -71.7622 0 - vertex -20 -81.4151 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 13.3836 -99.1004 0 - vertex 20 -81.4151 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -87.0832 0 - vertex -20 -81.4151 0 - vertex -13.3836 -99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 13.3836 -99.1004 0 - vertex 20 -97.9796 0 - vertex 20 -81.4151 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 13.3836 -99.1004 0 - vertex 0 -87.0832 0 - vertex 6.70689 -99.7748 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -81.4151 0 - vertex -20 -97.9796 0 - vertex -13.3836 -99.1004 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -6.70689 -99.7748 0 - vertex 0 -87.0832 0 - vertex -13.3836 -99.1004 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -87.0832 0 - vertex 0 -100 0 - vertex 6.70689 -99.7748 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -6.70689 -99.7748 0 - vertex 0 -100 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 -64.8505 0 - vertex 20 -48.286 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -48.286 0 - vertex 6.99057 -36.8427 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -64.8505 0 - vertex 0 -54.2451 0 - vertex 0 -71.7622 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 6.99057 -36.8427 0 - vertex -6.99057 -36.8427 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -31.7214 0 - vertex 6.99057 -36.8427 0 - vertex 20 -48.286 0 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 20 -81.4151 0 - vertex 20 -64.8505 0 - vertex 0 -71.7622 0 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -20 -64.8505 0 - vertex 0 -71.7622 0 - vertex 0 -54.2451 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 0 -54.2451 0 - vertex -6.99057 -36.8427 0 - vertex -20 -48.286 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -81.4151 0 - vertex 0 -71.7622 0 - vertex 0 -87.0832 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -64.8505 0 - vertex -20 -81.4151 0 - vertex 0 -71.7622 0 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -64.8505 0 - vertex 0 -54.2451 0 - vertex -20 -48.286 0 - endloop - endfacet -endsolid patch006 -solid patch007 - facet normal -0.041709 -0.380249 -0.923943 - outer loop - vertex -27.5 -50 60 - vertex -40.5084 -48.1569 59.8287 - vertex -37.0198 -43.8869 57.9139 - endloop - endfacet - facet normal 0.0271305 -0.427395 -0.903658 - outer loop - vertex -40.5084 -48.1569 59.8287 - vertex -50 -42.9289 57.0711 - vertex -37.0198 -43.8869 57.9139 - endloop - endfacet - facet normal -0.0530497 0.941223 0.333594 - outer loop - vertex -27.5 -60 50 - vertex -20 -57.0711 42.9289 - vertex -36.6093 -58.8915 45.4238 - endloop - endfacet - facet normal -0.0555981 0.640625 0.765839 - outer loop - vertex -50 -57.0711 42.9289 - vertex -36.6093 -58.8915 45.4238 - vertex -35.1456 -52.7371 40.3819 - endloop - endfacet - facet normal 0.0337472 0.146297 -0.988665 - outer loop - vertex -40.5084 -48.1569 59.8287 - vertex -27.5 -50 60 - vertex -38.7903 -54.4475 58.9565 - endloop - endfacet - facet normal 0.0575403 -0.382045 -0.922351 - outer loop - vertex -50 -50 60 - vertex -50 -42.9289 57.0711 - vertex -40.5084 -48.1569 59.8287 - endloop - endfacet - facet normal 0 0.923882 0.382679 - outer loop - vertex -20 -60 50 - vertex -20 -57.0711 42.9289 - vertex -27.5 -60 50 - endloop - endfacet - facet normal 0.0797713 0.993447 0.0818532 - outer loop - vertex -36.6093 -58.8915 45.4238 - vertex -38.6088 -59.3911 53.4361 - vertex -27.5 -60 50 - endloop - endfacet - facet normal 0.0542182 0.922523 0.382116 - outer loop - vertex -50 -57.0711 42.9289 - vertex -50 -60 50 - vertex -36.6093 -58.8915 45.4238 - endloop - endfacet - facet normal -0.0423279 0.125863 -0.991144 - outer loop - vertex -38.7903 -54.4475 58.9565 - vertex -50 -50 60 - vertex -40.5084 -48.1569 59.8287 - endloop - endfacet - facet normal -0.0652172 0.381864 -0.921915 - outer loop - vertex -38.7903 -54.4475 58.9565 - vertex -27.5 -50 60 - vertex -27.5 -57.0711 57.0711 - endloop - endfacet - facet normal -0.066983 0.996719 0.0454341 - outer loop - vertex -38.6088 -59.3911 53.4361 - vertex -36.6093 -58.8915 45.4238 - vertex -50 -60 50 - endloop - endfacet - facet normal -0.0675728 0.92177 -0.381804 - outer loop - vertex -38.6088 -59.3911 53.4361 - vertex -27.5 -57.0711 57.0711 - vertex -27.5 -60 50 - endloop - endfacet - facet normal 0.0656841 0.381852 -0.921886 - outer loop - vertex -50 -57.0711 57.0711 - vertex -50 -50 60 - vertex -38.7903 -54.4475 58.9565 - endloop - endfacet - facet normal 0.0620112 0.744532 -0.664701 - outer loop - vertex -38.7903 -54.4475 58.9565 - vertex -27.5 -57.0711 57.0711 - vertex -38.6088 -59.3911 53.4361 - endloop - endfacet - facet normal 0.0659049 0.921873 -0.381847 - outer loop - vertex -50 -57.0711 57.0711 - vertex -38.6088 -59.3911 53.4361 - vertex -50 -60 50 - endloop - endfacet - facet normal -0.0616065 0.742531 -0.666973 - outer loop - vertex -50 -57.0711 57.0711 - vertex -38.7903 -54.4475 58.9565 - vertex -38.6088 -59.3911 53.4361 - endloop - endfacet - facet normal 0.0168812 -0.917293 0.397855 - outer loop - vertex -20 -42.9289 42.9289 - vertex -27.5 -40 50 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal 0 -0.923882 0.382679 - outer loop - vertex -20 -42.9289 42.9289 - vertex -20 -40 50 - vertex -27.5 -40 50 - endloop - endfacet - facet normal 0.0740237 -0.936444 0.342919 - outer loop - vertex -27.5 -40 50 - vertex -38.4021 -40.1766 51.8711 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal -0.0148827 -0.382636 0.923779 - outer loop - vertex -20 -42.9289 42.9289 - vertex -35.8862 -43.4206 42.4693 - vertex -20 -50 40 - endloop - endfacet - facet normal -0.0506473 -0.922696 -0.382187 - outer loop - vertex -27.5 -40 50 - vertex -27.5 -42.9289 57.0711 - vertex -38.4021 -40.1766 51.8711 - endloop - endfacet - facet normal -0.0644615 -0.948538 0.310034 - outer loop - vertex -38.4021 -40.1766 51.8711 - vertex -50 -40 50 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal 0.0631509 -0.213414 0.974919 - outer loop - vertex -35.8862 -43.4206 42.4693 - vertex -35.1456 -52.7371 40.3819 - vertex -20 -50 40 - endloop - endfacet - facet normal 0.0384435 -0.847608 -0.529229 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -37.0198 -43.8869 57.9139 - vertex -38.4021 -40.1766 51.8711 - endloop - endfacet - facet normal 0.0167511 -0.382625 0.923752 - outer loop - vertex -50 -50 40 - vertex -35.8862 -43.4206 42.4693 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal 0.0467094 0.382261 0.922873 - outer loop - vertex -50 -57.0711 42.9289 - vertex -35.1456 -52.7371 40.3819 - vertex -50 -50 40 - endloop - endfacet - facet normal 0.0482821 0.62609 0.778254 - outer loop - vertex -36.6093 -58.8915 45.4238 - vertex -20 -57.0711 42.9289 - vertex -35.1456 -52.7371 40.3819 - endloop - endfacet - facet normal -0.0294474 -0.854803 -0.518116 - outer loop - vertex -37.0198 -43.8869 57.9139 - vertex -50 -42.9289 57.0711 - vertex -38.4021 -40.1766 51.8711 - endloop - endfacet - facet normal -0.0432421 -0.382321 -0.923017 - outer loop - vertex -27.5 -42.9289 57.0711 - vertex -27.5 -50 60 - vertex -37.0198 -43.8869 57.9139 - endloop - endfacet - facet normal -0.0661229 -0.223157 0.972537 - outer loop - vertex -50 -50 40 - vertex -35.1456 -52.7371 40.3819 - vertex -35.8862 -43.4206 42.4693 - endloop - endfacet - facet normal -0.0458132 0.382277 0.922911 - outer loop - vertex -20 -50 40 - vertex -35.1456 -52.7371 40.3819 - vertex -20 -57.0711 42.9289 - endloop - endfacet - facet normal -0.019721 -0.923702 0.382604 - outer loop - vertex -35.8862 -43.4206 42.4693 - vertex -50 -40 50 - vertex -50 -42.9289 42.9289 - endloop - endfacet - facet normal 0.0476159 -0.922834 -0.382245 - outer loop - vertex -38.4021 -40.1766 51.8711 - vertex -50 -42.9289 57.0711 - vertex -50 -40 50 - endloop - endfacet -endsolid patch007 -solid patch008 - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 25 - vertex 50 -50 35 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -39.3934 60.6066 - vertex 50 -28.8675 75 - vertex 50 -48.1125 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 74.3415 61.8582 - vertex 50 86.6025 75 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 65 50 - vertex 50 74.3415 61.8582 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 74.3415 61.8582 - vertex 50 74.2906 44.8203 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -48.1125 25 - vertex 50 -39.3934 39.3934 - vertex 50 -50 35 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -35 50 - vertex 50 -22.2245 61.2431 - vertex 50 -39.3934 60.6066 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -22.2245 61.2431 - vertex 50 -28.8675 75 - vertex 50 -39.3934 60.6066 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 74.3415 61.8582 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.3415 61.8582 - vertex 50 65 50 - vertex 50 74.2906 44.8203 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 41.6667 - vertex 50 67.3575 25 - vertex 50 86.6025 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 74.2906 44.8203 - vertex 50 86.6025 41.6667 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -28.8675 25 - vertex 50 -39.3934 39.3934 - vertex 50 -48.1125 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -35 50 - vertex 50 -39.3934 39.3934 - vertex 50 -23.0532 44.8966 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -35 50 - vertex 50 -23.0532 44.8966 - vertex 50 -22.2245 61.2431 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -9.6225 75 - vertex 50 -28.8675 75 - vertex 50 -22.2245 61.2431 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 60.6066 60.6066 - vertex 50 67.3575 75 - vertex 50 50 65 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 58.3333 - vertex 50 -75.4061 48.0166 - vertex 50 -74.3334 62.5671 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 58.3333 - vertex 50 -74.3334 62.5671 - vertex 50 -86.6025 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -75.4061 48.0166 - vertex 50 -86.6025 58.3333 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -75.4061 48.0166 - vertex 50 -65 50 - vertex 50 -74.3334 62.5671 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 75 - vertex 50 -74.3334 62.5671 - vertex 50 -67.3575 75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -65 50 - vertex 50 -60.6066 60.6066 - vertex 50 -74.3334 62.5671 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -86.6025 25 - vertex 50 -75.1752 35.2676 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -75.1752 35.2676 - vertex 50 -75.4061 48.0166 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -60.6066 39.3934 - vertex 50 -65 50 - vertex 50 -75.4061 48.0166 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -74.3334 62.5671 - vertex 50 -60.6066 60.6066 - vertex 50 -67.3575 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -75.1752 35.2676 - vertex 50 -86.6025 25 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -75.1752 35.2676 - vertex 50 -60.6066 39.3934 - vertex 50 -75.4061 48.0166 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -60.6066 60.6066 - vertex 50 -50 65 - vertex 50 -67.3575 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -60.6066 39.3934 - vertex 50 -75.1752 35.2676 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -67.3575 75 - vertex 50 -50 65 - vertex 50 -48.1125 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -67.3575 25 - vertex 50 -50 35 - vertex 50 -60.6066 39.3934 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -39.3934 60.6066 - vertex 50 -48.1125 75 - vertex 50 -50 65 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 86.6025 75 - vertex 50 74.3415 61.8582 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -12.3722 39.0134 - vertex 50 -9.6225 25 - vertex 50 4.24366 42.6158 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 11.8037 60.8572 - vertex 50 -5.58971 57.5541 - vertex 50 4.24366 42.6158 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 11.8037 60.8572 - vertex 50 22.5939 54.2272 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 22.5939 54.2272 - vertex 50 39.3934 60.6066 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 48.1125 25 - vertex 50 50 35 - vertex 50 39.3934 39.3934 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 4.24366 42.6158 - vertex 50 -9.6225 25 - vertex 50 9.6225 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 4.24366 42.6158 - vertex 50 22.5939 54.2272 - vertex 50 11.8037 60.8572 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 22.5939 54.2272 - vertex 50 35 50 - vertex 50 39.3934 60.6066 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.3934 39.3934 - vertex 50 35 50 - vertex 50 28.2388 40.5597 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 25 - vertex 50 48.1125 25 - vertex 50 39.3934 39.3934 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 4.24366 42.6158 - vertex 50 9.6225 25 - vertex 50 17.7589 37.3466 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 22.5939 54.2272 - vertex 50 4.24366 42.6158 - vertex 50 17.7589 37.3466 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 28.2388 40.5597 - vertex 50 35 50 - vertex 50 22.5939 54.2272 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 28.8675 25 - vertex 50 39.3934 39.3934 - vertex 50 28.2388 40.5597 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 17.7589 37.3466 - vertex 50 9.6225 25 - vertex 50 28.8675 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 17.7589 37.3466 - vertex 50 28.2388 40.5597 - vertex 50 22.5939 54.2272 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.2388 40.5597 - vertex 50 17.7589 37.3466 - vertex 50 28.8675 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 65 50 - vertex 50 60.6066 39.3934 - vertex 50 74.2906 44.8203 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 41.6667 - vertex 50 74.2906 44.8203 - vertex 50 67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -23.0532 44.8966 - vertex 50 -39.3934 39.3934 - vertex 50 -28.8675 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -5.58971 57.5541 - vertex 50 -22.2245 61.2431 - vertex 50 -23.0532 44.8966 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -9.6225 75 - vertex 50 -22.2245 61.2431 - vertex 50 -5.58971 57.5541 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 48.1125 75 - vertex 50 50 65 - vertex 50 67.3575 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.2906 44.8203 - vertex 50 60.6066 39.3934 - vertex 50 67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -23.0532 44.8966 - vertex 50 -28.8675 25 - vertex 50 -12.3722 39.0134 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -12.3722 39.0134 - vertex 50 -5.58971 57.5541 - vertex 50 -23.0532 44.8966 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -9.6225 75 - vertex 50 -5.58971 57.5541 - vertex 50 9.6225 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.3934 60.6066 - vertex 50 50 65 - vertex 50 48.1125 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 60.6066 39.3934 - vertex 50 50 35 - vertex 50 67.3575 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -12.3722 39.0134 - vertex 50 -28.8675 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -5.58971 57.5541 - vertex 50 -12.3722 39.0134 - vertex 50 4.24366 42.6158 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -5.58971 57.5541 - vertex 50 11.8037 60.8572 - vertex 50 9.6225 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 9.6225 75 - vertex 50 11.8037 60.8572 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 28.8675 75 - vertex 50 39.3934 60.6066 - vertex 50 48.1125 75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 67.3575 25 - vertex 50 50 35 - vertex 50 48.1125 25 - endloop - endfacet -endsolid patch008 -solid patch009 - facet normal -0 0 1 - outer loop - vertex 63.1835 20.4106 25 - vertex 75 10 25 - vertex 78.1402 25.7865 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 77.6996 42.7398 25 - vertex 78.1402 25.7865 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 67.9289 7.07107 25 - vertex 75 10 25 - vertex 63.1835 20.4106 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 9.6225 25 - vertex 63.1835 20.4106 25 - vertex 50 28.8675 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 75 10 25 - vertex 82.0711 7.07107 25 - vertex 78.1402 25.7865 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 78.1402 25.7865 25 - vertex 89.7303 15.4472 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 67.9289 7.07107 25 - vertex 63.1835 20.4106 25 - vertex 50 9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 78.1402 25.7865 25 - vertex 82.0711 7.07107 25 - vertex 89.7303 15.4472 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 89.7303 15.4472 25 - vertex 98.4808 17.3648 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 67.9289 7.07107 25 - vertex 50 9.6225 25 - vertex 65 0 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 82.0711 7.07107 25 - vertex 85 0 25 - vertex 89.7303 15.4472 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 98.4808 17.3648 25 - vertex 89.7303 15.4472 25 - vertex 100 0 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -86.6025 25 - vertex 64.2788 -76.6044 25 - vertex 50 -67.3575 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -9.6225 25 - vertex 65 0 25 - vertex 50 9.6225 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 28.8675 25 - vertex 63.1835 20.4106 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 34.202 25 - vertex 86.6025 50 25 - vertex 77.6996 42.7398 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 63.7764 35.8998 25 - vertex 78.1402 25.7865 25 - vertex 77.6996 42.7398 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 78.1402 25.7865 25 - vertex 63.7764 35.8998 25 - vertex 63.1835 20.4106 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 48.1125 25 - vertex 50 28.8675 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 77.6996 42.7398 25 - vertex 86.6025 50 25 - vertex 76.6044 64.2788 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 77.6996 42.7398 25 - vertex 66.0812 50.3368 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 66.0812 50.3368 25 - vertex 50 48.1125 25 - vertex 63.7764 35.8998 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 66.0812 50.3368 25 - vertex 77.6996 42.7398 25 - vertex 76.6044 64.2788 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 61.3178 61.5265 25 - vertex 50 48.1125 25 - vertex 66.0812 50.3368 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 64.2788 25 - vertex 61.3178 61.5265 25 - vertex 66.0812 50.3368 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 67.3575 25 - vertex 50 48.1125 25 - vertex 61.3178 61.5265 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 61.3178 61.5265 25 - vertex 76.6044 64.2788 25 - vertex 64.2788 76.6044 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 67.3575 25 - vertex 61.3178 61.5265 25 - vertex 64.2788 76.6044 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 67.3575 25 - vertex 64.2788 76.6044 25 - vertex 50 86.6025 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 79.858 -27.4478 25 - vertex 77.6146 -42.5462 25 - vertex 93.9693 -34.202 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 77.6146 -42.5462 25 - vertex 79.858 -27.4478 25 - vertex 67.3911 -29.0453 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 77.6146 -42.5462 25 - vertex 86.6025 -50 25 - vertex 93.9693 -34.202 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 93.9693 -34.202 25 - vertex 87.1138 -19.2772 25 - vertex 79.858 -27.4478 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 67.3911 -29.0453 25 - vertex 79.858 -27.4478 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 77.6146 -42.5462 25 - vertex 67.3911 -29.0453 25 - vertex 63.9444 -45.2133 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 86.6025 -50 25 - vertex 77.6146 -42.5462 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 93.9693 -34.202 25 - vertex 98.4808 -17.3648 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 79.858 -27.4478 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 60.991 -18.0167 25 - vertex 67.3911 -29.0453 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 77.6146 -42.5462 25 - vertex 63.9444 -45.2133 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 63.9444 -45.2133 25 - vertex 67.3911 -29.0453 25 - vertex 50 -28.8675 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 98.4808 -17.3648 25 - vertex 91.5102 -8.75708 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 75 -10 25 - vertex 87.1138 -19.2772 25 - vertex 82.0711 -7.07107 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 -28.8675 25 - vertex 67.3911 -29.0453 25 - vertex 60.991 -18.0167 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 89.7303 15.4472 25 - vertex 85 0 25 - vertex 100 0 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 61.3915 -60.3858 25 - vertex 50 -67.3575 25 - vertex 64.2788 -76.6044 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -48.1125 25 - vertex 50 -67.3575 25 - vertex 61.3915 -60.3858 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 67.9289 -7.07107 25 - vertex 65 0 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 85 0 25 - vertex 82.0711 -7.07107 25 - vertex 91.5102 -8.75708 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 100 0 25 - vertex 85 0 25 - vertex 91.5102 -8.75708 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 61.3915 -60.3858 25 - vertex 64.2788 -76.6044 25 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 50 -48.1125 25 - vertex 61.3915 -60.3858 25 - vertex 63.9444 -45.2133 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 60.991 -18.0167 25 - vertex 67.9289 -7.07107 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -28.8675 25 - vertex 60.991 -18.0167 25 - vertex 50 -9.6225 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 91.5102 -8.75708 25 - vertex 82.0711 -7.07107 25 - vertex 87.1138 -19.2772 25 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 98.4808 -17.3648 25 - vertex 100 0 25 - vertex 91.5102 -8.75708 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 50 -48.1125 25 - vertex 63.9444 -45.2133 25 - vertex 50 -28.8675 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 76.6044 -64.2788 25 - vertex 63.9444 -45.2133 25 - vertex 61.3915 -60.3858 25 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 75 -10 25 - vertex 67.9289 -7.07107 25 - vertex 60.991 -18.0167 25 - endloop - endfacet -endsolid patch009 -solid patch010 - facet normal -0 0 -1 - outer loop - vertex -8.17844 -47.0148 -75 - vertex -20.3431 -50.1686 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 30.1879 -43.3257 -75 - vertex 32.476 -18.75 -75 - vertex 50 -28.8675 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -10.2498 -63.5607 -75 - vertex -32.3359 -60.5982 -75 - vertex -20.3431 -50.1686 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -67.3575 -75 - vertex -32.3359 -60.5982 -75 - vertex -27.8383 -78.2461 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 0 -37.5 -75 - vertex -8.17844 -47.0148 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -8.17844 -47.0148 -75 - vertex -10.2498 -63.5607 -75 - vertex -20.3431 -50.1686 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -48.1125 -75 - vertex 30.1879 -43.3257 -75 - vertex 50 -28.8675 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 18.75 -32.476 -75 - vertex 32.476 -18.75 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -32.3359 -60.5982 -75 - vertex -10.2498 -63.5607 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -86.6025 -75 - vertex -50 -67.3575 -75 - vertex -27.8383 -78.2461 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 0 -37.5 -75 - vertex 8.34963 -49.0482 -75 - vertex -8.17844 -47.0148 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -67.3575 -75 - vertex -50 -48.1125 -75 - vertex -32.3359 -60.5982 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.3359 -60.5982 -75 - vertex -32.2308 -45.3474 -75 - vertex -20.3431 -50.1686 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -28.8675 -75 - vertex 32.476 -18.75 -75 - vertex 50 -9.6225 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -20.3431 -50.1686 -75 - vertex -32.2308 -45.3474 -75 - vertex -18.75 -32.476 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -48.1125 -75 - vertex -32.2308 -45.3474 -75 - vertex -32.3359 -60.5982 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 -9.6225 -75 - vertex 32.476 -18.75 -75 - vertex 37.5 0 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -36.7316 -34.2036 -75 - vertex -18.75 -32.476 -75 - vertex -32.2308 -45.3474 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -32.2308 -45.3474 -75 - vertex -50 -48.1125 -75 - vertex -36.7316 -34.2036 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -9.6225 -75 - vertex 37.5 0 -75 - vertex 50 9.6225 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -18.75 -32.476 -75 - vertex -36.7316 -34.2036 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -36.7316 -34.2036 -75 - vertex -50 -48.1125 -75 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 9.6225 -75 - vertex 37.5 0 -75 - vertex 32.476 18.75 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 34.202 -93.9693 -75 - vertex 17.3648 -98.4808 -75 - vertex 16.7654 -81.8564 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 16.7654 -81.8564 -75 - vertex 17.3648 -98.4808 -75 - vertex 0 -100 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 34.202 -93.9693 -75 - vertex 35.8735 -78.2658 -75 - vertex 50 -86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 34.202 -93.9693 -75 - vertex 16.7654 -81.8564 -75 - vertex 35.8735 -78.2658 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 0 -100 -75 - vertex -4.71315 -80.8405 -75 - vertex 16.7654 -81.8564 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 35.8735 -78.2658 -75 - vertex 50 -67.3575 -75 - vertex 50 -86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 16.7654 -81.8564 -75 - vertex 31.9366 -62.7449 -75 - vertex 35.8735 -78.2658 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -4.71315 -80.8405 -75 - vertex 0 -100 -75 - vertex -17.3648 -98.4808 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -4.71315 -80.8405 -75 - vertex 12.119 -63.9104 -75 - vertex 16.7654 -81.8564 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 31.9366 -62.7449 -75 - vertex 50 -67.3575 -75 - vertex 35.8735 -78.2658 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 31.9366 -62.7449 -75 - vertex 16.7654 -81.8564 -75 - vertex 12.119 -63.9104 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -17.3648 -98.4808 -75 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -4.71315 -80.8405 -75 - vertex -17.3648 -98.4808 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 12.119 -63.9104 -75 - vertex -4.71315 -80.8405 -75 - vertex -10.2498 -63.5607 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 12.119 -63.9104 -75 - vertex 8.34963 -49.0482 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 -48.1125 -75 - vertex 50 -67.3575 -75 - vertex 31.9366 -62.7449 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 12.119 -63.9104 -75 - vertex 30.1879 -43.3257 -75 - vertex 31.9366 -62.7449 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -10.2498 -63.5607 -75 - vertex 8.34963 -49.0482 -75 - vertex 12.119 -63.9104 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 0 -37.5 -75 - vertex 18.75 -32.476 -75 - vertex 8.34963 -49.0482 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -86.6025 -75 - vertex -27.8383 -78.2461 -75 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -27.8383 -78.2461 -75 - vertex -10.2498 -63.5607 -75 - vertex -4.71315 -80.8405 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 8.34963 -49.0482 -75 - vertex 18.75 -32.476 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 -48.1125 -75 - vertex 31.9366 -62.7449 -75 - vertex 30.1879 -43.3257 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -8.17844 -47.0148 -75 - vertex 8.34963 -49.0482 -75 - vertex -10.2498 -63.5607 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 9.37727 64.3489 -75 - vertex 14.8182 47.9341 -75 - vertex -6.73263 49.1968 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 17.3648 98.4808 -75 - vertex 34.202 93.9693 -75 - vertex 26.8879 77.9891 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 48.1125 -75 - vertex -29.95 43.1732 -75 - vertex -50 28.8675 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -6.73263 49.1968 -75 - vertex -18.75 32.476 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 26.8879 77.9891 -75 - vertex 9.37727 64.3489 -75 - vertex 1.4079 82.2671 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 9.37727 64.3489 -75 - vertex -6.73263 49.1968 -75 - vertex -12.9612 63.5763 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 17.3648 98.4808 -75 - vertex 26.8879 77.9891 -75 - vertex 1.4079 82.2671 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 48.1125 -75 - vertex -32.8384 61.9158 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -12.9612 63.5763 -75 - vertex -6.73263 49.1968 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 1.4079 82.2671 -75 - vertex 9.37727 64.3489 -75 - vertex -12.9612 63.5763 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 17.3648 98.4808 -75 - vertex 1.4079 82.2671 -75 - vertex 0 100 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 48.1125 -75 - vertex -50 67.3575 -75 - vertex -32.8384 61.9158 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -12.9612 63.5763 -75 - vertex -29.95 43.1732 -75 - vertex -32.8384 61.9158 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 1.4079 82.2671 -75 - vertex -12.9612 63.5763 -75 - vertex -20.4052 79.7278 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -17.3648 98.4808 -75 - vertex 0 100 -75 - vertex 1.4079 82.2671 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -37.0799 77.7597 -75 - vertex -50 67.3575 -75 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.8384 61.9158 -75 - vertex -50 67.3575 -75 - vertex -37.0799 77.7597 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -20.4052 79.7278 -75 - vertex -12.9612 63.5763 -75 - vertex -32.8384 61.9158 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -17.3648 98.4808 -75 - vertex 1.4079 82.2671 -75 - vertex -20.4052 79.7278 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -34.202 93.9693 -75 - vertex -37.0799 77.7597 -75 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -20.4052 79.7278 -75 - vertex -32.8384 61.9158 -75 - vertex -37.0799 77.7597 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -17.3648 98.4808 -75 - vertex -20.4052 79.7278 -75 - vertex -34.202 93.9693 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex -34.202 93.9693 -75 - vertex -20.4052 79.7278 -75 - vertex -37.0799 77.7597 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -36.7316 -34.2036 -75 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 28.8675 -75 - vertex 50 9.6225 -75 - vertex 32.476 18.75 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -50 -28.8675 -75 - vertex -50 -9.6225 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 28.8675 -75 - vertex 32.476 18.75 -75 - vertex 33.5608 39.2491 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -32.476 -18.75 -75 - vertex -50 -9.6225 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 48.1125 -75 - vertex 50 28.8675 -75 - vertex 33.5608 39.2491 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 32.476 18.75 -75 - vertex 18.75 32.476 -75 - vertex 33.5608 39.2491 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 -9.6225 -75 - vertex -50 9.6225 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 48.1125 -75 - vertex 33.5608 39.2491 -75 - vertex 31.0341 58.4031 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 33.5608 39.2491 -75 - vertex 18.75 32.476 -75 - vertex 14.8182 47.9341 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 9.6225 -75 - vertex -32.476 18.75 -75 - vertex -37.5 0 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 67.3575 -75 - vertex 50 48.1125 -75 - vertex 31.0341 58.4031 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 26.8879 77.9891 -75 - vertex 31.0341 58.4031 -75 - vertex 9.37727 64.3489 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 0 37.5 -75 - vertex -18.75 32.476 -75 - vertex -6.73263 49.1968 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex -18.75 32.476 -75 - vertex -32.476 18.75 -75 - vertex -29.95 43.1732 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -29.95 43.1732 -75 - vertex -32.476 18.75 -75 - vertex -50 28.8675 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 86.6025 -75 - vertex 26.8879 77.9891 -75 - vertex 34.202 93.9693 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 14.8182 47.9341 -75 - vertex 0 37.5 -75 - vertex -6.73263 49.1968 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 31.0341 58.4031 -75 - vertex 14.8182 47.9341 -75 - vertex 9.37727 64.3489 -75 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 50 67.3575 -75 - vertex 31.0341 58.4031 -75 - vertex 26.8879 77.9891 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex -50 28.8675 -75 - vertex -32.476 18.75 -75 - vertex -50 9.6225 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 50 86.6025 -75 - vertex 50 67.3575 -75 - vertex 26.8879 77.9891 -75 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 18.75 32.476 -75 - vertex 0 37.5 -75 - vertex 14.8182 47.9341 -75 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 31.0341 58.4031 -75 - vertex 33.5608 39.2491 -75 - vertex 14.8182 47.9341 -75 - endloop - endfacet -endsolid patch010 -solid patch011 - facet normal -1 0 0 - outer loop - vertex -50 38.9141 -40.8553 - vertex -50 48.1125 -25 - vertex -50 56.9708 -41.6522 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 32.7919 -58.1342 - vertex -50 38.9141 -40.8553 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 32.7919 -58.1342 - vertex -50 48.1125 -75 - vertex -50 28.8675 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 28.8675 -25 - vertex -50 48.1125 -25 - vertex -50 38.9141 -40.8553 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 38.9141 -40.8553 - vertex -50 32.7919 -58.1342 - vertex -50 20.6227 -41.5526 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 32.7919 -58.1342 - vertex -50 28.8675 -75 - vertex -50 14.0935 -58.3566 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 28.8675 -25 - vertex -50 38.9141 -40.8553 - vertex -50 20.6227 -41.5526 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 20.6227 -41.5526 - vertex -50 32.7919 -58.1342 - vertex -50 14.0935 -58.3566 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 14.0935 -58.3566 - vertex -50 28.8675 -75 - vertex -50 9.6225 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -86.6025 -75 - vertex -50 -86.6025 -58.3333 - vertex -50 -67.3575 -75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 28.8675 -25 - vertex -50 20.6227 -41.5526 - vertex -50 9.6225 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 20.6227 -41.5526 - vertex -50 14.0935 -58.3566 - vertex -50 1.31775 -41.8772 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 14.0935 -58.3566 - vertex -50 9.6225 -75 - vertex -50 -6.16398 -58.6027 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 48.1125 -75 - vertex -50 32.7919 -58.1342 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 38.9141 -40.8553 - vertex -50 56.9708 -41.6522 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.1125 -25 - vertex -50 67.3575 -25 - vertex -50 56.9708 -41.6522 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 66.6042 -60.9663 - vertex -50 48.1125 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 48.9286 -56.1358 - vertex -50 56.9708 -41.6522 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 56.9708 -41.6522 - vertex -50 67.3575 -25 - vertex -50 72.4408 -45.1781 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 -75 - vertex -50 48.1125 -75 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 56.9708 -41.6522 - vertex -50 72.4408 -45.1781 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 -25 - vertex -50 86.6025 -41.6667 - vertex -50 72.4408 -45.1781 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 67.3575 -75 - vertex -50 66.6042 -60.9663 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 72.4408 -45.1781 - vertex -50 86.6025 -58.3333 - vertex -50 66.6042 -60.9663 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 86.6025 -41.6667 - vertex -50 86.6025 -58.3333 - vertex -50 72.4408 -45.1781 - endloop - endfacet - facet normal -1 -0 -0 - outer loop - vertex -50 86.6025 -25 - vertex -50 86.6025 -41.6667 - vertex -50 67.3575 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 66.6042 -60.9663 - vertex -50 86.6025 -58.3333 - vertex -50 86.6025 -75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -28.8675 -25 - vertex -50 -39.6067 -42.3045 - vertex -50 -48.1125 -25 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -28.8675 -25 - vertex -50 -18.9388 -42.4878 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -61.0775 -40.8996 - vertex -50 -48.1125 -25 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -18.9388 -42.4878 - vertex -50 -29.0415 -59.9655 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -9.6225 -25 - vertex -50 -18.9388 -42.4878 - vertex -50 -28.8675 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -61.0775 -40.8996 - vertex -50 -39.6067 -42.3045 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -67.3575 -25 - vertex -50 -48.1125 -25 - vertex -50 -61.0775 -40.8996 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -18.9388 -42.4878 - vertex -50 -6.16398 -58.6027 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -39.6067 -42.3045 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -9.6225 -25 - vertex -50 1.31775 -41.8772 - vertex -50 -18.9388 -42.4878 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -70.3049 -55.1289 - vertex -50 -61.0775 -40.8996 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -67.3575 -25 - vertex -50 -61.0775 -40.8996 - vertex -50 -86.6025 -41.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -6.16398 -58.6027 - vertex -50 -9.6225 -75 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -70.3049 -55.1289 - vertex -50 -86.6025 -58.3333 - vertex -50 -86.6025 -41.6667 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -67.3575 -75 - vertex -50 -86.6025 -58.3333 - vertex -50 -70.3049 -55.1289 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 9.6225 -25 - vertex -50 20.6227 -41.5526 - vertex -50 1.31775 -41.8772 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 -75 - vertex -50 -29.0415 -59.9655 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 -75 - vertex -50 -67.3575 -75 - vertex -50 -51.7631 -58.1259 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 1.31775 -41.8772 - vertex -50 14.0935 -58.3566 - vertex -50 -6.16398 -58.6027 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -29.0415 -59.9655 - vertex -50 -9.6225 -75 - vertex -50 -28.8675 -75 - endloop - endfacet - facet normal -1 0 -0 - outer loop - vertex -50 -6.16398 -58.6027 - vertex -50 9.6225 -75 - vertex -50 -9.6225 -75 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -67.3575 -25 - vertex -50 -86.6025 -41.6667 - vertex -50 -86.6025 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -61.0775 -40.8996 - vertex -50 -70.3049 -55.1289 - vertex -50 -86.6025 -41.6667 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 -51.7631 -58.1259 - vertex -50 -67.3575 -75 - vertex -50 -70.3049 -55.1289 - endloop - endfacet - facet normal -1 -0 0 - outer loop - vertex -50 9.6225 -25 - vertex -50 1.31775 -41.8772 - vertex -50 -9.6225 -25 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 -48.1125 -75 - vertex -50 -51.7631 -58.1259 - vertex -50 -29.0415 -59.9655 - endloop - endfacet - facet normal -1 0 0 - outer loop - vertex -50 1.31775 -41.8772 - vertex -50 -6.16398 -58.6027 - vertex -50 -18.9388 -42.4878 - endloop - endfacet -endsolid patch011 -solid patch012 - facet normal -0 0 -1 - outer loop - vertex 93.9693 34.202 -25 - vertex 81.2015 24.5598 -25 - vertex 77.7882 41.2953 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 81.2015 24.5598 -25 - vertex 75 10 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 58.9285 18.1069 -25 - vertex 50 9.6225 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 67.5854 27.0152 -25 - vertex 67.9289 7.07107 -25 - vertex 58.9285 18.1069 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 81.2015 24.5598 -25 - vertex 93.9693 34.202 -25 - vertex 90.4705 14.6652 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 82.0711 7.07107 -25 - vertex 75 10 -25 - vertex 81.2015 24.5598 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 58.9285 18.1069 -25 - vertex 67.9289 7.07107 -25 - vertex 50 9.6225 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 90.4705 14.6652 -25 - vertex 93.9693 34.202 -25 - vertex 98.4808 17.3648 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 90.4705 14.6652 -25 - vertex 82.0711 7.07107 -25 - vertex 81.2015 24.5598 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 9.6225 -25 - vertex 67.9289 7.07107 -25 - vertex 65 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 100 0 -25 - vertex 90.4705 14.6652 -25 - vertex 98.4808 17.3648 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 85 0 -25 - vertex 82.0711 7.07107 -25 - vertex 90.4705 14.6652 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -9.6225 -25 - vertex 50 9.6225 -25 - vertex 65 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 85 0 -25 - vertex 90.4705 14.6652 -25 - vertex 100 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 67.5854 27.0152 -25 - vertex 58.9285 18.1069 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 75 10 -25 - vertex 67.9289 7.07107 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 77.7882 41.2953 -25 - vertex 81.2015 24.5598 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 86.6025 50 -25 - vertex 93.9693 34.202 -25 - vertex 77.7882 41.2953 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 64.1232 44.519 -25 - vertex 67.5854 27.0152 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 77.7882 41.2953 -25 - vertex 67.5854 27.0152 -25 - vertex 64.1232 44.519 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 86.6025 50 -25 - vertex 77.7882 41.2953 -25 - vertex 76.6044 64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 28.8675 -25 - vertex 50 48.1125 -25 - vertex 64.1232 44.519 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 64.1232 44.519 -25 - vertex 76.6044 64.2788 -25 - vertex 77.7882 41.2953 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 64.1232 44.519 -25 - vertex 50 48.1125 -25 - vertex 61.4484 60.172 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 76.6044 64.2788 -25 - vertex 64.1232 44.519 -25 - vertex 61.4484 60.172 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 61.4484 60.172 -25 - vertex 50 48.1125 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 64.2788 76.6044 -25 - vertex 76.6044 64.2788 -25 - vertex 61.4484 60.172 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 64.2788 76.6044 -25 - vertex 61.4484 60.172 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 86.6025 -25 - vertex 64.2788 76.6044 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 77.4232 -43.4472 -25 - vertex 86.6025 -50 -25 - vertex 76.6044 -64.2788 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 86.6025 -50 -25 - vertex 77.4232 -43.4472 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 65.9129 -50.6425 -25 - vertex 77.4232 -43.4472 -25 - vertex 76.6044 -64.2788 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 77.4232 -43.4472 -25 - vertex 76.5403 -27.9427 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 76.6044 -64.2788 -25 - vertex 61.2753 -61.6257 -25 - vertex 65.9129 -50.6425 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 77.4232 -43.4472 -25 - vertex 65.9129 -50.6425 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 63.2012 -36.5076 -25 - vertex 76.5403 -27.9427 -25 - vertex 77.4232 -43.4472 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 76.5403 -27.9427 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 61.2753 -61.6257 -25 - vertex 76.6044 -64.2788 -25 - vertex 64.2788 -76.6044 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 61.2753 -61.6257 -25 - vertex 50 -48.1125 -25 - vertex 65.9129 -50.6425 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 65.9129 -50.6425 -25 - vertex 50 -48.1125 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 76.5403 -27.9427 -25 - vertex 63.2012 -36.5076 -25 - vertex 62.9265 -20.6629 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 76.5403 -27.9427 -25 - vertex 75 -10 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 93.9693 -34.202 -25 - vertex 86.3348 -19.8135 -25 - vertex 98.4808 -17.3648 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -67.3575 -25 - vertex 61.2753 -61.6257 -25 - vertex 64.2788 -76.6044 -25 - endloop - endfacet - facet normal -0 0 -1 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 50 -9.6225 -25 - vertex 65 0 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 85 0 -25 - vertex 100 0 -25 - vertex 91.3679 -8.97975 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 85 0 -25 - vertex 91.3679 -8.97975 -25 - vertex 82.0711 -7.07107 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 62.9265 -20.6629 -25 - vertex 50 -9.6225 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 100 0 -25 - vertex 98.4808 -17.3648 -25 - vertex 91.3679 -8.97975 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 82.0711 -7.07107 -25 - vertex 91.3679 -8.97975 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -9.6225 -25 - vertex 62.9265 -20.6629 -25 - vertex 50 -28.8675 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 75 -10 -25 - vertex 62.9265 -20.6629 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -67.3575 -25 - vertex 64.2788 -76.6044 -25 - vertex 50 -86.6025 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 91.3679 -8.97975 -25 - vertex 98.4808 -17.3648 -25 - vertex 86.3348 -19.8135 -25 - endloop - endfacet - facet normal 0 -0 -1 - outer loop - vertex 82.0711 -7.07107 -25 - vertex 86.3348 -19.8135 -25 - vertex 75 -10 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -28.8675 -25 - vertex 62.9265 -20.6629 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 62.9265 -20.6629 -25 - vertex 75 -10 -25 - vertex 76.5403 -27.9427 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -28.8675 -25 - vertex 63.2012 -36.5076 -25 - endloop - endfacet - facet normal 0 0 -1 - outer loop - vertex 50 -67.3575 -25 - vertex 50 -48.1125 -25 - vertex 61.2753 -61.6257 -25 - endloop - endfacet -endsolid patch012 -solid patch013 - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -51.5177 -41.872 - vertex 50 -28.0125 -40.2176 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -39.6697 -57.6908 - vertex 50 -61.1182 -59.0886 - vertex 50 -48.1125 -75 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -28.0125 -40.2176 - vertex 50 -28.8675 -25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.9599 -41.2947 - vertex 50 67.3575 -25 - vertex 50 58.5014 -41.5594 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 74.9599 -41.2947 - vertex 50 70.779 -58.5287 - vertex 50 86.6025 -58.3333 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -39.6697 -57.6908 - vertex 50 -28.0125 -40.2176 - vertex 50 -51.5177 -41.872 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -28.8675 -75 - vertex 50 -39.6697 -57.6908 - vertex 50 -48.1125 -75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -28.0125 -40.2176 - vertex 50 -9.6225 -25 - vertex 50 -28.8675 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 58.5014 -41.5594 - vertex 50 67.3575 -25 - vertex 50 48.1125 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 70.779 -58.5287 - vertex 50 74.9599 -41.2947 - vertex 50 58.5014 -41.5594 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 -58.3333 - vertex 50 70.779 -58.5287 - vertex 50 86.6025 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -28.0125 -40.2176 - vertex 50 -39.6697 -57.6908 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -28.8675 -75 - vertex 50 -19.3334 -57.7609 - vertex 50 -39.6697 -57.6908 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -61.1182 -59.0886 - vertex 50 -39.6697 -57.6908 - vertex 50 -51.5177 -41.872 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 86.6025 -41.6667 - vertex 50 74.9599 -41.2947 - vertex 50 86.6025 -58.3333 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 74.9599 -41.2947 - vertex 50 86.6025 -25 - vertex 50 67.3575 -25 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 -75 - vertex 50 -61.1182 -59.0886 - vertex 50 -67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -48.1125 -25 - vertex 50 -67.3575 -25 - vertex 50 -51.5177 -41.872 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -51.5177 -41.872 - vertex 50 -70.2628 -44.8561 - vertex 50 -61.1182 -59.0886 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 86.6025 -41.6667 - vertex 50 86.6025 -25 - vertex 50 74.9599 -41.2947 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -61.1182 -59.0886 - vertex 50 -86.6025 -58.3333 - vertex 50 -67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -51.5177 -41.872 - vertex 50 -67.3575 -25 - vertex 50 -70.2628 -44.8561 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -70.2628 -44.8561 - vertex 50 -86.6025 -58.3333 - vertex 50 -61.1182 -59.0886 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 -58.3333 - vertex 50 -86.6025 -75 - vertex 50 -67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -67.3575 -25 - vertex 50 -86.6025 -41.6667 - vertex 50 -70.2628 -44.8561 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -86.6025 -41.6667 - vertex 50 -86.6025 -58.3333 - vertex 50 -70.2628 -44.8561 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -86.6025 -25 - vertex 50 -86.6025 -41.6667 - vertex 50 -67.3575 -25 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 14.8663 -58.4416 - vertex 50 28.8675 -75 - vertex 50 33.981 -58.2872 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 14.8663 -58.4416 - vertex 50 9.6225 -75 - vertex 50 28.8675 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 33.981 -58.2872 - vertex 50 28.8675 -75 - vertex 50 48.1125 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 19.8883 -41.7934 - vertex 50 14.8663 -58.4416 - vertex 50 33.981 -58.2872 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -1.76026 -61.2305 - vertex 50 9.6225 -75 - vertex 50 14.8663 -58.4416 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 33.981 -58.2872 - vertex 50 48.1125 -75 - vertex 50 52.8706 -58.3816 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 14.8663 -58.4416 - vertex 50 19.8883 -41.7934 - vertex 50 -2.82931 -43.2484 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 33.981 -58.2872 - vertex 50 39.9586 -41.6283 - vertex 50 19.8883 -41.7934 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -9.6225 -75 - vertex 50 9.6225 -75 - vertex 50 -1.76026 -61.2305 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -2.82931 -43.2484 - vertex 50 -1.76026 -61.2305 - vertex 50 14.8663 -58.4416 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 52.8706 -58.3816 - vertex 50 48.1125 -75 - vertex 50 67.3575 -75 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.9586 -41.6283 - vertex 50 33.981 -58.2872 - vertex 50 52.8706 -58.3816 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 19.8883 -41.7934 - vertex 50 9.6225 -25 - vertex 50 -2.82931 -43.2484 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -2.82931 -43.2484 - vertex 50 -9.6225 -25 - vertex 50 -28.0125 -40.2176 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 58.5014 -41.5594 - vertex 50 48.1125 -25 - vertex 50 39.9586 -41.6283 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 58.5014 -41.5594 - vertex 50 52.8706 -58.3816 - vertex 50 70.779 -58.5287 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 70.779 -58.5287 - vertex 50 67.3575 -75 - vertex 50 86.6025 -75 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -2.82931 -43.2484 - vertex 50 -28.0125 -40.2176 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -28.8675 -75 - vertex 50 -9.6225 -75 - vertex 50 -19.3334 -57.7609 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 39.9586 -41.6283 - vertex 50 48.1125 -25 - vertex 50 28.8675 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 19.8883 -41.7934 - vertex 50 28.8675 -25 - vertex 50 9.6225 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 -2.82931 -43.2484 - vertex 50 9.6225 -25 - vertex 50 -9.6225 -25 - endloop - endfacet - facet normal 1 0 -0 - outer loop - vertex 50 52.8706 -58.3816 - vertex 50 58.5014 -41.5594 - vertex 50 39.9586 -41.6283 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 52.8706 -58.3816 - vertex 50 67.3575 -75 - vertex 50 70.779 -58.5287 - endloop - endfacet - facet normal 1 -0 0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -1.76026 -61.2305 - vertex 50 -2.82931 -43.2484 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 -19.3334 -57.7609 - vertex 50 -9.6225 -75 - vertex 50 -1.76026 -61.2305 - endloop - endfacet - facet normal 1 0 0 - outer loop - vertex 50 39.9586 -41.6283 - vertex 50 28.8675 -25 - vertex 50 19.8883 -41.7934 - endloop - endfacet -endsolid patch013 -solid patch014 - facet normal 0.104348 -0.704047 -0.702445 - outer loop - vertex 38.627 -36.0851 55.6013 - vertex 50 -39.3934 60.6066 - vertex 38.7419 -44.3385 63.8906 - endloop - endfacet - facet normal 0.10103 -0.380725 -0.919152 - outer loop - vertex 27.5 -39.3934 60.6066 - vertex 38.7419 -44.3385 63.8906 - vertex 27.5 -50 65 - endloop - endfacet - facet normal 0.0834026 0.940134 0.330442 - outer loop - vertex 27.5 -65 50 - vertex 36.6956 -63.5667 43.6012 - vertex 20 -60.6066 39.3934 - endloop - endfacet - facet normal 0.0734473 0.691469 0.718662 - outer loop - vertex 36.6956 -63.5667 43.6012 - vertex 50 -60.6066 39.3934 - vertex 35.0899 -55.5723 36.0734 - endloop - endfacet - facet normal -0.100886 -0.380731 -0.919166 - outer loop - vertex 50 -39.3934 60.6066 - vertex 50 -50 65 - vertex 38.7419 -44.3385 63.8906 - endloop - endfacet - facet normal -0.102648 0.00891307 -0.994678 - outer loop - vertex 27.5 -50 65 - vertex 38.7419 -44.3385 63.8906 - vertex 38.7411 -55.9092 63.787 - endloop - endfacet - facet normal -0.117752 0.991633 0.0529011 - outer loop - vertex 36.6956 -63.5667 43.6012 - vertex 27.5 -65 50 - vertex 38.6185 -63.971 55.46 - endloop - endfacet - facet normal -0 0.92388 0.382683 - outer loop - vertex 20 -65 50 - vertex 27.5 -65 50 - vertex 20 -60.6066 39.3934 - endloop - endfacet - facet normal -0.084222 0.920597 0.381324 - outer loop - vertex 50 -65 50 - vertex 50 -60.6066 39.3934 - vertex 36.6956 -63.5667 43.6012 - endloop - endfacet - facet normal 0.102495 0.00889901 -0.994694 - outer loop - vertex 38.7419 -44.3385 63.8906 - vertex 50 -50 65 - vertex 38.7411 -55.9092 63.787 - endloop - endfacet - facet normal 0.100956 0.380728 -0.919159 - outer loop - vertex 27.5 -50 65 - vertex 38.7411 -55.9092 63.787 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal 0.101889 0.919071 -0.380692 - outer loop - vertex 38.6185 -63.971 55.46 - vertex 27.5 -65 50 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal 0.0985611 0.994969 0.0179397 - outer loop - vertex 38.6185 -63.971 55.46 - vertex 50 -65 50 - vertex 36.6956 -63.5667 43.6012 - endloop - endfacet - facet normal -0.100798 0.380734 -0.919174 - outer loop - vertex 50 -60.6066 60.6066 - vertex 38.7411 -55.9092 63.787 - vertex 50 -50 65 - endloop - endfacet - facet normal -0.103416 0.715363 -0.691058 - outer loop - vertex 38.7411 -55.9092 63.787 - vertex 38.6185 -63.971 55.46 - vertex 27.5 -60.6066 60.6066 - endloop - endfacet - facet normal -0.0995582 0.919289 -0.380782 - outer loop - vertex 50 -60.6066 60.6066 - vertex 50 -65 50 - vertex 38.6185 -63.971 55.46 - endloop - endfacet - facet normal 0.102193 0.713941 -0.692708 - outer loop - vertex 50 -60.6066 60.6066 - vertex 38.6185 -63.971 55.46 - vertex 38.7411 -55.9092 63.787 - endloop - endfacet - facet normal -0.0651247 -0.681101 0.729288 - outer loop - vertex 36.7146 -36.3923 43.6888 - vertex 20 -39.3934 39.3934 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal 0.0839959 -0.940217 0.330056 - outer loop - vertex 20 -39.3934 39.3934 - vertex 36.7146 -36.3923 43.6888 - vertex 27.5 -35 50 - endloop - endfacet - facet normal 0.0754102 -0.381594 0.921249 - outer loop - vertex 20 -50 35 - vertex 35.0929 -44.3639 36.0991 - vertex 20 -39.3934 39.3934 - endloop - endfacet - facet normal 0.0739638 -0.695508 0.714701 - outer loop - vertex 35.0929 -44.3639 36.0991 - vertex 50 -39.3934 39.3934 - vertex 36.7146 -36.3923 43.6888 - endloop - endfacet - facet normal -0.119237 -0.991858 0.0447202 - outer loop - vertex 27.5 -35 50 - vertex 36.7146 -36.3923 43.6888 - vertex 38.627 -36.0851 55.6013 - endloop - endfacet - facet normal 0 -0.92388 0.382683 - outer loop - vertex 20 -35 50 - vertex 20 -39.3934 39.3934 - vertex 27.5 -35 50 - endloop - endfacet - facet normal -0.0717873 -0.00226776 0.997417 - outer loop - vertex 20 -50 35 - vertex 35.0899 -55.5723 36.0734 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal -0.0846659 -0.920562 0.381309 - outer loop - vertex 50 -39.3934 39.3934 - vertex 50 -35 50 - vertex 36.7146 -36.3923 43.6888 - endloop - endfacet - facet normal -0.0763446 -0.381567 0.921183 - outer loop - vertex 50 -50 35 - vertex 50 -39.3934 39.3934 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal 0.0996856 -0.994972 0.00965525 - outer loop - vertex 36.7146 -36.3923 43.6888 - vertex 50 -35 50 - vertex 38.627 -36.0851 55.6013 - endloop - endfacet - facet normal 0.102011 -0.91906 -0.380687 - outer loop - vertex 27.5 -35 50 - vertex 38.627 -36.0851 55.6013 - vertex 27.5 -39.3934 60.6066 - endloop - endfacet - facet normal 0.0753809 0.381595 0.921251 - outer loop - vertex 20 -60.6066 39.3934 - vertex 35.0899 -55.5723 36.0734 - vertex 20 -50 35 - endloop - endfacet - facet normal 0.0726628 -0.00230626 0.997354 - outer loop - vertex 35.0899 -55.5723 36.0734 - vertex 50 -50 35 - vertex 35.0929 -44.3639 36.0991 - endloop - endfacet - facet normal -0.0998263 -0.919265 -0.380772 - outer loop - vertex 50 -35 50 - vertex 50 -39.3934 60.6066 - vertex 38.627 -36.0851 55.6013 - endloop - endfacet - facet normal -0.105552 -0.705412 -0.700894 - outer loop - vertex 27.5 -39.3934 60.6066 - vertex 38.627 -36.0851 55.6013 - vertex 38.7419 -44.3385 63.8906 - endloop - endfacet - facet normal -0.0646634 0.677192 0.73296 - outer loop - vertex 20 -60.6066 39.3934 - vertex 36.6956 -63.5667 43.6012 - vertex 35.0899 -55.5723 36.0734 - endloop - endfacet - facet normal -0.0762847 0.381568 0.921187 - outer loop - vertex 50 -60.6066 39.3934 - vertex 50 -50 35 - vertex 35.0899 -55.5723 36.0734 - endloop - endfacet -endsolid patch014 -solid patch015 - facet normal 0.58885 0.808055 0.0174243 - outer loop - vertex 50 86.6025 25 - vertex 65.7761 75.3227 14.953 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.433807 0.901 -0.00339618 - outer loop - vertex 50 86.6025 25 - vertex 36.3222 93.1703 20.308 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.291666 0.956168 -0.0259645 - outer loop - vertex 27.5 96.1444 50 - vertex 37.053 92.882 37.1706 - vertex 20 97.9796 33.3333 - endloop - endfacet - facet normal 0.775048 0.630673 0.0394032 - outer loop - vertex 83.5447 54.9571 -0.204582 - vertex 76.6544 64.2192 -12.9205 - vertex 70.3409 71.0786 1.47508 - endloop - endfacet - facet normal 0.731503 0.681025 0.0333006 - outer loop - vertex 79.3607 60.8431 12.6644 - vertex 70.3409 71.0786 1.47508 - vertex 65.7761 75.3227 14.953 - endloop - endfacet - facet normal 0.819153 0.573575 -0.000560831 - outer loop - vertex 86.6025 50 -25 - vertex 76.6044 64.2788 -25 - vertex 76.6544 64.2192 -12.9205 - endloop - endfacet - facet normal 0.258768 -0.965737 -0.0197785 - outer loop - vertex 17.3648 -98.4808 -75 - vertex 34.202 -93.9693 -75 - vertex 25.4911 -96.6964 -55.8091 - endloop - endfacet - facet normal 0.323439 -0.946205 -0.00908788 - outer loop - vertex 38.8506 -92.1446 -54.264 - vertex 36.2141 -93.2123 -36.9311 - vertex 25.4911 -96.6964 -55.8091 - endloop - endfacet - facet normal 0.432336 -0.901713 0 - outer loop - vertex 50 -86.6025 -25 - vertex 36.2141 -93.2123 -36.9311 - vertex 50 -86.6025 -41.6667 - endloop - endfacet - facet normal 0.454066 -0.888761 0.0626776 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 50 -86.6025 -25 - vertex 56.9654 -82.1884 -12.8692 - endloop - endfacet - facet normal 0.423698 -0.905802 0.0017863 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 49.9874 -86.6098 -1.35914 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.272851 -0.962055 -0.00160303 - outer loop - vertex 20 -97.9796 0 - vertex 34.7327 -93.7744 -16.0932 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.428063 -0.903729 0.00605391 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 36.2141 -93.2123 -36.9311 - vertex 50 -86.6025 -25 - endloop - endfacet - facet normal 0.285276 -0.958331 0.0148273 - outer loop - vertex 20.5118 -97.8737 -36.1001 - vertex 25.4911 -96.6964 -55.8091 - vertex 36.2141 -93.2123 -36.9311 - endloop - endfacet - facet normal 0.173397 -0.984685 0.0181329 - outer loop - vertex 9.04165 -99.5904 -55.6649 - vertex 17.3648 -98.4808 -75 - vertex 25.4911 -96.6964 -55.8091 - endloop - endfacet - facet normal 0.707107 0.707107 0.000561832 - outer loop - vertex 76.6544 64.2192 -12.9205 - vertex 76.6044 64.2788 -25 - vertex 64.2788 76.6044 -25 - endloop - endfacet - facet normal 0.611531 0.790121 -0.041686 - outer loop - vertex 65.7761 75.3227 14.953 - vertex 70.3409 71.0786 1.47508 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.688791 0.723698 -0.0427524 - outer loop - vertex 70.3409 71.0786 1.47508 - vertex 76.6544 64.2192 -12.9205 - vertex 61.2701 79.0315 -10.042 - endloop - endfacet - facet normal 0.285574 0.958348 0.00400851 - outer loop - vertex 36.3222 93.1703 20.308 - vertex 20 97.9796 33.3333 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.437623 0.898992 -0.0173307 - outer loop - vertex 50 86.6025 25 - vertex 53.0082 84.7946 7.18018 - vertex 36.3222 93.1703 20.308 - endloop - endfacet - facet normal 0.167018 -0.985953 0.00121489 - outer loop - vertex 14.1378 -98.9956 -18.6292 - vertex 20 -97.9796 0 - vertex 13.3836 -99.1004 0 - endloop - endfacet - facet normal 0.248606 -0.968271 -0.0254232 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 20 -97.9796 0 - vertex 14.1378 -98.9956 -18.6292 - endloop - endfacet - facet normal 0.906047 0.4225 -0.0239391 - outer loop - vertex 93.9693 34.202 -25 - vertex 86.6025 50 -25 - vertex 88.8787 45.8321 -12.4096 - endloop - endfacet - facet normal 0.818931 0.57342 0.0232758 - outer loop - vertex 86.6025 50 25 - vertex 79.3607 60.8431 12.6644 - vertex 76.6044 64.2788 25 - endloop - endfacet - facet normal 0.885786 0.462231 0.0415341 - outer loop - vertex 92.8747 37.0715 -0.1349 - vertex 88.8787 45.8321 -12.4096 - vertex 83.5447 54.9571 -0.204582 - endloop - endfacet - facet normal 0.847894 0.529095 0.0336729 - outer loop - vertex 89.4625 44.6818 12.2368 - vertex 83.5447 54.9571 -0.204582 - vertex 79.3607 60.8431 12.6644 - endloop - endfacet - facet normal 0.237696 0.971332 -0.00397865 - outer loop - vertex 20 97.9796 33.3333 - vertex 22.5155 97.4323 50 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0.334482 0.942402 -0 - outer loop - vertex 27.5 96.1444 50 - vertex 27.5 96.1444 62.5 - vertex 39.2656 91.9685 55.8745 - endloop - endfacet - facet normal 0.438629 0.898633 -0.0079985 - outer loop - vertex 39.2656 91.9685 55.8745 - vertex 50 86.6025 41.6667 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.707025 0.707025 0.0151721 - outer loop - vertex 76.6044 64.2788 25 - vertex 65.7761 75.3227 14.953 - vertex 64.2788 76.6044 25 - endloop - endfacet - facet normal 0.272444 -0.962172 3.14028e-05 - outer loop - vertex 20 -97.9796 16.6667 - vertex 34.3321 -93.9218 4.1825 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.416355 -0.90891 -0.0230588 - outer loop - vertex 49.9874 -86.6098 -1.35914 - vertex 46.1781 -88.6994 12.2251 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.467725 -0.882142 -0.0553012 - outer loop - vertex 34.7327 -93.7744 -16.0932 - vertex 56.9654 -82.1884 -12.8692 - vertex 49.9874 -86.6098 -1.35914 - endloop - endfacet - facet normal 0.573295 -0.818752 -0.0312573 - outer loop - vertex 56.9654 -82.1884 -12.8692 - vertex 50 -86.6025 -25 - vertex 64.2788 -76.6044 -25 - endloop - endfacet - facet normal 0.435315 -0.900214 0.0107625 - outer loop - vertex 36.2141 -93.2123 -36.9311 - vertex 38.8506 -92.1446 -54.264 - vertex 50 -86.6025 -41.6667 - endloop - endfacet - facet normal 0.32132 -0.946903 0.0112908 - outer loop - vertex 25.4911 -96.6964 -55.8091 - vertex 34.202 -93.9693 -75 - vertex 38.8506 -92.1446 -54.264 - endloop - endfacet - facet normal 0.831879 0.553975 0.0329926 - outer loop - vertex 88.8787 45.8321 -12.4096 - vertex 86.6025 50 -25 - vertex 76.6544 64.2192 -12.9205 - endloop - endfacet - facet normal 0.72671 0.686341 -0.0287807 - outer loop - vertex 76.6044 64.2788 25 - vertex 79.3607 60.8431 12.6644 - vertex 65.7761 75.3227 14.953 - endloop - endfacet - facet normal 0.832384 0.552034 -0.0489449 - outer loop - vertex 76.6544 64.2192 -12.9205 - vertex 83.5447 54.9571 -0.204582 - vertex 88.8787 45.8321 -12.4096 - endloop - endfacet - facet normal 0.770969 0.635611 -0.0400557 - outer loop - vertex 79.3607 60.8431 12.6644 - vertex 83.5447 54.9571 -0.204582 - vertex 70.3409 71.0786 1.47508 - endloop - endfacet - facet normal 0.262571 0.964839 -0.0119167 - outer loop - vertex 27.5 96.1444 50 - vertex 20 97.9796 33.3333 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0.331425 0.943457 0.00687255 - outer loop - vertex 27.5 96.1444 50 - vertex 39.2656 91.9685 55.8745 - vertex 37.053 92.882 37.1706 - endloop - endfacet - facet normal 0.436396 0.899755 -0 - outer loop - vertex 50 86.6025 25 - vertex 37.053 92.882 37.1706 - vertex 50 86.6025 41.6667 - endloop - endfacet - facet normal 0.573472 0.819005 -0.0190166 - outer loop - vertex 50 86.6025 25 - vertex 64.2788 76.6044 25 - vertex 65.7761 75.3227 14.953 - endloop - endfacet - facet normal 0.272419 -0.962179 0 - outer loop - vertex 20 -97.9796 16.6667 - vertex 20 -97.9796 0 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.413659 0.910426 -0.00328654 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 47.4798 88.0095 -7.63112 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal 0.0503692 -0.998522 0.0204119 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex 14.1378 -98.9956 -18.6292 - vertex -4.15257 -99.9137 -18.4073 - endloop - endfacet - facet normal -0.0715548 -0.997201 0.0216807 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex -16.4069 -98.6449 -37.1516 - vertex -9.63293 -99.535 -55.7352 - endloop - endfacet - facet normal -0.199716 -0.979494 0.0265557 - outer loop - vertex -17.3648 -98.4808 -75 - vertex -9.63293 -99.535 -55.7352 - vertex -30.515 -95.2304 -54.0087 - endloop - endfacet - facet normal -0.258798 -0.96585 -0.0125693 - outer loop - vertex -17.3648 -98.4808 -75 - vertex -30.515 -95.2304 -54.0087 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal -0.422622 -0.906306 -0 - outer loop - vertex -50 -86.6025 -58.3333 - vertex -50 -86.6025 -75 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal -0.0335579 -0.999433 0.00288455 - outer loop - vertex -4.15257 -99.9137 -18.4073 - vertex 0 -100 0 - vertex -6.70689 -99.7748 0 - endloop - endfacet - facet normal 0.408034 0.912814 0.0167032 - outer loop - vertex 50 86.6025 -58.3333 - vertex 34.202 93.9693 -75 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.417636 0.908521 -0.012998 - outer loop - vertex 47.4798 88.0095 -7.63112 - vertex 50 86.6025 -25 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal 0.404996 0.914318 -0 - outer loop - vertex 50 86.6025 -58.3333 - vertex 30.5386 95.2229 -54.0167 - vertex 50 86.6025 -41.6667 - endloop - endfacet - facet normal 0.42214 0.906531 0 - outer loop - vertex 50 86.6025 -25 - vertex 50 86.6025 -41.6667 - vertex 34.1021 94.0056 -33.0557 - endloop - endfacet - facet normal 0.278055 0.960557 0.00382099 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 34.7811 93.7564 -13.9596 - vertex 20 97.9796 0 - endloop - endfacet - facet normal -0.314023 -0.949415 -0 - outer loop - vertex -27.5 -96.1444 75 - vertex -35.2517 -93.5805 75 - vertex -27.5 -96.1444 62.5 - endloop - endfacet - facet normal -0.0713915 -0.997231 -0.0208293 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex -4.15257 -99.9137 -18.4073 - vertex -16.4069 -98.6449 -37.1516 - endloop - endfacet - facet normal -0.203997 -0.978586 -0.0274879 - outer loop - vertex -16.4069 -98.6449 -37.1516 - vertex -30.515 -95.2304 -54.0087 - vertex -9.63293 -99.535 -55.7352 - endloop - endfacet - facet normal -0.40794 -0.912854 0.0168105 - outer loop - vertex -30.515 -95.2304 -54.0087 - vertex -50 -86.6025 -58.3333 - vertex -34.202 -93.9693 -75 - endloop - endfacet - facet normal -0.100494 -0.994917 -0.00643809 - outer loop - vertex -13.3836 -99.1004 0 - vertex -4.15257 -99.9137 -18.4073 - vertex -6.70689 -99.7748 0 - endloop - endfacet - facet normal 0.258798 0.96585 -0.01252 - outer loop - vertex 17.3648 98.4808 -75 - vertex 30.5386 95.2229 -54.0167 - vertex 34.202 93.9693 -75 - endloop - endfacet - facet normal 0.423485 0.905897 -0.00323615 - outer loop - vertex 34.7811 93.7564 -13.9596 - vertex 50 86.6025 -25 - vertex 34.1021 94.0056 -33.0557 - endloop - endfacet - facet normal 0.414236 0.91 -0.0175749 - outer loop - vertex 34.1021 94.0056 -33.0557 - vertex 50 86.6025 -41.6667 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.277165 0.960818 0.00279924 - outer loop - vertex 20.6881 97.8366 -19.0489 - vertex 20 97.9796 0 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal -0.46423 -0.885715 0 - outer loop - vertex -50 -86.6025 58.3333 - vertex -42.7684 -90.3928 75 - vertex -50 -86.6025 75 - endloop - endfacet - facet normal -0.390421 -0.920626 0.00434297 - outer loop - vertex -35.2517 -93.5805 75 - vertex -42.7684 -90.3928 75 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal 0.284307 -0.958717 -0.00564927 - outer loop - vertex 36.2141 -93.2123 -36.9311 - vertex 34.7327 -93.7744 -16.0932 - vertex 20.5118 -97.8737 -36.1001 - endloop - endfacet - facet normal 0.173124 -0.984785 -0.0150871 - outer loop - vertex 25.4911 -96.6964 -55.8091 - vertex 20.5118 -97.8737 -36.1001 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal 0.0871378 -0.996002 -0.0196486 - outer loop - vertex 0 -100 -75 - vertex 17.3648 -98.4808 -75 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal 0.695669 0.71798 0.0234289 - outer loop - vertex 76.6544 64.2192 -12.9205 - vertex 64.2788 76.6044 -25 - vertex 61.2701 79.0315 -10.042 - endloop - endfacet - facet normal 0.628374 0.776803 0.0415027 - outer loop - vertex 70.3409 71.0786 1.47508 - vertex 61.2701 79.0315 -10.042 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.282634 0.959228 -0 - outer loop - vertex 20 97.9796 16.6667 - vertex 20 97.9796 33.3333 - vertex 36.3222 93.1703 20.308 - endloop - endfacet - facet normal 0.445833 0.895105 -0.00441516 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 36.3222 93.1703 20.308 - vertex 53.0082 84.7946 7.18018 - endloop - endfacet - facet normal 0.100496 -0.994936 -0.00152878 - outer loop - vertex 6.70689 -99.7748 0 - vertex 14.1378 -98.9956 -18.6292 - vertex 13.3836 -99.1004 0 - endloop - endfacet - facet normal 0.242622 -0.969766 0.0262437 - outer loop - vertex 14.1378 -98.9956 -18.6292 - vertex 20.5118 -97.8737 -36.1001 - vertex 34.7327 -93.7744 -16.0932 - endloop - endfacet - facet normal 0.112766 -0.993399 0.0210544 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex 9.04165 -99.5904 -55.6649 - vertex 20.5118 -97.8737 -36.1001 - endloop - endfacet - facet normal -0.00305076 -0.99974 0.0226053 - outer loop - vertex -9.63293 -99.535 -55.7352 - vertex 0 -100 -75 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal 0.573487 0.819027 -0.017543 - outer loop - vertex 61.2701 79.0315 -10.042 - vertex 64.2788 76.6044 -25 - vertex 50 86.6025 -25 - endloop - endfacet - facet normal 0.542972 0.839502 -0.0204476 - outer loop - vertex 53.0082 84.7946 7.18018 - vertex 61.2701 79.0315 -10.042 - vertex 47.4798 88.0095 -7.63112 - endloop - endfacet - facet normal 0.281841 0.959453 0.00385484 - outer loop - vertex 20 97.9796 16.6667 - vertex 36.3222 93.1703 20.308 - vertex 35.6132 93.4436 4.12214 - endloop - endfacet - facet normal 0.440748 0.897122 0.030215 - outer loop - vertex 35.6132 93.4436 4.12214 - vertex 53.0082 84.7946 7.18018 - vertex 47.4798 88.0095 -7.63112 - endloop - endfacet - facet normal 0.0498558 -0.998517 -0.0218783 - outer loop - vertex 6.70689 -99.7748 0 - vertex -4.15257 -99.9137 -18.4073 - vertex 14.1378 -98.9956 -18.6292 - endloop - endfacet - facet normal 0.115023 -0.993123 -0.0218091 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex 20.5118 -97.8737 -36.1001 - vertex 14.1378 -98.9956 -18.6292 - endloop - endfacet - facet normal -0.00288355 -0.999758 -0.0218298 - outer loop - vertex 2.17111 -99.9764 -37.0793 - vertex -9.63293 -99.535 -55.7352 - vertex 9.04165 -99.5904 -55.6649 - endloop - endfacet - facet normal -0.087138 -0.996005 -0.0195307 - outer loop - vertex -17.3648 -98.4808 -75 - vertex 0 -100 -75 - vertex -9.63293 -99.535 -55.7352 - endloop - endfacet - facet normal 0.0335555 -0.999362 -0.0122555 - outer loop - vertex 6.70689 -99.7748 0 - vertex 0 -100 0 - vertex -4.15257 -99.9137 -18.4073 - endloop - endfacet - facet normal 0.422622 0.906306 0 - outer loop - vertex 50 86.6025 -58.3333 - vertex 50 86.6025 -75 - vertex 34.202 93.9693 -75 - endloop - endfacet - facet normal 0.546981 0.837065 0.0115582 - outer loop - vertex 50 86.6025 -25 - vertex 47.4798 88.0095 -7.63112 - vertex 61.2701 79.0315 -10.042 - endloop - endfacet - facet normal 0.278988 0.960295 0 - outer loop - vertex 20 97.9796 16.6667 - vertex 35.6132 93.4436 4.12214 - vertex 20 97.9796 0 - endloop - endfacet - facet normal 0.329269 -0.944177 -0.0105293 - outer loop - vertex 27.5 -96.1444 62.5 - vertex 39.2665 -91.9681 55.9636 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0.447137 -0.894466 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 50 -86.6025 58.3333 - vertex 39.2665 -91.9681 55.9636 - endloop - endfacet - facet normal 0.81914 -0.573566 -0.00564515 - outer loop - vertex 86.6025 -50 25 - vertex 76.6044 -64.2788 25 - vertex 76.1299 -64.8401 13.1775 - endloop - endfacet - facet normal 0.916847 -0.397555 0.0366157 - outer loop - vertex 93.9693 -34.202 -25 - vertex 95.647 -29.1831 -12.5165 - vertex 86.8246 -49.6135 -13.4291 - endloop - endfacet - facet normal 0.917722 -0.394064 -0.0499985 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 91.9574 -39.2917 -0.568089 - vertex 86.8246 -49.6135 -13.4291 - endloop - endfacet - facet normal 0.826648 -0.562085 -0.0267074 - outer loop - vertex 86.6025 -50 25 - vertex 76.1299 -64.8401 13.1775 - vertex 88.4105 -46.7288 12.1154 - endloop - endfacet - facet normal 0.871781 -0.488058 -0.0423872 - outer loop - vertex 88.4105 -46.7288 12.1154 - vertex 81.6519 -57.7318 -0.197758 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.999374 -0.00384446 0.0351629 - outer loop - vertex 99.5185 -9.80141 -12.3868 - vertex 100 0 -25 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal 0.999342 -0.00381447 -0.0360703 - outer loop - vertex 99.9991 -0.416489 -0.064092 - vertex 99.5185 -9.80141 -12.3868 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal 0.982796 0.181544 -0.033968 - outer loop - vertex 98.4808 17.3648 25 - vertex 99.6001 8.93394 12.3255 - vertex 96.2174 27.2437 12.3115 - endloop - endfacet - facet normal 0.995173 0.0910356 -0.0366554 - outer loop - vertex 98.264 18.5522 -0.061308 - vertex 99.6001 8.93394 12.3255 - vertex 99.9991 -0.416489 -0.064092 - endloop - endfacet - facet normal 0.237696 -0.971332 -0.00397865 - outer loop - vertex 22.5155 -97.4323 50 - vertex 20 -97.9796 33.3333 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal 0.334487 -0.9424 0 - outer loop - vertex 27.5 -96.1444 62.5 - vertex 27.5 -96.1444 50 - vertex 39.2665 -91.9681 55.9636 - endloop - endfacet - facet normal 0.438176 -0.89885 -0.00837307 - outer loop - vertex 50 -86.6025 41.6667 - vertex 39.2665 -91.9681 55.9636 - vertex 36.9775 -92.9121 37.5153 - endloop - endfacet - facet normal 0.707097 -0.707097 0.00519144 - outer loop - vertex 64.2788 -76.6044 25 - vertex 76.1299 -64.8401 13.1775 - vertex 76.6044 -64.2788 25 - endloop - endfacet - facet normal 0.906301 -0.422619 -0.00327943 - outer loop - vertex 93.9693 -34.202 -25 - vertex 86.8246 -49.6135 -13.4291 - vertex 86.6025 -50 -25 - endloop - endfacet - facet normal 0.872505 -0.486759 0.042441 - outer loop - vertex 81.6519 -57.7318 -0.197758 - vertex 86.8246 -49.6135 -13.4291 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.828058 -0.558844 0.0448667 - outer loop - vertex 76.1299 -64.8401 13.1775 - vertex 81.6519 -57.7318 -0.197758 - vertex 88.4105 -46.7288 12.1154 - endloop - endfacet - facet normal 0.995744 0.0871151 -0.0300954 - outer loop - vertex 100 0 -25 - vertex 98.4808 17.3648 -25 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal 0.995165 0.0910241 0.0368834 - outer loop - vertex 99.9991 -0.416489 -0.064092 - vertex 99.5907 9.03858 -12.3789 - vertex 98.264 18.5522 -0.061308 - endloop - endfacet - facet normal 0.965514 0.258708 0.0291923 - outer loop - vertex 98.4808 17.3648 25 - vertex 96.2174 27.2437 12.3115 - vertex 93.9693 34.202 25 - endloop - endfacet - facet normal 0.982752 0.181589 0.034998 - outer loop - vertex 99.6001 8.93394 12.3255 - vertex 98.264 18.5522 -0.061308 - vertex 96.2174 27.2437 12.3115 - endloop - endfacet - facet normal 0.981131 -0.190305 -0.0341522 - outer loop - vertex 99.5329 -9.65377 12.257 - vertex 98.4808 -17.3648 25 - vertex 95.9067 -28.318 12.0851 - endloop - endfacet - facet normal 0.965575 -0.258724 0.0269745 - outer loop - vertex 93.9693 -34.202 25 - vertex 95.9067 -28.318 12.0851 - vertex 98.4808 -17.3648 25 - endloop - endfacet - facet normal 0.995761 -0.0871167 0.0294972 - outer loop - vertex 100 0 25 - vertex 98.4808 -17.3648 25 - vertex 99.5329 -9.65377 12.257 - endloop - endfacet - facet normal 0.980931 -0.190916 0.0363962 - outer loop - vertex 99.5329 -9.65377 12.257 - vertex 95.9067 -28.318 12.0851 - vertex 98.0268 -19.7673 -0.202037 - endloop - endfacet - facet normal 0.46423 -0.885715 0 - outer loop - vertex 50 -86.6025 58.3333 - vertex 50 -86.6025 75 - vertex 42.7684 -90.3928 75 - endloop - endfacet - facet normal 0.95433 -0.295892 -0.0412471 - outer loop - vertex 98.0268 -19.7673 -0.202037 - vertex 95.9067 -28.318 12.0851 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.925652 -0.376945 -0.0328758 - outer loop - vertex 93.9693 -34.202 25 - vertex 88.4105 -46.7288 12.1154 - vertex 95.9067 -28.318 12.0851 - endloop - endfacet - facet normal 0.979912 -0.195985 0.0369018 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 98.4808 -17.3648 -25 - vertex 99.5185 -9.80141 -12.3868 - endloop - endfacet - facet normal 0.979898 -0.195468 -0.0399103 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 99.5185 -9.80141 -12.3868 - vertex 98.0268 -19.7673 -0.202037 - endloop - endfacet - facet normal 0.999416 -0.0034879 -0.0339918 - outer loop - vertex 100 0 25 - vertex 99.5329 -9.65377 12.257 - vertex 99.6001 8.93394 12.3255 - endloop - endfacet - facet normal 0.994149 -0.101055 -0.0381459 - outer loop - vertex 99.9991 -0.416489 -0.064092 - vertex 99.5329 -9.65377 12.257 - vertex 98.0268 -19.7673 -0.202037 - endloop - endfacet - facet normal 0.390421 -0.920626 0.0043626 - outer loop - vertex 35.2517 -93.5805 75 - vertex 39.2665 -91.9681 55.9636 - vertex 42.7684 -90.3928 75 - endloop - endfacet - facet normal 0.314023 -0.949415 0 - outer loop - vertex 27.5 -96.1444 75 - vertex 27.5 -96.1444 62.5 - vertex 35.2517 -93.5805 75 - endloop - endfacet - facet normal 0.448635 -0.893674 -0.00857659 - outer loop - vertex 39.2665 -91.9681 55.9636 - vertex 50 -86.6025 58.3333 - vertex 42.7684 -90.3928 75 - endloop - endfacet - facet normal 0.965606 -0.258732 -0.0257499 - outer loop - vertex 93.9693 -34.202 -25 - vertex 98.4808 -17.3648 -25 - vertex 95.647 -29.1831 -12.5165 - endloop - endfacet - facet normal 0.953812 -0.297311 0.0430012 - outer loop - vertex 95.647 -29.1831 -12.5165 - vertex 98.0268 -19.7673 -0.202037 - vertex 91.9574 -39.2917 -0.568089 - endloop - endfacet - facet normal 0.906127 -0.422538 0.0198742 - outer loop - vertex 86.6025 -50 25 - vertex 88.4105 -46.7288 12.1154 - vertex 93.9693 -34.202 25 - endloop - endfacet - facet normal 0.925528 -0.376779 0.0378927 - outer loop - vertex 88.4105 -46.7288 12.1154 - vertex 91.9574 -39.2917 -0.568089 - vertex 95.9067 -28.318 12.0851 - endloop - endfacet - facet normal 0.995756 -0.0871162 -0.0296837 - outer loop - vertex 98.4808 -17.3648 -25 - vertex 100 0 -25 - vertex 99.5185 -9.80141 -12.3868 - endloop - endfacet - facet normal 0.994077 -0.101595 0.0386041 - outer loop - vertex 98.0268 -19.7673 -0.202037 - vertex 99.5185 -9.80141 -12.3868 - vertex 99.9991 -0.416489 -0.064092 - endloop - endfacet - facet normal 0.995747 0.0871154 0.029988 - outer loop - vertex 100 0 25 - vertex 99.6001 8.93394 12.3255 - vertex 98.4808 17.3648 25 - endloop - endfacet - facet normal 0.99938 -0.00374205 0.0350088 - outer loop - vertex 99.5329 -9.65377 12.257 - vertex 99.9991 -0.416489 -0.064092 - vertex 99.6001 8.93394 12.3255 - endloop - endfacet - facet normal 0.212598 -0.97714 0 - outer loop - vertex 22.5155 -97.4323 50 - vertex 20 -97.9796 50 - vertex 20 -97.9796 33.3333 - endloop - endfacet - facet normal 0.314023 0.949415 -0 - outer loop - vertex 27.5 96.1444 62.5 - vertex 27.5 96.1444 75 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal 0.448683 0.89365 -0.00855008 - outer loop - vertex 42.7684 90.3928 75 - vertex 50 86.6025 58.3333 - vertex 39.2656 91.9685 55.8745 - endloop - endfacet - facet normal 0.282808 -0.959074 0.0140455 - outer loop - vertex 20 -97.9796 33.3333 - vertex 34.3396 -93.9191 21.8686 - vertex 36.9775 -92.9121 37.5153 - endloop - endfacet - facet normal 0.419303 -0.907541 0.0235218 - outer loop - vertex 46.1781 -88.6994 12.2251 - vertex 50 -86.6025 25 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.53484 -0.844684 -0.0213611 - outer loop - vertex 60.4894 -79.6306 11.9434 - vertex 50 -86.6025 25 - vertex 46.1781 -88.6994 12.2251 - endloop - endfacet - facet normal 0.59203 -0.804645 -0.0452331 - outer loop - vertex 67.4343 -73.8418 -0.134955 - vertex 60.4894 -79.6306 11.9434 - vertex 49.9874 -86.6098 -1.35914 - endloop - endfacet - facet normal 0.706904 -0.706904 -0.023921 - outer loop - vertex 73.4611 -67.8488 -12.3904 - vertex 64.2788 -76.6044 -25 - vertex 76.6044 -64.2788 -25 - endloop - endfacet - facet normal 0.656132 -0.753262 -0.0456879 - outer loop - vertex 73.4611 -67.8488 -12.3904 - vertex 67.4343 -73.8418 -0.134955 - vertex 56.9654 -82.1884 -12.8692 - endloop - endfacet - facet normal 0.422622 -0.906306 0 - outer loop - vertex 50 -86.6025 -75 - vertex 50 -86.6025 -58.3333 - vertex 34.202 -93.9693 -75 - endloop - endfacet - facet normal 0.928884 0.368714 0.0349787 - outer loop - vertex 96.1185 27.5906 -12.3821 - vertex 93.9693 34.202 -25 - vertex 88.8787 45.8321 -12.4096 - endloop - endfacet - facet normal 0.928773 0.368558 -0.0393159 - outer loop - vertex 88.8787 45.8321 -12.4096 - vertex 92.8747 37.0715 -0.1349 - vertex 96.1185 27.5906 -12.3821 - endloop - endfacet - facet normal 0.847193 0.530371 -0.0311559 - outer loop - vertex 86.6025 50 25 - vertex 89.4625 44.6818 12.2368 - vertex 79.3607 60.8431 12.6644 - endloop - endfacet - facet normal 0.885977 0.462014 -0.0398435 - outer loop - vertex 83.5447 54.9571 -0.204582 - vertex 89.4625 44.6818 12.2368 - vertex 92.8747 37.0715 -0.1349 - endloop - endfacet - facet normal 0.212598 0.97714 0 - outer loop - vertex 20 97.9796 50 - vertex 22.5155 97.4323 50 - vertex 20 97.9796 33.3333 - endloop - endfacet - facet normal 0.329212 0.944198 -0.0104898 - outer loop - vertex 39.2656 91.9685 55.8745 - vertex 27.5 96.1444 62.5 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal 0.447133 0.894467 0 - outer loop - vertex 50 86.6025 58.3333 - vertex 50 86.6025 41.6667 - vertex 39.2656 91.9685 55.8745 - endloop - endfacet - facet normal 0.272454 -0.962169 0 - outer loop - vertex 20 -97.9796 33.3333 - vertex 20 -97.9796 16.6667 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.403414 -0.915018 -3.1335e-05 - outer loop - vertex 46.1781 -88.6994 12.2251 - vertex 34.3396 -93.9191 21.8686 - vertex 34.3321 -93.9218 4.1825 - endloop - endfacet - facet normal 0.535436 -0.844332 0.0202677 - outer loop - vertex 60.4894 -79.6306 11.9434 - vertex 46.1781 -88.6994 12.2251 - vertex 49.9874 -86.6098 -1.35914 - endloop - endfacet - facet normal 0.587832 -0.807667 0.046122 - outer loop - vertex 49.9874 -86.6098 -1.35914 - vertex 56.9654 -82.1884 -12.8692 - vertex 67.4343 -73.8418 -0.134955 - endloop - endfacet - facet normal 0.654546 -0.754542 0.0472841 - outer loop - vertex 56.9654 -82.1884 -12.8692 - vertex 64.2788 -76.6044 -25 - vertex 73.4611 -67.8488 -12.3904 - endloop - endfacet - facet normal 0.445118 -0.895472 0 - outer loop - vertex 38.8506 -92.1446 -54.264 - vertex 50 -86.6025 -58.3333 - vertex 50 -86.6025 -41.6667 - endloop - endfacet - facet normal 0.43933 -0.898115 -0.0194579 - outer loop - vertex 34.202 -93.9693 -75 - vertex 50 -86.6025 -58.3333 - vertex 38.8506 -92.1446 -54.264 - endloop - endfacet - facet normal 0.262571 -0.964839 -0.0119167 - outer loop - vertex 20 -97.9796 33.3333 - vertex 27.5 -96.1444 50 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal 0.331245 -0.943517 0.00718017 - outer loop - vertex 27.5 -96.1444 50 - vertex 36.9775 -92.9121 37.5153 - vertex 39.2665 -91.9681 55.9636 - endloop - endfacet - facet normal 0.436031 -0.899932 0 - outer loop - vertex 50 -86.6025 41.6667 - vertex 36.9775 -92.9121 37.5153 - vertex 50 -86.6025 25 - endloop - endfacet - facet normal 0.688061 -0.724961 -0.0316669 - outer loop - vertex 64.2788 -76.6044 25 - vertex 60.4894 -79.6306 11.9434 - vertex 76.1299 -64.8401 13.1775 - endloop - endfacet - facet normal 0.819148 -0.573572 0.00343571 - outer loop - vertex 86.8246 -49.6135 -13.4291 - vertex 76.6044 -64.2788 -25 - vertex 86.6025 -50 -25 - endloop - endfacet - facet normal 0.804299 -0.592207 -0.0489229 - outer loop - vertex 86.8246 -49.6135 -13.4291 - vertex 81.6519 -57.7318 -0.197758 - vertex 73.4611 -67.8488 -12.3904 - endloop - endfacet - facet normal 0.749023 -0.661201 -0.042161 - outer loop - vertex 81.6519 -57.7318 -0.197758 - vertex 76.1299 -64.8401 13.1775 - vertex 67.4343 -73.8418 -0.134955 - endloop - endfacet - facet normal 0.982333 0.18386 0.0349068 - outer loop - vertex 99.5907 9.03858 -12.3789 - vertex 98.4808 17.3648 -25 - vertex 96.1185 27.5906 -12.3821 - endloop - endfacet - facet normal 0.98229 0.183839 -0.0361901 - outer loop - vertex 96.1185 27.5906 -12.3821 - vertex 98.264 18.5522 -0.061308 - vertex 99.5907 9.03858 -12.3789 - endloop - endfacet - facet normal 0.93203 0.360895 -0.0327791 - outer loop - vertex 93.9693 34.202 25 - vertex 96.2174 27.2437 12.3115 - vertex 89.4625 44.6818 12.2368 - endloop - endfacet - facet normal 0.95954 0.279087 -0.0373312 - outer loop - vertex 92.8747 37.0715 -0.1349 - vertex 96.2174 27.2437 12.3115 - vertex 98.264 18.5522 -0.061308 - endloop - endfacet - facet normal 0.46423 0.885715 0 - outer loop - vertex 42.7684 90.3928 75 - vertex 50 86.6025 75 - vertex 50 86.6025 58.3333 - endloop - endfacet - facet normal 0.291799 -0.956125 -0.0260287 - outer loop - vertex 36.9775 -92.9121 37.5153 - vertex 27.5 -96.1444 50 - vertex 20 -97.9796 33.3333 - endloop - endfacet - facet normal 0.42546 -0.904877 -0.0134925 - outer loop - vertex 50 -86.6025 25 - vertex 36.9775 -92.9121 37.5153 - vertex 34.3396 -93.9191 21.8686 - endloop - endfacet - facet normal 0.573419 -0.818929 0.0233849 - outer loop - vertex 64.2788 -76.6044 25 - vertex 50 -86.6025 25 - vertex 60.4894 -79.6306 11.9434 - endloop - endfacet - facet normal 0.684524 -0.727608 0.0448719 - outer loop - vertex 60.4894 -79.6306 11.9434 - vertex 67.4343 -73.8418 -0.134955 - vertex 76.1299 -64.8401 13.1775 - endloop - endfacet - facet normal 0.807052 -0.589484 0.0342873 - outer loop - vertex 73.4611 -67.8488 -12.3904 - vertex 76.6044 -64.2788 -25 - vertex 86.8246 -49.6135 -13.4291 - endloop - endfacet - facet normal 0.749093 -0.660923 0.0451816 - outer loop - vertex 67.4343 -73.8418 -0.134955 - vertex 73.4611 -67.8488 -12.3904 - vertex 81.6519 -57.7318 -0.197758 - endloop - endfacet - facet normal 0.965523 0.25871 -0.0289007 - outer loop - vertex 98.4808 17.3648 -25 - vertex 93.9693 34.202 -25 - vertex 96.1185 27.5906 -12.3821 - endloop - endfacet - facet normal 0.959441 0.279357 0.0378596 - outer loop - vertex 98.264 18.5522 -0.061308 - vertex 96.1185 27.5906 -12.3821 - vertex 92.8747 37.0715 -0.1349 - endloop - endfacet - facet normal 0.905976 0.422468 0.026978 - outer loop - vertex 93.9693 34.202 25 - vertex 89.4625 44.6818 12.2368 - vertex 86.6025 50 25 - endloop - endfacet - facet normal 0.931866 0.361121 0.0348759 - outer loop - vertex 96.2174 27.2437 12.3115 - vertex 92.8747 37.0715 -0.1349 - vertex 89.4625 44.6818 12.2368 - endloop - endfacet - facet normal 0.390421 0.920626 0.00434299 - outer loop - vertex 42.7684 90.3928 75 - vertex 39.2656 91.9685 55.8745 - vertex 35.2517 93.5805 75 - endloop - endfacet - facet normal -0.467368 0.882319 -0.0555011 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -56.9547 82.1959 -12.8877 - vertex -49.9767 86.616 -1.38088 - endloop - endfacet - facet normal -0.573294 0.818751 -0.0313054 - outer loop - vertex -50 86.6025 -25 - vertex -64.2788 76.6044 -25 - vertex -56.9547 82.1959 -12.8877 - endloop - endfacet - facet normal -0.419262 0.907561 0.0235151 - outer loop - vertex -34.3293 93.9228 21.8746 - vertex -46.1796 88.6986 12.2171 - vertex -50 86.6025 25 - endloop - endfacet - facet normal -0.81893 -0.57342 0.0233025 - outer loop - vertex -86.6025 -50 25 - vertex -79.3664 -60.8356 12.6628 - vertex -76.6044 -64.2788 25 - endloop - endfacet - facet normal -0.929004 -0.368396 0.0351584 - outer loop - vertex -96.131 -27.5468 -12.3849 - vertex -93.9693 -34.202 -25 - vertex -88.8886 -45.8128 -12.411 - endloop - endfacet - facet normal -0.885863 -0.462083 0.0415503 - outer loop - vertex -92.8816 -37.0542 -0.137898 - vertex -88.8886 -45.8128 -12.411 - vertex -83.5527 -54.9449 -0.206588 - endloop - endfacet - facet normal -0.847951 -0.529003 0.0336902 - outer loop - vertex -89.468 -44.6708 12.2345 - vertex -83.5527 -54.9449 -0.206588 - vertex -79.3664 -60.8356 12.6628 - endloop - endfacet - facet normal -0.535432 0.844337 0.0201992 - outer loop - vertex -60.486 79.6332 11.9276 - vertex -46.1796 88.6986 12.2171 - vertex -49.9767 86.616 -1.38088 - endloop - endfacet - facet normal -0.587699 0.807765 0.0461088 - outer loop - vertex -49.9767 86.616 -1.38088 - vertex -56.9547 82.1959 -12.8877 - vertex -67.4208 73.8541 -0.150617 - endloop - endfacet - facet normal -0.654419 0.754649 0.0473415 - outer loop - vertex -56.9547 82.1959 -12.8877 - vertex -64.2788 76.6044 -25 - vertex -73.4484 67.8625 -12.4043 - endloop - endfacet - facet normal -0.534819 0.844697 -0.0213297 - outer loop - vertex -60.486 79.6332 11.9276 - vertex -50 86.6025 25 - vertex -46.1796 88.6986 12.2171 - endloop - endfacet - facet normal -0.847247 -0.530282 -0.031193 - outer loop - vertex -86.6025 -50 25 - vertex -89.468 -44.6708 12.2345 - vertex -79.3664 -60.8356 12.6628 - endloop - endfacet - facet normal -0.965521 -0.25871 -0.0289653 - outer loop - vertex -96.131 -27.5468 -12.3849 - vertex -98.4808 -17.3648 -25 - vertex -93.9693 -34.202 -25 - endloop - endfacet - facet normal -0.928893 -0.368246 -0.0394152 - outer loop - vertex -88.8886 -45.8128 -12.411 - vertex -92.8816 -37.0542 -0.137898 - vertex -96.131 -27.5468 -12.3849 - endloop - endfacet - facet normal -0.886052 -0.461869 -0.0398665 - outer loop - vertex -83.5527 -54.9449 -0.206588 - vertex -89.468 -44.6708 12.2345 - vertex -92.8816 -37.0542 -0.137898 - endloop - endfacet - facet normal -0.706903 0.706903 -0.0240038 - outer loop - vertex -64.2788 76.6044 -25 - vertex -76.6044 64.2788 -25 - vertex -73.4484 67.8625 -12.4043 - endloop - endfacet - facet normal -0.591918 0.80473 -0.0451874 - outer loop - vertex -67.4208 73.8541 -0.150617 - vertex -60.486 79.6332 11.9276 - vertex -49.9767 86.616 -1.38088 - endloop - endfacet - facet normal -0.656023 0.753358 -0.0456656 - outer loop - vertex -73.4484 67.8625 -12.4043 - vertex -67.4208 73.8541 -0.150617 - vertex -56.9547 82.1959 -12.8877 - endloop - endfacet - facet normal -0.573419 0.818929 0.0233706 - outer loop - vertex -64.2788 76.6044 25 - vertex -50 86.6025 25 - vertex -60.486 79.6332 11.9276 - endloop - endfacet - facet normal -0.905976 -0.422467 0.0269994 - outer loop - vertex -93.9693 -34.202 25 - vertex -89.468 -44.6708 12.2345 - vertex -86.6025 -50 25 - endloop - endfacet - facet normal -0.982356 -0.183785 0.0346442 - outer loop - vertex -99.5881 -9.06697 -12.3787 - vertex -98.4808 -17.3648 -25 - vertex -96.131 -27.5468 -12.3849 - endloop - endfacet - facet normal -0.959476 -0.279244 0.0377917 - outer loop - vertex -98.2656 -18.5439 -0.056713 - vertex -96.131 -27.5468 -12.3849 - vertex -92.8816 -37.0542 -0.137898 - endloop - endfacet - facet normal -0.291801 0.956125 -0.0260296 - outer loop - vertex -36.9782 92.9119 37.517 - vertex -27.5 96.1444 50 - vertex -20 97.9796 33.3333 - endloop - endfacet - facet normal -0.573471 -0.819004 -0.0190693 - outer loop - vertex -50 -86.6025 25 - vertex -64.2788 -76.6044 25 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.819153 -0.573575 -0.000633422 - outer loop - vertex -76.661 -64.2113 -12.9207 - vertex -86.6025 -50 -25 - vertex -76.6044 -64.2788 -25 - endloop - endfacet - facet normal -0.688846 -0.723645 -0.0427726 - outer loop - vertex -70.347 -71.0725 1.47391 - vertex -76.661 -64.2113 -12.9207 - vertex -61.2739 -79.0286 -10.0423 - endloop - endfacet - facet normal -0.611574 -0.790086 -0.0417168 - outer loop - vertex -70.347 -71.0725 1.47391 - vertex -53.0109 -84.7929 7.17859 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.272574 0.962134 -0.00146753 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -34.285 93.939 4.174 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.427738 0.903881 0.00622994 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -36.1727 93.2284 -36.9681 - vertex -50 86.6025 -25 - endloop - endfacet - facet normal -0.272339 0.962201 0.000199298 - outer loop - vertex -34.285 93.939 4.174 - vertex -34.3293 93.9228 21.8746 - vertex -20 97.9796 16.6667 - endloop - endfacet - facet normal -0.436039 0.899928 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -36.9782 92.9119 37.517 - vertex -50 86.6025 25 - endloop - endfacet - facet normal -0.282795 0.959077 0.0140918 - outer loop - vertex -36.9782 92.9119 37.517 - vertex -20 97.9796 33.3333 - vertex -34.3293 93.9228 21.8746 - endloop - endfacet - facet normal -0.707025 -0.707025 0.0151987 - outer loop - vertex -76.6044 -64.2788 25 - vertex -65.7797 -75.3195 14.9518 - vertex -64.2788 -76.6044 25 - endloop - endfacet - facet normal -0.831964 -0.553839 0.0331305 - outer loop - vertex -88.8886 -45.8128 -12.411 - vertex -86.6025 -50 -25 - vertex -76.661 -64.2113 -12.9207 - endloop - endfacet - facet normal -0.775121 -0.630581 0.03943 - outer loop - vertex -83.5527 -54.9449 -0.206588 - vertex -76.661 -64.2113 -12.9207 - vertex -70.347 -71.0725 1.47391 - endloop - endfacet - facet normal -0.731553 -0.68097 0.033324 - outer loop - vertex -79.3664 -60.8356 12.6628 - vertex -70.347 -71.0725 1.47391 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.423375 0.905953 0.00165032 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -49.9767 86.616 -1.38088 - vertex -34.285 93.939 4.174 - endloop - endfacet - facet normal -0.453525 0.889012 0.0630259 - outer loop - vertex -34.6546 93.8033 -16.1476 - vertex -50 86.6025 -25 - vertex -56.9547 82.1959 -12.8877 - endloop - endfacet - facet normal -0.403273 0.91508 -0.000171536 - outer loop - vertex -34.285 93.939 4.174 - vertex -46.1796 88.6986 12.2171 - vertex -34.3293 93.9228 21.8746 - endloop - endfacet - facet normal -0.425412 0.904898 -0.0135604 - outer loop - vertex -36.9782 92.9119 37.517 - vertex -34.3293 93.9228 21.8746 - vertex -50 86.6025 25 - endloop - endfacet - facet normal -0.726754 -0.686292 -0.0288353 - outer loop - vertex -76.6044 -64.2788 25 - vertex -79.3664 -60.8356 12.6628 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.906045 -0.4225 -0.0240068 - outer loop - vertex -88.8886 -45.8128 -12.411 - vertex -93.9693 -34.202 -25 - vertex -86.6025 -50 -25 - endloop - endfacet - facet normal -0.83247 -0.5519 -0.0490006 - outer loop - vertex -76.661 -64.2113 -12.9207 - vertex -83.5527 -54.9449 -0.206588 - vertex -88.8886 -45.8128 -12.411 - endloop - endfacet - facet normal -0.77104 -0.635524 -0.0400861 - outer loop - vertex -79.3664 -60.8356 12.6628 - vertex -83.5527 -54.9449 -0.206588 - vertex -70.347 -71.0725 1.47391 - endloop - endfacet - facet normal -0.416074 0.909039 -0.0230395 - outer loop - vertex -49.9767 86.616 -1.38088 - vertex -46.1796 88.6986 12.2171 - vertex -34.285 93.939 4.174 - endloop - endfacet - facet normal -0.827902 0.559087 0.0447336 - outer loop - vertex -76.1193 64.8525 13.1683 - vertex -81.6289 57.7643 -0.210629 - vertex -88.3918 46.7642 12.1066 - endloop - endfacet - facet normal -0.819139 0.573566 -0.00577342 - outer loop - vertex -86.6025 50 25 - vertex -76.6044 64.2788 25 - vertex -76.1193 64.8525 13.1683 - endloop - endfacet - facet normal -0.982807 -0.181491 -0.0339348 - outer loop - vertex -98.4808 -17.3648 25 - vertex -99.6002 -8.93358 12.3277 - vertex -96.2203 -27.2335 12.3122 - endloop - endfacet - facet normal -0.999325 0.00407918 -0.0365012 - outer loop - vertex -99.9992 0.407363 -0.064789 - vertex -99.5096 9.89181 -12.4091 - vertex -99.5881 -9.06697 -12.3787 - endloop - endfacet - facet normal -0.995174 -0.0910507 -0.0365885 - outer loop - vertex -98.2656 -18.5439 -0.056713 - vertex -99.6002 -8.93358 12.3277 - vertex -99.9992 0.407363 -0.064789 - endloop - endfacet - facet normal -0.979741 0.196269 -0.0398178 - outer loop - vertex -98.004 19.8799 -0.222364 - vertex -95.6263 29.2507 -12.5369 - vertex -99.5096 9.89181 -12.4091 - endloop - endfacet - facet normal -0.917511 0.394574 -0.0498431 - outer loop - vertex -91.9278 39.3609 -0.583074 - vertex -86.8061 49.6458 -13.4447 - vertex -95.6263 29.2507 -12.5369 - endloop - endfacet - facet normal -0.871506 0.488566 -0.0421878 - outer loop - vertex -88.3918 46.7642 12.1066 - vertex -81.6289 57.7643 -0.210629 - vertex -91.9278 39.3609 -0.583074 - endloop - endfacet - facet normal -0.826502 0.562313 -0.0264225 - outer loop - vertex -86.6025 50 25 - vertex -76.1193 64.8525 13.1683 - vertex -88.3918 46.7642 12.1066 - endloop - endfacet - facet normal -0.995746 -0.0871154 0.0299985 - outer loop - vertex -100 0 25 - vertex -99.6002 -8.93358 12.3277 - vertex -98.4808 -17.3648 25 - endloop - endfacet - facet normal -0.994 0.102164 0.0390709 - outer loop - vertex -98.004 19.8799 -0.222364 - vertex -99.5096 9.89181 -12.4091 - vertex -99.9992 0.407363 -0.064789 - endloop - endfacet - facet normal -0.999382 0.0036918 0.0349599 - outer loop - vertex -99.534 9.64234 12.2585 - vertex -99.9992 0.407363 -0.064789 - vertex -99.6002 -8.93358 12.3277 - endloop - endfacet - facet normal -0.953541 0.298206 0.0428104 - outer loop - vertex -91.9278 39.3609 -0.583074 - vertex -95.6263 29.2507 -12.5369 - vertex -98.004 19.8799 -0.222364 - endloop - endfacet - facet normal -0.925331 0.377278 0.037737 - outer loop - vertex -88.3918 46.7642 12.1066 - vertex -91.9278 39.3609 -0.583074 - vertex -95.8872 28.3838 12.0748 - endloop - endfacet - facet normal -0.90613 0.422539 0.0197065 - outer loop - vertex -86.6025 50 25 - vertex -88.3918 46.7642 12.1066 - vertex -93.9693 34.202 25 - endloop - endfacet - facet normal -0.999418 0.00343521 -0.0339527 - outer loop - vertex -100 0 25 - vertex -99.534 9.64234 12.2585 - vertex -99.6002 -8.93358 12.3277 - endloop - endfacet - facet normal -0.994083 0.101544 -0.0385697 - outer loop - vertex -99.9992 0.407363 -0.064789 - vertex -99.534 9.64234 12.2585 - vertex -98.004 19.8799 -0.222364 - endloop - endfacet - facet normal -0.954054 0.296813 -0.0410282 - outer loop - vertex -95.8872 28.3838 12.0748 - vertex -91.9278 39.3609 -0.583074 - vertex -98.004 19.8799 -0.222364 - endloop - endfacet - facet normal -0.925456 0.377451 -0.0325838 - outer loop - vertex -93.9693 34.202 25 - vertex -88.3918 46.7642 12.1066 - vertex -95.8872 28.3838 12.0748 - endloop - endfacet - facet normal -0.995761 0.0871167 0.0295083 - outer loop - vertex -98.4808 17.3648 25 - vertex -99.534 9.64234 12.2585 - vertex -100 0 25 - endloop - endfacet - facet normal -0.980864 0.19122 0.0366083 - outer loop - vertex -95.8872 28.3838 12.0748 - vertex -98.004 19.8799 -0.222364 - vertex -99.534 9.64234 12.2585 - endloop - endfacet - facet normal -0.965579 0.258725 0.0268135 - outer loop - vertex -93.9693 34.202 25 - vertex -95.8872 28.3838 12.0748 - vertex -98.4808 17.3648 25 - endloop - endfacet - facet normal -0.981072 0.190564 -0.034404 - outer loop - vertex -98.4808 17.3648 25 - vertex -95.8872 28.3838 12.0748 - vertex -99.534 9.64234 12.2585 - endloop - endfacet - facet normal -0.931906 -0.36102 0.0348684 - outer loop - vertex -96.2203 -27.2335 12.3122 - vertex -92.8816 -37.0542 -0.137898 - vertex -89.468 -44.6708 12.2345 - endloop - endfacet - facet normal -0.819149 0.573573 0.00314847 - outer loop - vertex -76.6044 64.2788 -25 - vertex -86.6025 50 -25 - vertex -86.8061 49.6458 -13.4447 - endloop - endfacet - facet normal -0.806889 0.5897 0.0343951 - outer loop - vertex -73.4484 67.8625 -12.4043 - vertex -76.6044 64.2788 -25 - vertex -86.8061 49.6458 -13.4447 - endloop - endfacet - facet normal -0.684445 0.727687 0.044801 - outer loop - vertex -60.486 79.6332 11.9276 - vertex -67.4208 73.8541 -0.150617 - vertex -76.1193 64.8525 13.1683 - endloop - endfacet - facet normal -0.748899 0.661147 0.0451079 - outer loop - vertex -67.4208 73.8541 -0.150617 - vertex -73.4484 67.8625 -12.4043 - vertex -81.6289 57.7643 -0.210629 - endloop - endfacet - facet normal -0.687995 0.725026 -0.0316292 - outer loop - vertex -64.2788 76.6044 25 - vertex -60.486 79.6332 11.9276 - vertex -76.1193 64.8525 13.1683 - endloop - endfacet - facet normal -0.932073 -0.360783 -0.0327892 - outer loop - vertex -93.9693 -34.202 25 - vertex -96.2203 -27.2335 12.3122 - vertex -89.468 -44.6708 12.2345 - endloop - endfacet - facet normal -0.995744 -0.0871152 -0.0300857 - outer loop - vertex -99.5881 -9.06697 -12.3787 - vertex -100 0 -25 - vertex -98.4808 -17.3648 -25 - endloop - endfacet - facet normal -0.982317 -0.183754 -0.0358965 - outer loop - vertex -96.131 -27.5468 -12.3849 - vertex -98.2656 -18.5439 -0.056713 - vertex -99.5881 -9.06697 -12.3787 - endloop - endfacet - facet normal -0.959582 -0.278946 -0.0372942 - outer loop - vertex -92.8816 -37.0542 -0.137898 - vertex -96.2203 -27.2335 12.3122 - vertex -98.2656 -18.5439 -0.056713 - endloop - endfacet - facet normal -0.995757 0.0871163 -0.0296576 - outer loop - vertex -99.5096 9.89181 -12.4091 - vertex -98.4808 17.3648 -25 - vertex -100 0 -25 - endloop - endfacet - facet normal -0.96561 0.258733 -0.0255913 - outer loop - vertex -95.6263 29.2507 -12.5369 - vertex -93.9693 34.202 -25 - vertex -98.4808 17.3648 -25 - endloop - endfacet - facet normal -0.906302 0.42262 -0.00301421 - outer loop - vertex -86.8061 49.6458 -13.4447 - vertex -86.6025 50 -25 - vertex -93.9693 34.202 -25 - endloop - endfacet - facet normal -0.804135 0.592436 -0.0488526 - outer loop - vertex -86.8061 49.6458 -13.4447 - vertex -81.6289 57.7643 -0.210629 - vertex -73.4484 67.8625 -12.4043 - endloop - endfacet - facet normal -0.748838 0.661418 -0.0420413 - outer loop - vertex -81.6289 57.7643 -0.210629 - vertex -76.1193 64.8525 13.1683 - vertex -67.4208 73.8541 -0.150617 - endloop - endfacet - facet normal -0.707097 0.707097 0.005295 - outer loop - vertex -64.2788 76.6044 25 - vertex -76.1193 64.8525 13.1683 - vertex -76.6044 64.2788 25 - endloop - endfacet - facet normal -0.965514 -0.258708 0.0292065 - outer loop - vertex -98.4808 -17.3648 25 - vertex -96.2203 -27.2335 12.3122 - vertex -93.9693 -34.202 25 - endloop - endfacet - facet normal -0.999356 0.00419496 0.0356282 - outer loop - vertex -99.5096 9.89181 -12.4091 - vertex -100 0 -25 - vertex -99.5881 -9.06697 -12.3787 - endloop - endfacet - facet normal -0.995169 -0.091019 0.0368062 - outer loop - vertex -99.9992 0.407363 -0.064789 - vertex -99.5881 -9.06697 -12.3787 - vertex -98.2656 -18.5439 -0.056713 - endloop - endfacet - facet normal -0.982762 -0.18154 0.0349692 - outer loop - vertex -99.6002 -8.93358 12.3277 - vertex -98.2656 -18.5439 -0.056713 - vertex -96.2203 -27.2335 12.3122 - endloop - endfacet - facet normal -0.97976 0.196778 0.036736 - outer loop - vertex -95.6263 29.2507 -12.5369 - vertex -98.4808 17.3648 -25 - vertex -99.5096 9.89181 -12.4091 - endloop - endfacet - facet normal -0.916653 0.398036 0.0362592 - outer loop - vertex -86.8061 49.6458 -13.4447 - vertex -93.9693 34.202 -25 - vertex -95.6263 29.2507 -12.5369 - endloop - endfacet - facet normal -0.872231 0.487261 0.0423062 - outer loop - vertex -81.6289 57.7643 -0.210629 - vertex -86.8061 49.6458 -13.4447 - vertex -91.9278 39.3609 -0.583074 - endloop - endfacet - facet normal -0.262571 -0.964839 -0.0119167 - outer loop - vertex -20 -97.9796 33.3333 - vertex -25.016 -96.8204 50 - vertex -27.5 -96.1444 50 - endloop - endfacet - facet normal -0.276986 -0.96087 0.00272835 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -20.6573 -97.8431 -19.044 - vertex -34.7716 -93.76 -13.9625 - endloop - endfacet - facet normal -0.422031 -0.906582 0 - outer loop - vertex -50 -86.6025 -41.6667 - vertex -34.0799 -94.0136 -33.0533 - vertex -50 -86.6025 -25 - endloop - endfacet - facet normal -0.277004 -0.960865 0.00267378 - outer loop - vertex -20.6573 -97.8431 -19.044 - vertex -20 -97.9796 0 - vertex -34.7716 -93.76 -13.9625 - endloop - endfacet - facet normal 0.0335579 0.999433 0.00285939 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 0 100 0 - vertex 6.70689 99.7748 0 - endloop - endfacet - facet normal 0.00355818 0.999738 0.0226167 - outer loop - vertex 9.68083 99.5303 -55.7605 - vertex 0 100 -75 - vertex -8.98427 99.5956 -55.7105 - endloop - endfacet - facet normal 0.0722065 0.997155 0.0216333 - outer loop - vertex -2.08806 99.9782 -37.1245 - vertex 16.4596 98.6361 -37.1697 - vertex 9.68083 99.5303 -55.7605 - endloop - endfacet - facet normal 0.125428 0.991997 0.0144988 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 20.6881 97.8366 -19.0489 - vertex 16.4596 98.6361 -37.1697 - endloop - endfacet - facet normal -0.438629 -0.898633 -0.00799843 - outer loop - vertex -50 -86.6025 41.6667 - vertex -37.053 -92.882 37.1703 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.291666 -0.956168 -0.0259643 - outer loop - vertex -20 -97.9796 33.3333 - vertex -27.5 -96.1444 50 - vertex -37.053 -92.882 37.1703 - endloop - endfacet - facet normal -0.278992 -0.960293 -0 - outer loop - vertex -20 -97.9796 16.6667 - vertex -35.6133 -93.4435 4.12026 - vertex -20 -97.9796 0 - endloop - endfacet - facet normal -0.282638 -0.959227 -0 - outer loop - vertex -20 -97.9796 33.3333 - vertex -36.323 -93.17 20.3068 - vertex -20 -97.9796 16.6667 - endloop - endfacet - facet normal -0.423402 -0.905936 -0.00330637 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -34.7716 -93.76 -13.9625 - vertex -50 -86.6025 -25 - endloop - endfacet - facet normal -0.278048 -0.960559 0.00387047 - outer loop - vertex -34.7716 -93.76 -13.9625 - vertex -20 -97.9796 0 - vertex -35.6133 -93.4435 4.12026 - endloop - endfacet - facet normal -0.0335554 0.999359 -0.0124611 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex -6.70689 99.7748 0 - vertex 0 100 0 - endloop - endfacet - facet normal -0.422622 0.906306 0 - outer loop - vertex -50 86.6025 -75 - vertex -50 86.6025 -58.3333 - vertex -34.202 93.9693 -75 - endloop - endfacet - facet normal -0.0871377 0.996001 -0.0197041 - outer loop - vertex 0 100 -75 - vertex -17.3648 98.4808 -75 - vertex -8.98427 99.5956 -55.7105 - endloop - endfacet - facet normal -0.258767 0.965736 -0.0198141 - outer loop - vertex -17.3648 98.4808 -75 - vertex -34.202 93.9693 -75 - vertex -25.4516 96.7069 -55.8478 - endloop - endfacet - facet normal 0.0034391 0.999755 -0.0218568 - outer loop - vertex -8.98427 99.5956 -55.7105 - vertex -2.08806 99.9782 -37.1245 - vertex 9.68083 99.5303 -55.7605 - endloop - endfacet - facet normal 0.0721053 0.997182 -0.0207077 - outer loop - vertex -2.08806 99.9782 -37.1245 - vertex 4.20548 99.9115 -18.4222 - vertex 16.4596 98.6361 -37.1697 - endloop - endfacet - facet normal -0.314023 0.949415 0 - outer loop - vertex -35.2517 93.5805 75 - vertex -27.5 96.1444 75 - vertex -27.5 96.1444 62.5 - endloop - endfacet - facet normal -0.436396 -0.899755 -0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -50 -86.6025 25 - vertex -37.053 -92.882 37.1703 - endloop - endfacet - facet normal -0.329212 -0.944198 -0.0104898 - outer loop - vertex -27.5 -96.1444 62.5 - vertex -35.2517 -93.5805 75 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.212598 -0.97714 0 - outer loop - vertex -20 -97.9796 33.3333 - vertex -20 -97.9796 50 - vertex -22.5155 -97.4323 50 - endloop - endfacet - facet normal -0.125019 -0.992047 0.0145815 - outer loop - vertex -4.15257 -99.9137 -18.4073 - vertex -20.6573 -97.8431 -19.044 - vertex -16.4069 -98.6449 -37.1516 - endloop - endfacet - facet normal -0.250522 -0.968016 0.0135905 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -30.515 -95.2304 -54.0087 - vertex -16.4069 -98.6449 -37.1516 - endloop - endfacet - facet normal -0.40488 -0.91437 -0 - outer loop - vertex -50 -86.6025 -41.6667 - vertex -50 -86.6025 -58.3333 - vertex -30.515 -95.2304 -54.0087 - endloop - endfacet - facet normal -0.123766 -0.992144 -0.0182309 - outer loop - vertex -13.3836 -99.1004 0 - vertex -20.6573 -97.8431 -19.044 - vertex -4.15257 -99.9137 -18.4073 - endloop - endfacet - facet normal 0.200051 0.979428 0.0264705 - outer loop - vertex 17.3648 98.4808 -75 - vertex 9.68083 99.5303 -55.7605 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.277204 0.960807 0.00268171 - outer loop - vertex 34.1021 94.0056 -33.0557 - vertex 20.6881 97.8366 -19.0489 - vertex 34.7811 93.7564 -13.9596 - endloop - endfacet - facet normal 0.250882 0.967923 0.0135602 - outer loop - vertex 16.4596 98.6361 -37.1697 - vertex 34.1021 94.0056 -33.0557 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.167018 0.985953 -0.00136825 - outer loop - vertex 13.3836 99.1004 0 - vertex 20 97.9796 0 - vertex 20.6881 97.8366 -19.0489 - endloop - endfacet - facet normal -0.448683 -0.89365 -0.00855004 - outer loop - vertex -39.2656 -91.9685 55.8744 - vertex -42.7684 -90.3928 75 - vertex -50 -86.6025 58.3333 - endloop - endfacet - facet normal -0.334482 -0.942402 0 - outer loop - vertex -27.5 -96.1444 50 - vertex -27.5 -96.1444 62.5 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.237696 -0.971332 -0.00397865 - outer loop - vertex -20 -97.9796 33.3333 - vertex -22.5155 -97.4323 50 - vertex -25.016 -96.8204 50 - endloop - endfacet - facet normal -0.257275 -0.966178 -0.0176083 - outer loop - vertex -34.0799 -94.0136 -33.0533 - vertex -16.4069 -98.6449 -37.1516 - vertex -20.6573 -97.8431 -19.044 - endloop - endfacet - facet normal -0.41412 -0.910052 -0.0176064 - outer loop - vertex -50 -86.6025 -41.6667 - vertex -30.515 -95.2304 -54.0087 - vertex -34.0799 -94.0136 -33.0533 - endloop - endfacet - facet normal -0.167018 -0.985953 -0.00130219 - outer loop - vertex -13.3836 -99.1004 0 - vertex -20 -97.9796 0 - vertex -20.6573 -97.8431 -19.044 - endloop - endfacet - facet normal 0.100495 0.994918 -0.00626293 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 6.70689 99.7748 0 - vertex 13.3836 99.1004 0 - endloop - endfacet - facet normal 0.087138 0.996005 -0.0195297 - outer loop - vertex 17.3648 98.4808 -75 - vertex 0 100 -75 - vertex 9.68083 99.5303 -55.7605 - endloop - endfacet - facet normal 0.20437 0.978509 -0.0274543 - outer loop - vertex 9.68083 99.5303 -55.7605 - vertex 16.4596 98.6361 -37.1697 - vertex 30.5386 95.2229 -54.0167 - endloop - endfacet - facet normal 0.257641 0.966082 -0.0174965 - outer loop - vertex 20.6881 97.8366 -19.0489 - vertex 34.1021 94.0056 -33.0557 - vertex 16.4596 98.6361 -37.1697 - endloop - endfacet - facet normal 0.124196 0.992091 -0.0181959 - outer loop - vertex 4.20548 99.9115 -18.4222 - vertex 13.3836 99.1004 0 - vertex 20.6881 97.8366 -19.0489 - endloop - endfacet - facet normal -0.447133 -0.894467 0 - outer loop - vertex -50 -86.6025 41.6667 - vertex -39.2656 -91.9685 55.8744 - vertex -50 -86.6025 58.3333 - endloop - endfacet - facet normal -0.331425 -0.943457 0.00687246 - outer loop - vertex -37.053 -92.882 37.1703 - vertex -27.5 -96.1444 50 - vertex -39.2656 -91.9685 55.8744 - endloop - endfacet - facet normal -0.448637 0.893673 -0.00857543 - outer loop - vertex -39.2668 91.968 55.9654 - vertex -50 86.6025 58.3333 - vertex -42.7684 90.3928 75 - endloop - endfacet - facet normal -0.334487 0.9424 0 - outer loop - vertex -27.5 96.1444 62.5 - vertex -27.5 96.1444 50 - vertex -39.2668 91.968 55.9654 - endloop - endfacet - facet normal -0.237696 0.971332 -0.00397865 - outer loop - vertex -20 97.9796 33.3333 - vertex -25.016 96.8204 50 - vertex -22.5155 97.4323 50 - endloop - endfacet - facet normal -0.573487 -0.819027 -0.0175303 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -50 -86.6025 -25 - vertex -61.2739 -79.0286 -10.0423 - endloop - endfacet - facet normal -0.437633 -0.898986 -0.0173465 - outer loop - vertex -36.323 -93.17 20.3068 - vertex -50 -86.6025 25 - vertex -53.0109 -84.7929 7.17859 - endloop - endfacet - facet normal -0.542986 -0.839492 -0.0204628 - outer loop - vertex -53.0109 -84.7929 7.17859 - vertex -61.2739 -79.0286 -10.0423 - vertex -47.479 -88.0099 -7.63341 - endloop - endfacet - facet normal -0.167018 0.985953 0.00109199 - outer loop - vertex -13.3836 99.1004 0 - vertex -14.0535 99.0076 -18.6679 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.435119 0.900307 0.0108912 - outer loop - vertex -38.8343 92.1515 -54.2819 - vertex -50 86.6025 -41.6667 - vertex -36.1727 93.2284 -36.9681 - endloop - endfacet - facet normal -0.284584 0.958534 0.0150007 - outer loop - vertex -20.4194 97.893 -36.1707 - vertex -25.4516 96.7069 -55.8478 - vertex -36.1727 93.2284 -36.9681 - endloop - endfacet - facet normal -0.241831 0.969965 0.0261872 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -20.4194 97.893 -36.1707 - vertex -34.6546 93.8033 -16.1476 - endloop - endfacet - facet normal -0.44714 0.894464 0 - outer loop - vertex -50 86.6025 41.6667 - vertex -50 86.6025 58.3333 - vertex -39.2668 91.968 55.9654 - endloop - endfacet - facet normal -0.331242 0.943518 0.00718254 - outer loop - vertex -39.2668 91.968 55.9654 - vertex -27.5 96.1444 50 - vertex -36.9782 92.9119 37.517 - endloop - endfacet - facet normal -0.262571 0.964839 -0.0119167 - outer loop - vertex -27.5 96.1444 50 - vertex -25.016 96.8204 50 - vertex -20 97.9796 33.3333 - endloop - endfacet - facet normal -0.707107 -0.707107 0.000637766 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -76.661 -64.2113 -12.9207 - vertex -76.6044 -64.2788 -25 - endloop - endfacet - facet normal -0.695723 -0.717929 0.0234109 - outer loop - vertex -64.2788 -76.6044 -25 - vertex -61.2739 -79.0286 -10.0423 - vertex -76.661 -64.2113 -12.9207 - endloop - endfacet - facet normal -0.588877 -0.808034 0.0174413 - outer loop - vertex -53.0109 -84.7929 7.17859 - vertex -50 -86.6025 25 - vertex -65.7797 -75.3195 14.9518 - endloop - endfacet - facet normal -0.628423 -0.776763 0.0415291 - outer loop - vertex -70.347 -71.0725 1.47391 - vertex -61.2739 -79.0286 -10.0423 - vertex -53.0109 -84.7929 7.17859 - endloop - endfacet - facet normal -0.24779 0.968475 -0.0255997 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -34.6546 93.8033 -16.1476 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.432137 0.901808 0 - outer loop - vertex -36.1727 93.2284 -36.9681 - vertex -50 86.6025 -41.6667 - vertex -50 86.6025 -25 - endloop - endfacet - facet normal -0.283643 0.958912 -0.00579609 - outer loop - vertex -20.4194 97.893 -36.1707 - vertex -36.1727 93.2284 -36.9681 - vertex -34.6546 93.8033 -16.1476 - endloop - endfacet - facet normal -0.272177 0.962247 0 - outer loop - vertex -34.285 93.939 4.174 - vertex -20 97.9796 16.6667 - vertex -20 97.9796 0 - endloop - endfacet - facet normal -0.438182 0.898847 -0.00836934 - outer loop - vertex -50 86.6025 41.6667 - vertex -39.2668 91.968 55.9654 - vertex -36.9782 92.9119 37.517 - endloop - endfacet - facet normal -0.272406 0.962182 0 - outer loop - vertex -34.3293 93.9228 21.8746 - vertex -20 97.9796 33.3333 - vertex -20 97.9796 16.6667 - endloop - endfacet - facet normal -0.285575 -0.958348 0.00400448 - outer loop - vertex -20 -97.9796 33.3333 - vertex -37.053 -92.882 37.1703 - vertex -36.323 -93.17 20.3068 - endloop - endfacet - facet normal -0.281845 -0.959452 0.00385401 - outer loop - vertex -36.323 -93.17 20.3068 - vertex -35.6133 -93.4435 4.12026 - vertex -20 -97.9796 16.6667 - endloop - endfacet - facet normal -0.417594 -0.908541 -0.0130093 - outer loop - vertex -47.479 -88.0099 -7.63341 - vertex -50 -86.6025 -25 - vertex -34.7716 -93.76 -13.9625 - endloop - endfacet - facet normal -0.413627 -0.910441 -0.00331757 - outer loop - vertex -47.479 -88.0099 -7.63341 - vertex -34.7716 -93.76 -13.9625 - vertex -35.6133 -93.4435 4.12026 - endloop - endfacet - facet normal -0.0491409 0.998556 -0.0216991 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -6.70689 99.7748 0 - vertex 4.20548 99.9115 -18.4222 - endloop - endfacet - facet normal -0.439297 0.898132 -0.0194192 - outer loop - vertex -34.202 93.9693 -75 - vertex -50 86.6025 -58.3333 - vertex -38.8343 92.1515 -54.2819 - endloop - endfacet - facet normal -0.1729 0.984771 0.0182053 - outer loop - vertex -8.98427 99.5956 -55.7105 - vertex -17.3648 98.4808 -75 - vertex -25.4516 96.7069 -55.8478 - endloop - endfacet - facet normal -0.321031 0.947001 0.0113113 - outer loop - vertex -25.4516 96.7069 -55.8478 - vertex -34.202 93.9693 -75 - vertex -38.8343 92.1515 -54.2819 - endloop - endfacet - facet normal -0.111914 0.993494 0.0210733 - outer loop - vertex -2.08806 99.9782 -37.1245 - vertex -8.98427 99.5956 -55.7105 - vertex -20.4194 97.893 -36.1707 - endloop - endfacet - facet normal -0.049706 0.998558 0.0202881 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex 4.20548 99.9115 -18.4222 - vertex -2.08806 99.9782 -37.1245 - endloop - endfacet - facet normal -0.390421 0.920626 0.00436439 - outer loop - vertex -35.2517 93.5805 75 - vertex -39.2668 91.968 55.9654 - vertex -42.7684 90.3928 75 - endloop - endfacet - facet normal -0.114112 0.99323 -0.0217467 - outer loop - vertex -14.0535 99.0076 -18.6679 - vertex -2.08806 99.9782 -37.1245 - vertex -20.4194 97.893 -36.1707 - endloop - endfacet - facet normal -0.323186 0.946291 -0.00917599 - outer loop - vertex -25.4516 96.7069 -55.8478 - vertex -38.8343 92.1515 -54.2819 - vertex -36.1727 93.2284 -36.9681 - endloop - endfacet - facet normal -0.172638 0.984868 -0.0152155 - outer loop - vertex -20.4194 97.893 -36.1707 - vertex -8.98427 99.5956 -55.7105 - vertex -25.4516 96.7069 -55.8478 - endloop - endfacet - facet normal -0.44504 0.895511 0 - outer loop - vertex -50 86.6025 -58.3333 - vertex -50 86.6025 -41.6667 - vertex -38.8343 92.1515 -54.2819 - endloop - endfacet - facet normal -0.100496 0.994937 -0.00133981 - outer loop - vertex -13.3836 99.1004 0 - vertex -6.70689 99.7748 0 - vertex -14.0535 99.0076 -18.6679 - endloop - endfacet - facet normal -0.440758 -0.897117 0.030232 - outer loop - vertex -53.0109 -84.7929 7.17859 - vertex -47.479 -88.0099 -7.63341 - vertex -35.6133 -93.4435 4.12026 - endloop - endfacet - facet normal -0.546994 -0.837057 0.011568 - outer loop - vertex -61.2739 -79.0286 -10.0423 - vertex -50 -86.6025 -25 - vertex -47.479 -88.0099 -7.63341 - endloop - endfacet - facet normal -0.445847 -0.895098 -0.00442405 - outer loop - vertex -35.6133 -93.4435 4.12026 - vertex -36.323 -93.17 20.3068 - vertex -53.0109 -84.7929 7.17859 - endloop - endfacet - facet normal -0.43381 -0.900998 -0.00339187 - outer loop - vertex -37.053 -92.882 37.1703 - vertex -50 -86.6025 25 - vertex -36.323 -93.17 20.3068 - endloop - endfacet - facet normal -0.212598 0.97714 0 - outer loop - vertex -20 97.9796 50 - vertex -20 97.9796 33.3333 - vertex -22.5155 97.4323 50 - endloop - endfacet - facet normal -0.32927 0.944177 -0.0105298 - outer loop - vertex -35.2517 93.5805 75 - vertex -27.5 96.1444 62.5 - vertex -39.2668 91.968 55.9654 - endloop - endfacet - facet normal -0.46423 0.885715 0 - outer loop - vertex -50 86.6025 58.3333 - vertex -50 86.6025 75 - vertex -42.7684 90.3928 75 - endloop - endfacet -endsolid patch015 -solid patch016 - facet normal -0.923881 0.38268 0 - outer loop - vertex 82.0711 -7.07107 25 - vertex 85 0 8.33333 - vertex 82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex 82.0711 -7.07107 8.33333 - vertex 85 0 -8.33333 - vertex 82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex 85 0 -25 - vertex 82.0711 -7.07107 -25 - vertex 82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex 85 0 25 - vertex 82.0711 7.07107 25 - vertex 82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex 75 10 -8.33333 - vertex 82.0711 7.07107 8.33333 - vertex 75 10 8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex 67.9289 7.07107 -25 - vertex 75 10 -8.33333 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex 82.0711 -7.07107 25 - vertex 82.0711 -7.07107 8.33333 - vertex 75 -10 25 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex 82.0711 -7.07107 8.33333 - vertex 82.0711 -7.07107 -8.33333 - vertex 75 -10 8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex 82.0711 -7.07107 -8.33333 - vertex 82.0711 -7.07107 -25 - vertex 75 -10 -8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex 82.0711 7.07107 8.33333 - vertex 82.0711 7.07107 25 - vertex 75 10 8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex 75 10 -8.33333 - vertex 75 10 8.33333 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex 67.9289 7.07107 -25 - vertex 67.9289 7.07107 -8.33333 - vertex 65 0 -25 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex 67.9289 7.07107 -25 - vertex 75 10 -25 - vertex 75 10 -8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex 75 10 -8.33333 - vertex 82.0711 7.07107 -8.33333 - vertex 82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 -0 - outer loop - vertex 85 0 25 - vertex 82.0711 7.07107 8.33333 - vertex 85 0 8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex 85 0 -8.33333 - vertex 85 0 -25 - vertex 82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex 85 0 8.33333 - vertex 85 0 -8.33333 - vertex 82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex 85 0 25 - vertex 85 0 8.33333 - vertex 82.0711 -7.07107 25 - endloop - endfacet - facet normal -0.382682 -0.92388 -0 - outer loop - vertex 75 10 -8.33333 - vertex 75 10 -25 - vertex 82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 -0 - outer loop - vertex 82.0711 7.07107 8.33333 - vertex 82.0711 7.07107 -8.33333 - vertex 85 0 8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex 82.0711 7.07107 -25 - vertex 85 0 -25 - vertex 85 0 -8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 -0 - outer loop - vertex 85 0 8.33333 - vertex 82.0711 7.07107 -8.33333 - vertex 85 0 -8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex 75 10 -25 - vertex 82.0711 7.07107 -25 - vertex 82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 -0 - outer loop - vertex 82.0711 7.07107 -8.33333 - vertex 82.0711 7.07107 -25 - vertex 85 0 -8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex 65 0 25 - vertex 65 0 8.33333 - vertex 67.9289 7.07107 25 - endloop - endfacet - facet normal 0.923881 0.38268 0 - outer loop - vertex 65 0 25 - vertex 67.9289 -7.07107 8.33333 - vertex 65 0 8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex 67.9289 7.07107 25 - vertex 65 0 8.33333 - vertex 67.9289 7.07107 8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 0 - outer loop - vertex 67.9289 -7.07107 8.33333 - vertex 67.9289 -7.07107 -8.33333 - vertex 65 0 8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 0 - outer loop - vertex 67.9289 -7.07107 25 - vertex 67.9289 -7.07107 8.33333 - vertex 65 0 25 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex 65 0 8.33333 - vertex 65 0 -8.33333 - vertex 67.9289 7.07107 8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex 67.9289 7.07107 25 - vertex 67.9289 7.07107 8.33333 - vertex 75 10 25 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex 67.9289 -7.07107 8.33333 - vertex 75 -10 -8.33333 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 -0 - outer loop - vertex 65 0 -8.33333 - vertex 65 0 8.33333 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex 67.9289 -7.07107 25 - vertex 75 -10 8.33333 - vertex 67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex 67.9289 7.07107 8.33333 - vertex 65 0 -8.33333 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex 75 10 25 - vertex 67.9289 7.07107 8.33333 - vertex 75 10 8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex 75 -10 25 - vertex 82.0711 -7.07107 8.33333 - vertex 75 -10 8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 0 - outer loop - vertex 67.9289 -7.07107 -25 - vertex 65 0 -25 - vertex 65 0 -8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex 75 -10 8.33333 - vertex 82.0711 -7.07107 -8.33333 - vertex 75 -10 -8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex 75 -10 -25 - vertex 67.9289 -7.07107 -25 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex 82.0711 -7.07107 -25 - vertex 75 -10 -25 - vertex 75 -10 -8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 -0 - outer loop - vertex 75 10 25 - vertex 75 10 8.33333 - vertex 82.0711 7.07107 25 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex 67.9289 7.07107 8.33333 - vertex 67.9289 7.07107 -8.33333 - vertex 75 10 8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex 65 0 -8.33333 - vertex 65 0 -25 - vertex 67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex 75 -10 25 - vertex 75 -10 8.33333 - vertex 67.9289 -7.07107 25 - endloop - endfacet - facet normal 0.923881 0.38268 0 - outer loop - vertex 67.9289 -7.07107 -8.33333 - vertex 67.9289 -7.07107 -25 - vertex 65 0 -8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex 75 -10 8.33333 - vertex 75 -10 -8.33333 - vertex 67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex 75 -10 -8.33333 - vertex 75 -10 -25 - vertex 67.9289 -7.07107 -8.33333 - endloop - endfacet -endsolid patch016 -solid patch017 - facet normal -0.923881 0.38268 0 - outer loop - vertex -65 0 -25 - vertex -67.9289 -7.07107 -8.33333 - vertex -65 0 -8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex -65 0 -8.33333 - vertex -67.9289 -7.07107 8.33333 - vertex -65 0 8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex -67.9289 -7.07107 25 - vertex -65 0 25 - vertex -65 0 8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex -75 -10 -25 - vertex -75 -10 -8.33333 - vertex -67.9289 -7.07107 -25 - endloop - endfacet - facet normal 0.382682 0.92388 -0 - outer loop - vertex -82.0711 -7.07107 -8.33333 - vertex -82.0711 -7.07107 8.33333 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 -0 - outer loop - vertex -85 0 8.33333 - vertex -85 0 25 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex -65 0 -25 - vertex -65 0 -8.33333 - vertex -67.9289 7.07107 -25 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex -65 0 -8.33333 - vertex -65 0 8.33333 - vertex -67.9289 7.07107 -8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex -65 0 8.33333 - vertex -65 0 25 - vertex -67.9289 7.07107 8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 -0 - outer loop - vertex -75 -10 -25 - vertex -82.0711 -7.07107 -8.33333 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex -82.0711 7.07107 25 - vertex -85 0 25 - vertex -85 0 8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 -0 - outer loop - vertex -82.0711 -7.07107 -8.33333 - vertex -85 0 8.33333 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 0 - outer loop - vertex -82.0711 -7.07107 25 - vertex -82.0711 -7.07107 8.33333 - vertex -85 0 25 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -75 -10 -8.33333 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex -67.9289 -7.07107 -8.33333 - vertex -67.9289 -7.07107 -25 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex -67.9289 -7.07107 8.33333 - vertex -67.9289 -7.07107 25 - vertex -65 0 8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex -67.9289 -7.07107 -8.33333 - vertex -67.9289 -7.07107 8.33333 - vertex -65 0 -8.33333 - endloop - endfacet - facet normal -0.923881 0.38268 0 - outer loop - vertex -65 0 -25 - vertex -67.9289 -7.07107 -25 - vertex -67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex -82.0711 -7.07107 25 - vertex -75 -10 8.33333 - vertex -82.0711 -7.07107 8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -67.9289 -7.07107 -8.33333 - vertex -75 -10 -8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex -75 -10 25 - vertex -67.9289 -7.07107 25 - vertex -67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -67.9289 -7.07107 8.33333 - vertex -67.9289 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 0 - outer loop - vertex -82.0711 -7.07107 25 - vertex -75 -10 25 - vertex -75 -10 8.33333 - endloop - endfacet - facet normal -0.382682 0.92388 0 - outer loop - vertex -75 -10 8.33333 - vertex -75 -10 25 - vertex -67.9289 -7.07107 8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex -82.0711 7.07107 -25 - vertex -82.0711 7.07107 -8.33333 - vertex -85 0 -25 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex -82.0711 7.07107 -25 - vertex -75 10 -8.33333 - vertex -82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex -85 0 -25 - vertex -82.0711 7.07107 -8.33333 - vertex -85 0 -8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex -75 10 -8.33333 - vertex -75 10 8.33333 - vertex -82.0711 7.07107 -8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex -75 10 -25 - vertex -75 10 -8.33333 - vertex -82.0711 7.07107 -25 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex -82.0711 7.07107 -8.33333 - vertex -82.0711 7.07107 8.33333 - vertex -85 0 -8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 -0 - outer loop - vertex -85 0 -25 - vertex -85 0 -8.33333 - vertex -82.0711 -7.07107 -25 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex -75 10 -8.33333 - vertex -67.9289 7.07107 8.33333 - vertex -75 10 8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex -82.0711 7.07107 -8.33333 - vertex -75 10 8.33333 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex -75 10 -25 - vertex -67.9289 7.07107 -8.33333 - vertex -75 10 -8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex -85 0 8.33333 - vertex -85 0 -8.33333 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal 0.923881 0.38268 -0 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -85 0 -8.33333 - vertex -82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex -67.9289 7.07107 8.33333 - vertex -67.9289 7.07107 25 - vertex -75 10 8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex -67.9289 7.07107 -8.33333 - vertex -67.9289 7.07107 8.33333 - vertex -75 10 -8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex -75 10 8.33333 - vertex -75 10 25 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex -67.9289 7.07107 -25 - vertex -67.9289 7.07107 -8.33333 - vertex -75 10 -25 - endloop - endfacet - facet normal 0.923881 0.38268 -0 - outer loop - vertex -85 0 -8.33333 - vertex -85 0 8.33333 - vertex -82.0711 -7.07107 -8.33333 - endloop - endfacet - facet normal 0.923881 -0.38268 0 - outer loop - vertex -82.0711 7.07107 8.33333 - vertex -82.0711 7.07107 25 - vertex -85 0 8.33333 - endloop - endfacet - facet normal 0.382682 0.92388 -0 - outer loop - vertex -82.0711 -7.07107 -25 - vertex -82.0711 -7.07107 -8.33333 - vertex -75 -10 -25 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex -65 0 25 - vertex -67.9289 7.07107 25 - vertex -67.9289 7.07107 8.33333 - endloop - endfacet - facet normal -0.382682 -0.92388 0 - outer loop - vertex -67.9289 7.07107 25 - vertex -75 10 25 - vertex -75 10 8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex -67.9289 7.07107 -8.33333 - vertex -65 0 8.33333 - vertex -67.9289 7.07107 8.33333 - endloop - endfacet - facet normal 0.382682 -0.92388 0 - outer loop - vertex -75 10 25 - vertex -82.0711 7.07107 25 - vertex -82.0711 7.07107 8.33333 - endloop - endfacet - facet normal -0.923881 -0.38268 0 - outer loop - vertex -67.9289 7.07107 -25 - vertex -65 0 -8.33333 - vertex -67.9289 7.07107 -8.33333 - endloop - endfacet -endsolid patch017 -solid patch018 - facet normal 0 0 1 - outer loop - vertex 22.5155 97.4323 50 - vertex 20 97.9796 50 - vertex 20 81.4898 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 27.5 65 50 - vertex 27.5 80.5722 50 - vertex 20 65 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 22.5155 97.4323 50 - vertex 20 81.4898 50 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex 27.5 80.5722 50 - vertex 27.5 96.1444 50 - vertex 25.016 96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 65 50 - vertex 27.5 80.5722 50 - vertex 20 81.4898 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 20 81.4898 50 - vertex 27.5 80.5722 50 - vertex 25.016 96.8204 50 - endloop - endfacet -endsolid patch018 -solid patch019 - facet normal 0 0 1 - outer loop - vertex 27.5 35 50 - vertex 25.1837 27.7854 50 - vertex 27.5 25.4951 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 22.6774 29.8661 50 - vertex 25.1837 27.7854 50 - vertex 27.5 35 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 20 35 50 - vertex 22.6774 29.8661 50 - vertex 27.5 35 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 35 50 - vertex 20 31.7214 50 - vertex 22.6774 29.8661 50 - endloop - endfacet -endsolid patch019 -solid patch020 - facet normal -0 0 1 - outer loop - vertex 20 -31.7214 50 - vertex 20 -35 50 - vertex 22.6774 -29.8661 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex 25.1837 -27.7854 50 - vertex 27.5 -35 50 - vertex 27.5 -25.4951 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 22.6774 -29.8661 50 - vertex 20 -35 50 - vertex 27.5 -35 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 25.1837 -27.7854 50 - vertex 22.6774 -29.8661 50 - vertex 27.5 -35 50 - endloop - endfacet -endsolid patch020 -solid patch021 - facet normal 0 -0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 27.5 -65 50 - vertex 20 -65 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 20 -65 50 - vertex 20 -81.4898 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 20 -81.4898 50 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -81.4898 50 - vertex 22.5155 -97.4323 50 - vertex 25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 27.5 -80.5722 50 - vertex 25.016 -96.8204 50 - vertex 27.5 -96.1444 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex 20 -97.9796 50 - vertex 22.5155 -97.4323 50 - vertex 20 -81.4898 50 - endloop - endfacet -endsolid patch021 -solid patch022 - facet normal -0 0 1 - outer loop - vertex -27.5 -60 50 - vertex -27.5 -78.0722 50 - vertex -20 -60 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -22.5155 -97.4323 50 - vertex -20 -97.9796 50 - vertex -20 -78.9898 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -60 50 - vertex -27.5 -78.0722 50 - vertex -20 -78.9898 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -22.5155 -97.4323 50 - vertex -20 -78.9898 50 - vertex -25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -78.9898 50 - vertex -27.5 -78.0722 50 - vertex -25.016 -96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 -78.0722 50 - vertex -27.5 -96.1444 50 - vertex -25.016 -96.8204 50 - endloop - endfacet -endsolid patch022 -solid patch023 - facet normal 0 0 1 - outer loop - vertex -27.5 -40 50 - vertex -25.1837 -27.7854 50 - vertex -27.5 -25.4951 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -22.6774 -29.8661 50 - vertex -25.1837 -27.7854 50 - vertex -27.5 -40 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 -40 50 - vertex -22.6774 -29.8661 50 - vertex -27.5 -40 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -20 -40 50 - vertex -20 -31.7214 50 - vertex -22.6774 -29.8661 50 - endloop - endfacet -endsolid patch023 -solid patch024 - facet normal 0 -0 1 - outer loop - vertex -25.1837 27.7854 50 - vertex -22.6774 29.8661 50 - vertex -27.5 40 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -22.6774 29.8661 50 - vertex -20 40 50 - vertex -27.5 40 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -25.1837 27.7854 50 - vertex -27.5 40 50 - vertex -27.5 25.4951 50 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -20 31.7214 50 - vertex -20 40 50 - vertex -22.6774 29.8661 50 - endloop - endfacet -endsolid patch024 -solid patch025 - facet normal 0 0 1 - outer loop - vertex -20 97.9796 50 - vertex -22.5155 97.4323 50 - vertex -20 78.9898 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -25.016 96.8204 50 - vertex -27.5 96.1444 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -20 78.9898 50 - vertex -22.5155 97.4323 50 - vertex -25.016 96.8204 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -20 78.9898 50 - vertex -25.016 96.8204 50 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -20 60 50 - vertex -20 78.9898 50 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 78.0722 50 - vertex -27.5 60 50 - vertex -20 60 50 - endloop - endfacet -endsolid patch025 -solid patch026 - facet normal -0.0342027 -0.935647 0.351275 - outer loop - vertex -27.5 60 50 - vertex -36.2567 58.1386 44.1894 - vertex -20 57.0711 42.9289 - endloop - endfacet - facet normal -0.0349906 -0.972826 0.22888 - outer loop - vertex -40.1038 59.9273 51.2039 - vertex -50 60 50 - vertex -36.2567 58.1386 44.1894 - endloop - endfacet - facet normal 0.0669225 0.381821 -0.92181 - outer loop - vertex -38.7364 45.8624 59.1039 - vertex -50 42.9289 57.0711 - vertex -50 50 60 - endloop - endfacet - facet normal 0.0709574 0.737326 -0.671801 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -38.5748 40.5611 53.3026 - vertex -38.7364 45.8624 59.1039 - endloop - endfacet - facet normal 0.0306586 -0.964382 0.262732 - outer loop - vertex -36.2567 58.1386 44.1894 - vertex -27.5 60 50 - vertex -40.1038 59.9273 51.2039 - endloop - endfacet - facet normal 0 -0.923882 0.382679 - outer loop - vertex -20 60 50 - vertex -27.5 60 50 - vertex -20 57.0711 42.9289 - endloop - endfacet - facet normal 0.0397354 -0.923152 -0.382376 - outer loop - vertex -50 57.0711 57.0711 - vertex -50 60 50 - vertex -40.1038 59.9273 51.2039 - endloop - endfacet - facet normal -0.0609015 0.0501106 -0.996885 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -38.7364 45.8624 59.1039 - vertex -50 50 60 - endloop - endfacet - facet normal -0.0670837 0.381817 -0.9218 - outer loop - vertex -27.5 42.9289 57.0711 - vertex -38.7364 45.8624 59.1039 - vertex -27.5 50 60 - endloop - endfacet - facet normal -0.0266507 -0.941532 -0.335867 - outer loop - vertex -27.5 60 50 - vertex -36.9531 58.2533 55.6466 - vertex -40.1038 59.9273 51.2039 - endloop - endfacet - facet normal 0.0424554 -0.924625 -0.378506 - outer loop - vertex -50 57.0711 57.0711 - vertex -40.1038 59.9273 51.2039 - vertex -36.9531 58.2533 55.6466 - endloop - endfacet - facet normal 0.0612827 0.0494774 -0.996893 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -27.5 50 60 - vertex -38.7364 45.8624 59.1039 - endloop - endfacet - facet normal 0.0652895 -0.381862 -0.92191 - outer loop - vertex -50 57.0711 57.0711 - vertex -38.6983 53.2097 59.4709 - vertex -50 50 60 - endloop - endfacet - facet normal -0.0577773 -0.922338 -0.382039 - outer loop - vertex -27.5 57.0711 57.0711 - vertex -36.9531 58.2533 55.6466 - vertex -27.5 60 50 - endloop - endfacet - facet normal -0.0335104 -0.596471 -0.801935 - outer loop - vertex -50 57.0711 57.0711 - vertex -36.9531 58.2533 55.6466 - vertex -38.6983 53.2097 59.4709 - endloop - endfacet - facet normal -0.0658897 -0.381847 -0.921874 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -27.5 57.0711 57.0711 - vertex -27.5 50 60 - endloop - endfacet - facet normal 0.0422507 -0.612901 -0.78903 - outer loop - vertex -38.6983 53.2097 59.4709 - vertex -36.9531 58.2533 55.6466 - vertex -27.5 57.0711 57.0711 - endloop - endfacet - facet normal -0.0610479 0.498331 0.864835 - outer loop - vertex -35.0499 49.8411 40.0013 - vertex -50 42.9289 42.9289 - vertex -36.4184 41.5206 44.6991 - endloop - endfacet - facet normal 0.00398699 0.382676 0.923874 - outer loop - vertex -35.0499 49.8411 40.0013 - vertex -50 50 40 - vertex -50 42.9289 42.9289 - endloop - endfacet - facet normal 0.0458731 0.922909 0.382276 - outer loop - vertex -36.4184 41.5206 44.6991 - vertex -50 42.9289 42.9289 - vertex -50 40 50 - endloop - endfacet - facet normal 0.052604 0.484398 0.873265 - outer loop - vertex -36.4184 41.5206 44.6991 - vertex -20 42.9289 42.9289 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal -0.00414776 -0.382675 0.923874 - outer loop - vertex -50 57.0711 42.9289 - vertex -50 50 40 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal -0.0753156 0.99292 0.0918574 - outer loop - vertex -36.4184 41.5206 44.6991 - vertex -50 40 50 - vertex -38.5748 40.5611 53.3026 - endloop - endfacet - facet normal -0.00396055 0.382676 0.923874 - outer loop - vertex -35.0499 49.8411 40.0013 - vertex -20 42.9289 42.9289 - vertex -20 50 40 - endloop - endfacet - facet normal -0.0435708 0.9385 0.34252 - outer loop - vertex -20 42.9289 42.9289 - vertex -36.4184 41.5206 44.6991 - vertex -27.5 40 50 - endloop - endfacet - facet normal -0.0461645 -0.45546 0.889059 - outer loop - vertex -36.2567 58.1386 44.1894 - vertex -50 57.0711 42.9289 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal 0.0651072 0.921921 -0.381867 - outer loop - vertex -38.5748 40.5611 53.3026 - vertex -50 40 50 - vertex -50 42.9289 57.0711 - endloop - endfacet - facet normal 0.0895338 0.987127 0.13253 - outer loop - vertex -27.5 40 50 - vertex -36.4184 41.5206 44.6991 - vertex -38.5748 40.5611 53.3026 - endloop - endfacet - facet normal 0.00412025 -0.382675 0.923874 - outer loop - vertex -20 57.0711 42.9289 - vertex -35.0499 49.8411 40.0013 - vertex -20 50 40 - endloop - endfacet - facet normal 0 0.923882 0.382679 - outer loop - vertex -20 40 50 - vertex -20 42.9289 42.9289 - vertex -27.5 40 50 - endloop - endfacet - facet normal 0.0400855 -0.445583 0.894343 - outer loop - vertex -20 57.0711 42.9289 - vertex -36.2567 58.1386 44.1894 - vertex -35.0499 49.8411 40.0013 - endloop - endfacet - facet normal 0.036639 -0.923261 0.382422 - outer loop - vertex -50 60 50 - vertex -50 57.0711 42.9289 - vertex -36.2567 58.1386 44.1894 - endloop - endfacet - facet normal -0.0698965 0.735427 -0.673989 - outer loop - vertex -38.5748 40.5611 53.3026 - vertex -50 42.9289 57.0711 - vertex -38.7364 45.8624 59.1039 - endloop - endfacet - facet normal -0.067158 0.921796 -0.381815 - outer loop - vertex -27.5 40 50 - vertex -38.5748 40.5611 53.3026 - vertex -27.5 42.9289 57.0711 - endloop - endfacet -endsolid patch026 -solid patch027 - facet normal 0 0 1 - outer loop - vertex -38.9169 56.2753 75 - vertex -50 48.1125 75 - vertex -40.559 40.5083 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -38.9169 56.2753 75 - vertex -40.559 40.5083 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -40.559 40.5083 75 - vertex -50 48.1125 75 - vertex -50 28.8675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -40.559 40.5083 75 - vertex -38.7748 25.5778 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -96.1444 75 - vertex -27.5 -78.4821 75 - vertex -35.2517 -93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -40.559 40.5083 75 - vertex -50 28.8675 75 - vertex -38.7748 25.5778 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -38.7748 25.5778 75 - vertex -27.5 25.4951 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -35.2517 -93.5805 75 - vertex -27.5 -78.4821 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -42.7684 -90.3928 75 - vertex -35.2517 -93.5805 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.7748 25.5778 75 - vertex -50 28.8675 75 - vertex -50 9.6225 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 43.1574 75 - vertex -27.5 60.8198 75 - vertex -38.9169 56.2753 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 67.3575 75 - vertex -50 48.1125 75 - vertex -38.9169 56.2753 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.9169 56.2753 75 - vertex -27.5 60.8198 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 67.3575 75 - vertex -38.9169 56.2753 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 60.8198 75 - vertex -27.5 78.4821 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 67.3575 75 - vertex -38.6275 74.5675 75 - vertex -50 86.6025 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.6275 74.5675 75 - vertex -27.5 78.4821 75 - vertex -35.2517 93.5805 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -42.7684 90.3928 75 - vertex -50 86.6025 75 - vertex -38.6275 74.5675 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 78.4821 75 - vertex -27.5 96.1444 75 - vertex -35.2517 93.5805 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -42.7684 90.3928 75 - vertex -38.6275 74.5675 75 - vertex -35.2517 93.5805 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 -28.8675 75 - vertex -38.9258 -37.7032 75 - vertex -40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -48.1125 75 - vertex -38.9258 -37.7032 75 - vertex -50 -28.8675 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -38.9258 -37.7032 75 - vertex -27.5 -25.4951 75 - vertex -40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -28.8675 75 - vertex -40.3789 -22.1533 75 - vertex -50 -9.6225 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 -48.1125 75 - vertex -38.8583 -55.5405 75 - vertex -38.9258 -37.7032 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -43.1574 75 - vertex -27.5 -25.4951 75 - vertex -38.9258 -37.7032 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -27.5 -25.4951 75 - vertex -36.3417 -9.24839 75 - vertex -40.3789 -22.1533 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -40.3789 -22.1533 75 - vertex -36.3417 -9.24839 75 - vertex -50 -9.6225 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -67.3575 75 - vertex -38.8583 -55.5405 75 - vertex -50 -48.1125 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -38.8583 -55.5405 75 - vertex -27.5 -43.1574 75 - vertex -38.9258 -37.7032 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -9.6225 75 - vertex -36.3417 -9.24839 75 - vertex -50 9.6225 75 - endloop - endfacet - facet normal -0 0 1 - outer loop - vertex -50 -67.3575 75 - vertex -38.6268 -74.3694 75 - vertex -38.8583 -55.5405 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -60.8198 75 - vertex -27.5 -43.1574 75 - vertex -38.8583 -55.5405 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 9.6225 75 - vertex -36.3417 -9.24839 75 - vertex -36.3417 9.24839 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -50 -67.3575 75 - vertex -50 -86.6025 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -38.6268 -74.3694 75 - vertex -27.5 -60.8198 75 - vertex -38.8583 -55.5405 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -36.3417 9.24839 75 - vertex -38.7748 25.5778 75 - vertex -50 9.6225 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -42.7684 -90.3928 75 - vertex -38.6268 -74.3694 75 - vertex -50 -86.6025 75 - endloop - endfacet - facet normal 0 -0 1 - outer loop - vertex -27.5 -78.4821 75 - vertex -27.5 -60.8198 75 - vertex -38.6268 -74.3694 75 - endloop - endfacet - facet normal 0 0 1 - outer loop - vertex -38.7748 25.5778 75 - vertex -36.3417 9.24839 75 - vertex -27.5 25.4951 75 - endloop - endfacet -endsolid patch027 diff --git a/tutorials/socketOctree/system/controlDict b/tutorials/socketOctree/system/controlDict deleted file mode 100755 index c016ed2e7772add9024ad2e9a105b48603128a58..0000000000000000000000000000000000000000 --- a/tutorials/socketOctree/system/controlDict +++ /dev/null @@ -1,49 +0,0 @@ -// ************************************************************************* // -// FoamX Case Dictionary. - -version 1.0; -format ascii; -root "/home/franjo/foam/franjo2.0/run"; -case "jetAdaptive"; -instance "system"; -local ""; -class dictionary; -form dictionary; -object controlDict; - -// ************************************************************************* // - -applicationClass icoFoam; - -startFrom latestTime; - -startTime 0; - -stopAt endTime; - -endTime 500; - -deltaT 1; - -writeControl timeStep; - -writeInterval 100; - -cycleWrite 0; - -writeFormat binary; - -writeCompression compressed; - -timeFormat general; - -timePrecision 6; - -runTimeModifiable yes; - -nCorrectors 2; - -nNonOrthogonalCorrectors 0; - - -// ************************************************************************* // diff --git a/tutorials/socketOctree/system/meshDict b/tutorials/socketOctree/system/meshDict deleted file mode 100755 index e9ec4e6418f9784db9c6881ae8127dc4c289667a..0000000000000000000000000000000000000000 --- a/tutorials/socketOctree/system/meshDict +++ /dev/null @@ -1,49 +0,0 @@ -// The FOAM Project // File: adaptiveProperties -/* -------------------------------------------------------------------------------- - ========= | dictionary - \\ / | - \\ / | Name: adaptiveProperties - \\ / | Family: Data file - \\/ | - F ield | FOAM version: 1.9.6 - O peration | Product of Nabla Ltd. - A and | - M anipulation | Email: Enquiries@Nabla.co.uk -------------------------------------------------------------------------------- -*/ - -version 0.5; -format ascii; - -root "/home/larson/franjo/foam/run"; -case "thetaTest"; -instance "system"; -local ""; - -note "fvSchemes for Foam"; - -class dictionary; -object adaptiveProperties; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -surfaceFile "socket1.stl"; - -maxCellSize 4.0; - -boundaryCellSize 2.0; - -minCellSize 0.05; - -internalVertex (0.0 1.0 -0.25); -/* -patchCellSize -2 -( - walls 0.05 - walls1 0.05 -); -*/ - -// ************************************************************************* // diff --git a/tutorials/tetMesh/cutCubeOctree/0/.gitignore b/tutorials/tetMesh/cutCubeOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/tetMesh/cutCubeOctree/Allclean b/tutorials/tetMesh/cutCubeOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..b928b6cfea9e31cf9680fd810604054f9fe8b007 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/Allclean @@ -0,0 +1,12 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh diff --git a/tutorials/tetMesh/cutCubeOctree/Allrun b/tutorials/tetMesh/cutCubeOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..7dc47c3b86589ee42cf63b91f5e079e1efe46983 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/Allrun @@ -0,0 +1,6 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication tetMesh +runApplication checkMesh diff --git a/tutorials/tetMesh/cutCubeOctree/README b/tutorials/tetMesh/cutCubeOctree/README new file mode 100644 index 0000000000000000000000000000000000000000..e9309b20ed33bf0ec56e6a66829466be008f7408 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/README @@ -0,0 +1 @@ +Please run tetMesh to generate a tetrahedral mesh. diff --git a/tutorials/tetMesh/cutCubeOctree/constant/.gitignore b/tutorials/tetMesh/cutCubeOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/cutCubeOctree/geom.stl b/tutorials/tetMesh/cutCubeOctree/geom.stl similarity index 100% rename from tutorials/cutCubeOctree/geom.stl rename to tutorials/tetMesh/cutCubeOctree/geom.stl diff --git a/tutorials/cutCubeOctree/geom1.stl b/tutorials/tetMesh/cutCubeOctree/geom1.stl similarity index 100% rename from tutorials/cutCubeOctree/geom1.stl rename to tutorials/tetMesh/cutCubeOctree/geom1.stl diff --git a/tutorials/tetMesh/cutCubeOctree/system/controlDict b/tutorials/tetMesh/cutCubeOctree/system/controlDict new file mode 100644 index 0000000000000000000000000000000000000000..e59222d563497919bb954af4b70c74427cca5b4b --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/system/controlDict @@ -0,0 +1,53 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// ************************************************************************* // + +applicationClass ; + +startFrom latestTime; + +startTime 0; + +stopAt endTime; + +endTime 500; + +deltaT 1; + +writeControl timeStep; + +writeInterval 100; + +cycleWrite 0; + +writeFormat ascii; + +writeCompression compressed; + +timeFormat general; + +timePrecision 6; + +runTimeModifiable yes; + +nCorrectors 2; + +nNonOrthogonalCorrectors 0; + + +// ************************************************************************* // diff --git a/tutorials/tetMesh/cutCubeOctree/system/fvSchemes b/tutorials/tetMesh/cutCubeOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/tetMesh/cutCubeOctree/system/fvSolution b/tutorials/tetMesh/cutCubeOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/tetMesh/cutCubeOctree/system/meshDict b/tutorials/tetMesh/cutCubeOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..e22380538876c53f4ebec74df0b7232dbc6190a2 --- /dev/null +++ b/tutorials/tetMesh/cutCubeOctree/system/meshDict @@ -0,0 +1,40 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +surfaceFile "geom1.stl"; + +maxCellSize 0.2; + +boundaryCellSize 0.1; + +minCellSize 0.1; + +localRefinement +{ + patch0000 + { + cellSize 0.05; + } + patch0007 + { + cellSize 0.05; + } +} + +// ************************************************************************* // diff --git a/tutorials/tetMesh/socketOctree/0/.gitignore b/tutorials/tetMesh/socketOctree/0/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/0/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/tetMesh/socketOctree/Allclean b/tutorials/tetMesh/socketOctree/Allclean new file mode 100755 index 0000000000000000000000000000000000000000..b928b6cfea9e31cf9680fd810604054f9fe8b007 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/Allclean @@ -0,0 +1,12 @@ +#!/bin/bash + +# Klas Jareteg, 2012-10-13 +# Description: +# Script to run comparative case between coupled and segregated solvers. + + +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/CleanFunctions + +cleanCase +rm -r constant/polyMesh diff --git a/tutorials/tetMesh/socketOctree/Allrun b/tutorials/tetMesh/socketOctree/Allrun new file mode 100755 index 0000000000000000000000000000000000000000..7dc47c3b86589ee42cf63b91f5e079e1efe46983 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/Allrun @@ -0,0 +1,6 @@ +#!/bin/sh +# Source tutorial run functions +. $WM_PROJECT_DIR/bin/tools/RunFunctions + +runApplication tetMesh +runApplication checkMesh diff --git a/tutorials/tetMesh/socketOctree/README b/tutorials/tetMesh/socketOctree/README new file mode 100644 index 0000000000000000000000000000000000000000..4e84beae2ae54902b8de8be65ce437ec240b1739 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/README @@ -0,0 +1 @@ +Please run cartesianMesh or tetMesh to generate te volume mesh. diff --git a/tutorials/tetMesh/socketOctree/constant/.gitignore b/tutorials/tetMesh/socketOctree/constant/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..86d0cb2726c6c7c179b99520c452dd1b68e7a813 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/constant/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore \ No newline at end of file diff --git a/tutorials/tetMesh/socketOctree/socket.fms b/tutorials/tetMesh/socketOctree/socket.fms new file mode 100644 index 0000000000000000000000000000000000000000..936a583f68e59567fb5cfbb4a231d03c37fec3d1 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/socket.fms @@ -0,0 +1,2241 @@ +38( +object +wall +patch0 +patch +patch1 +patch +patch2 +patch +patch3 +patch +patch4 +patch +patch5 +patch +patch7 +patch +patch8 +patch +patch9 +patch +patch10 +patch +patch11 +patch +patch13 +patch +patch14 +patch +patch15 +patch +patch16 +patch +patch17 +patch +patch18 +patch +patch19 +patch +patch20 +patch +patch21 +patch +patch22 +patch +patch23 +patch +patch24 +patch +patch25 +patch +patch26 +patch +path27 +patch +patch28 +patch +patch29 +patch +patch30 +patch +patch31 +patch +patch32 +patch +patch33 +patch +patch34 +patch +patch35 +patch +patch36 +patch +patch37 +patch +patch6 +patch) +836((-98.4808 17.3648 25) (-100 0 25) (-90.472 14.6634 25) (-58.9291 18.1066 25) (-67.9289 7.07107 25) (-50 9.6225 25) (-76.6044 -64.2788 25) (-64.2788 -76.6044 25) (-61.2753 -61.6257 25) (-50 -48.1125 25) (-50 -67.3575 25) (-82.0711 7.07107 25) (-81.203 24.5589 25) (-93.9693 34.202 25) (-67.5886 27.0128 25) (-50 28.8675 25) (-75 10 25) (-50 -86.6025 25) (-77.7885 41.2952 25) (-64.1254 44.5169 25) (-86.6025 50 25) (-50 48.1125 25) (-76.6044 64.2788 25) (-61.4482 60.1728 25) (-50 67.3575 25) (-64.2788 76.6044 25) (-50 86.6025 25) (-76.5403 -27.9427 25) (-75 -10 25) (-86.3348 -19.8135 25) (-62.9265 -20.6629 25) (-82.0711 -7.07107 25) (-93.9693 -34.202 25) (-67.9289 -7.07107 25) (-63.2012 -36.5076 25) (-91.3679 -8.97974 25) (-77.4233 -43.4472 25) (-98.4808 -17.3648 25) (-50 -9.6225 25) (-50 -28.8675 25) (-85 0 25) (-86.6025 -50 25) (-65.9129 -50.6425 25) (-65 0 25) (38.6275 74.5675 75) (50 67.3575 75) (50 86.6025 75) (27.5 78.4821 75) (27.5 60.8198 75) (38.8583 -55.5402 75) (27.5 -60.8198 75) (38.6268 -74.3693 75) (50 -67.3575 75) (38.9169 56.2753 75) (27.5 -43.1574 75) (50 -48.1125 75) (50 48.1125 75) (27.5 43.1574 75) (50 -86.6025 75) (27.5 -78.4821 75) (35.2517 93.5805 75) (42.7684 90.3928 75) (42.7684 -90.3928 75) (35.2517 -93.5805 75) (27.5 96.1444 75) (27.5 -96.1444 75) (36.3417 9.24839 75) (36.3417 -9.24839 75) (50 9.6225 75) (50 -9.6225 75) (38.7748 25.5778 75) (40.3789 -22.1533 75) (50 28.8675 75) (27.5 25.4951 75) (50 -28.8675 75) (27.5 -25.4951 75) (40.559 40.5083 75) (38.9258 -37.7032 75) (-20 81.4151 0) (-20 64.8505 0) (0 80.0149 0) (20 64.8505 0) (20 81.4151 0) (-13.3836 99.1004 0) (13.3836 99.1004 0) (-20 97.9796 0) (-6.70689 99.7748 0) (20 97.9796 0) (6.70689 99.7748 0) (0 100 0) (0 47.412 0) (0 60.5293 0) (-20 48.286 0) (20 48.286 0) (-6.99057 36.8427 0) (6.99057 36.8427 0) (-20 31.7214 0) (20 31.7214 0) (-50 -86.6025 41.6667) (-50 -86.6025 58.3333) (-50 -72.7398 45.1315) (-50 50 60) (-50 42.9289 57.0711) (-50 38.1931 66.569) (-50 28.8675 75) (-50 48.1125 75) (-50 -72.4016 61.5374) (-50 -86.6025 75) (-50 -67.3575 75) (-50 -57.0711 57.0711) (-50 -60 50) (-50 50 40) (-50 -57.0711 42.9289) (-50 24.777 61.2904) (-50 -59.3991 66.7554) (-50 42.9289 42.9289) (-50 40 50) (-50 9.6225 75) (-50 86.6025 58.3333) (-50 67.3575 75) (-50 86.6025 75) (-50 86.6025 41.6667) (-50 72.7615 54.9694) (-50 60 50) (-50 57.0711 57.0711) (-50 72.9043 38.7048) (-50 57.0711 42.9289) (-50 9.31671 41.8755) (-50 -42.9289 42.9289) (-50 -28.8675 75) (-50 -9.6225 75) (-50 -9.20725 58.1596) (-50 7.72654 59.5349) (-50 -42.9289 57.0711) (-50 -24.3431 54.6496) (-50 -7.54086 40.5115) (-50 -24.3141 38.9123) (-50 -40 50) (-50 -48.1125 75) (-50 -50 60) (-50 24.425 45.4369) (-50 -50 40) (-79.8138 -27.1233 -25) (-93.9693 -34.202 -25) (-87.1351 -19.2209 -25) (-75 -10 -25) (-67.9289 -7.07107 -25) (-67.1672 -27.2873 -25) (-58.8409 -18.1346 -25) (-50 -28.8675 -25) (-98.4808 -17.3648 -25) (-82.0711 -7.07107 -25) (-50 -9.6225 -25) (-91.5168 -8.74011 -25) (-100 0 -25) (-85 0 -25) (-65 0 -25) (-63.9539 -44.7004 -25) (-77.4794 -42.1095 -25) (-50 -48.1125 -25) (-86.6025 -50 -25) (-76.6044 -64.2788 -25) (-61.418 -60.2423 -25) (-50 -67.3575 -25) (-64.2788 -76.6044 -25) (-50 -86.6025 -25) (-63.77 35.8952 -25) (-78.1277 25.7829 -25) (-77.6899 42.7319 -25) (-63.1721 20.406 -25) (-93.9693 34.202 -25) (-66.0782 50.3346 -25) (-75 10 -25) (-50 28.8675 -25) (-86.6025 50 -25) (-89.7207 15.4527 -25) (-50 48.1125 -25) (-76.6044 64.2788 -25) (-67.9289 7.07107 -25) (-82.0711 7.07107 -25) (-50 9.6225 -25) (-64.2788 76.6044 -25) (-50 86.6025 -25) (-50 67.3575 -25) (-61.3177 61.5263 -25) (-98.4808 17.3648 -25) (33.5378 16.777 61.0519) (37.3559 3.28438 58.0102) (20 76.0222 15.0039) (20 97.9796 16.6667) (20 62.8929 25.7602) (20 60.6066 39.3934) (20 79.2233 32.1829) (22.6774 29.8661 50) (20 31.7214 50) (20 31.7214 33.3333) (27.5 25.4951 62.5) (27.5 35 50) (27.5 25.4951 50) (-36.3417 -9.24839 75) (-27.5 -25.4951 75) (-33.5351 -16.7824 61.0745) (-27.5 -25.4951 62.5) (-27.5 -25.4951 50) (-22.6774 -29.8661 50) (-20 -31.7214 33.3333) (-25.1837 -27.7854 50) (-20 -40 50) (-20 -42.9289 42.9289) (-20 -31.7214 50) (20 -31.7214 33.3333) (22.6774 -29.8661 50) (25.1837 -27.7854 50) (35.6194 -11.7263 53.7453) (27.5 -25.4951 50) (27.5 -25.4951 62.5) (20 -39.3934 39.3934) (20 -31.7214 50) (20 -43.758 25.2531) (20 -50 35) (20 -64.8505 0) (20 -49.8517 11.8026) (20 -48.286 0) (20 -59.5852 25.5168) (-20 97.9796 50) (-20 78.9898 50) (-20 97.9796 33.3333) (-27.5 42.9289 57.0711) (-27.5 50 60) (-27.5 38.8384 66.7925) (-27.5 25.4951 62.5) (-27.5 25.4951 75) (-20 -57.6764 13.4257) (-20 -75.6829 15.1229) (-20 -64.8505 0) (-20 -62.1725 27.2886) (-20 -57.0711 42.9289) (-20 -78.8495 31.6006) (-27.5 -42.9289 57.0711) (27.5 36.1733 68.1145) (27.5 39.3934 60.6066) (20 97.9796 33.3333) (20 65 50) (27.5 -35 50) (20 -35 50) (20 -69.4506 14.8283) (-27.5 55.2476 66.9116) (-27.5 43.1574 75) (-20 -81.4151 0) (-20 -50 40) (-20 97.9796 16.6667) (-20 83.9674 19.9229) (-27.5 25.4951 50) (-27.5 40 50) (-36.3417 9.24839 75) (-20 -48.286 0) (-20 -45.6982 25.7885) (-33.3967 -17.056 43.464) (-37.3561 -3.2825 58.0705) (-35.6139 11.743 53.8604) (33.3945 17.0604 43.4034) (25.1837 27.7854 50) (20 57.8078 12.7685) (20 50 35) (20 45.5064 24.0211) (20 39.3934 39.3934) (37.4402 2.11676 39.0684) (34.274 -15.2166 35.0879) (20 -31.7214 16.6667) (20 35 50) (20 -31.7214 0) (-20 60 50) (-20 74.5519 34.028) (27.5 60.6066 60.6066) (27.5 66.2171 67.7504) (27.5 76.8004 61.1116) (27.5 -66.2171 67.7504) (27.5 -50 65) (-27.5 96.1444 75) (-27.5 78.4821 75) (-27.5 96.1444 62.5) (-27.5 -73.4553 63.5117) (-27.5 -57.0711 57.0711) (-27.5 -55.2476 66.9116) (-27.5 -60.8198 75) (27.5 50 65) (20 -97.9796 50) (20 -81.4898 50) (20 -97.9796 33.3333) (-27.5 96.1444 50) (-27.5 78.0722 50) (-27.5 73.4553 63.5117) (-27.5 -50 60) (-27.5 -43.1574 75) (27.5 -36.1733 68.1145) (20 -81.4151 0) (20 -97.9796 0) (20 -97.9796 16.6667) (20 -84.3761 19.6041) (20 -76.0618 33.425) (20 -65 50) (-27.5 60 50) (-27.5 57.0711 57.0711) (27.5 -96.1444 50) (27.5 -96.1444 62.5) (27.5 -80.5722 50) (27.5 -65 50) (27.5 -76.8004 61.1116) (27.5 96.1444 50) (27.5 80.5722 50) (27.5 96.1444 62.5) (27.5 -60.6066 60.6066) (-27.5 -96.1444 50) (-27.5 -78.0722 50) (-27.5 -96.1444 62.5) (-27.5 -96.1444 75) (-27.5 -78.4821 75) (27.5 65 50) (-27.5 -60 50) (20 -60.6066 39.3934) (-27.5 60.8198 75) (-20 -97.9796 16.6667) (-20 -97.9796 0) (-20 -97.9796 33.3333) (-20 -78.9898 50) (-27.5 -38.8384 66.7925) (-27.5 -40 50) (20 81.4898 50) (27.5 -39.3934 60.6066) (-20 -97.9796 50) (-20 -60 50) (20 97.9796 50) (34.9655 13.5522 -56.227) (32.476 18.75 -75) (37.5 0 -75) (-20 43.9211 27.0189) (-20 31.7214 16.6667) (-20 49.7152 12.4405) (-20 31.7214 33.3333) (-33.4723 16.9073 18.2472) (-18.75 -32.476 -75) (-25.0898 -27.8703 -52.7154) (-9.77074 -36.2047 -55.3444) (-21.223 -30.9166 -34.874) (-37.4323 -2.25275 2.36658) (-32.3394 -18.9845 7.84387) (-30.9723 -21.1416 -14.419) (-13.4703 -34.9972 -18.3411) (-33.3888 17.0715 0.780048) (29.4828 23.1736 -15.3386) (32.1117 19.3672 7.48614) (31.5798 20.2229 -36.9367) (37.3331 3.53357 -18.437) (37.4996 -0.172499 -37.9034) (19.8668 31.805 -57.3293) (-33.7446 -16.3569 -59.8798) (-34.3296 -15.0907 -36.4073) (-37.4717 -1.45742 -15.9083) (11.0649 35.8304 -18.8367) (16.1087 33.8639 -36.7898) (20 31.7214 16.6667) (32.4669 18.7657 26.2883) (20 42.9891 10.7098) (37.4483 1.96876 20.689) (37.3569 3.2728 1.15635) (33.7839 -16.2758 -0.75261) (33.6967 -16.4554 -19.5029) (36.6441 -7.96625 -56.816) (32.0358 -19.4924 -39.2304) (-20 58.6722 27.2612) (-34.2369 15.2998 35.3898) (0 -37.5 -75) (-1.8284 -37.4554 -36.9408) (-20 -31.7214 0) (-37.4611 -1.70839 21.1626) (-24.242 28.6108 -21.0482) (-8.64115 36.4908 -17.8341) (-33.1556 17.5202 -16.5603) (-37.5 0 -75) (-37.4964 0.521254 -50.7867) (-37.3461 3.39372 -31.6059) (-33.2228 17.3925 -36.523) (-4.28242 37.2547 -37.0287) (-1.45427 37.4718 -55.7041) (-20.2142 31.5854 -56.3313) (-18.75 32.476 -75) (-21.8234 30.4957 -38.0135) (-33.2312 17.3763 -55.9708) (-32.476 18.75 -75) (18.75 32.476 -75) (-32.476 -18.75 -75) (0 37.5 -75) (23.2669 -29.4092 -22.2881) (17.3132 -33.2642 -38.6666) (26.8281 -26.2012 -56.9324) (32.476 -18.75 -75) (18.75 -32.476 -75) (-20 57.0711 42.9289) (-20 68.9073 15.3707) (-20 42.9289 42.9289) (-20 40 50) (-20 31.7214 50) (-22.6774 29.8661 50) (-25.1837 27.7854 50) (9.4897 -36.2794 -56.4108) (-20 -43.0859 11.2998) (-20 -31.7214 16.6667) (-32.4986 -18.7106 26.4243) (-37.4428 -2.06999 39.2501) (6.99057 -36.8427 0) (7.0086 -36.8392 -18.2398) (-6.99057 -36.8427 0) (33.6503 -16.5501 17.5219) (-20 50 40) (39.5601 35.3693 46.6922) (32.3647 39.5932 39.1973) (50 35 50) (50 39.3934 39.3934) (38.6605 63.1428 57.2297) (50 60.6066 60.6066) (38.7482 50.1971 64.9987) (38.773 37.2567 57.9126) (50 50 65) (50 39.3934 60.6066) (35.1847 56.4486 36.4569) (50 50 35) (50 60.6066 39.3934) (37.135 46.7259 35.3617) (36.8547 63.896 44.352) (50 65 50) (0 -71.7622 0) (0 -87.0832 0) (13.3836 -99.1004 0) (-13.3836 -99.1004 0) (6.70689 -99.7748 0) (-6.70689 -99.7748 0) (0 -100 0) (0 -54.2451 0) (-40.5084 -48.1569 59.8287) (-37.0198 -43.8869 57.9139) (-36.6093 -58.8915 45.4238) (-35.1456 -52.7371 40.3819) (-38.7903 -54.4475 58.9565) (-38.6088 -59.3911 53.4361) (-35.8862 -43.4206 42.4693) (-38.4021 -40.1766 51.8711) (50 -48.1125 25) (50 -50 35) (50 -67.3575 25) (50 -39.3934 60.6066) (50 74.3415 61.8582) (50 86.6025 58.3333) (50 74.2906 44.8203) (50 -39.3934 39.3934) (50 -35 50) (50 -22.2245 61.2431) (50 86.6025 41.6667) (50 67.3575 25) (50 86.6025 25) (50 -28.8675 25) (50 -23.0532 44.8966) (50 -86.6025 58.3333) (50 -75.4061 48.0166) (50 -74.3334 62.5671) (50 -86.6025 41.6667) (50 -65 50) (50 -60.6066 60.6066) (50 -86.6025 25) (50 -75.1752 35.2676) (50 -60.6066 39.3934) (50 -50 65) (50 -12.3722 39.0134) (50 -9.6225 25) (50 4.24366 42.6158) (50 11.8037 60.8572) (50 -5.58971 57.5541) (50 22.5939 54.2272) (50 48.1125 25) (50 9.6225 25) (50 28.2388 40.5597) (50 28.8675 25) (50 17.7589 37.3466) (63.1835 20.4106 25) (75 10 25) (78.1402 25.7865 25) (93.9693 34.202 25) (77.6996 42.7398 25) (67.9289 7.07107 25) (82.0711 7.07107 25) (89.7303 15.4472 25) (98.4808 17.3648 25) (65 0 25) (85 0 25) (100 0 25) (64.2788 -76.6044 25) (63.7764 35.8998 25) (86.6025 50 25) (76.6044 64.2788 25) (66.0812 50.3368 25) (61.3178 61.5265 25) (64.2788 76.6044 25) (79.858 -27.4478 25) (77.6146 -42.5462 25) (93.9693 -34.202 25) (67.3911 -29.0453 25) (86.6025 -50 25) (87.1138 -19.2772 25) (75 -10 25) (63.9444 -45.2133 25) (76.6044 -64.2788 25) (98.4808 -17.3648 25) (60.991 -18.0167 25) (91.5102 -8.75708 25) (82.0711 -7.07107 25) (61.3915 -60.3858 25) (67.9289 -7.07107 25) (-8.17844 -47.0148 -75) (-20.3431 -50.1686 -75) (30.1879 -43.3257 -75) (50 -28.8675 -75) (-10.2498 -63.5607 -75) (-32.3359 -60.5982 -75) (-50 -67.3575 -75) (-27.8383 -78.2461 -75) (50 -48.1125 -75) (-50 -86.6025 -75) (8.34963 -49.0482 -75) (-50 -48.1125 -75) (-32.2308 -45.3474 -75) (50 -9.6225 -75) (-36.7316 -34.2036 -75) (50 9.6225 -75) (-50 -28.8675 -75) (34.202 -93.9693 -75) (17.3648 -98.4808 -75) (16.7654 -81.8564 -75) (0 -100 -75) (35.8735 -78.2658 -75) (50 -86.6025 -75) (-4.71315 -80.8405 -75) (50 -67.3575 -75) (31.9366 -62.7449 -75) (-17.3648 -98.4808 -75) (12.119 -63.9104 -75) (-34.202 -93.9693 -75) (9.37727 64.3489 -75) (14.8182 47.9341 -75) (-6.73263 49.1968 -75) (17.3648 98.4808 -75) (34.202 93.9693 -75) (26.8879 77.9891 -75) (-50 48.1125 -75) (-29.95 43.1732 -75) (-50 28.8675 -75) (1.4079 82.2671 -75) (-12.9612 63.5763 -75) (-32.8384 61.9158 -75) (0 100 -75) (-50 67.3575 -75) (-20.4052 79.7278 -75) (-17.3648 98.4808 -75) (-37.0799 77.7597 -75) (-50 86.6025 -75) (-34.202 93.9693 -75) (50 28.8675 -75) (-50 -9.6225 -75) (33.5608 39.2491 -75) (50 48.1125 -75) (-50 9.6225 -75) (31.0341 58.4031 -75) (50 67.3575 -75) (50 86.6025 -75) (-50 38.9141 -40.8553) (-50 56.9708 -41.6522) (-50 48.9286 -56.1358) (-50 32.7919 -58.1342) (-50 20.6227 -41.5526) (-50 14.0935 -58.3566) (-50 -86.6025 -58.3333) (-50 1.31775 -41.8772) (-50 -6.16398 -58.6027) (-50 66.6042 -60.9663) (-50 72.4408 -45.1781) (-50 86.6025 -41.6667) (-50 86.6025 -58.3333) (-50 -39.6067 -42.3045) (-50 -18.9388 -42.4878) (-50 -61.0775 -40.8996) (-50 -29.0415 -59.9655) (-50 -51.7631 -58.1259) (-50 -70.3049 -55.1289) (-50 -86.6025 -41.6667) (93.9693 34.202 -25) (81.2015 24.5598 -25) (77.7882 41.2953 -25) (75 10 -25) (67.5854 27.0152 -25) (50 28.8675 -25) (58.9285 18.1069 -25) (50 9.6225 -25) (67.9289 7.07107 -25) (90.4705 14.6652 -25) (82.0711 7.07107 -25) (98.4808 17.3648 -25) (65 0 -25) (100 0 -25) (85 0 -25) (50 -9.6225 -25) (86.6025 50 -25) (64.1232 44.519 -25) (76.6044 64.2788 -25) (50 48.1125 -25) (61.4484 60.172 -25) (50 67.3575 -25) (64.2788 76.6044 -25) (50 86.6025 -25) (77.4232 -43.4472 -25) (86.6025 -50 -25) (76.6044 -64.2788 -25) (93.9693 -34.202 -25) (65.9129 -50.6425 -25) (76.5403 -27.9427 -25) (61.2753 -61.6257 -25) (63.2012 -36.5076 -25) (86.3348 -19.8135 -25) (64.2788 -76.6044 -25) (50 -48.1125 -25) (62.9265 -20.6629 -25) (75 -10 -25) (98.4808 -17.3648 -25) (50 -67.3575 -25) (67.9289 -7.07107 -25) (91.3679 -8.97975 -25) (82.0711 -7.07107 -25) (50 -28.8675 -25) (50 -86.6025 -25) (50 -51.5177 -41.872) (50 -28.0125 -40.2176) (50 -39.6697 -57.6908) (50 -61.1182 -59.0886) (50 74.9599 -41.2947) (50 58.5014 -41.5594) (50 70.779 -58.5287) (50 86.6025 -58.3333) (50 -19.3334 -57.7609) (50 86.6025 -41.6667) (50 -70.2628 -44.8561) (50 -86.6025 -58.3333) (50 -86.6025 -41.6667) (50 14.8663 -58.4416) (50 33.981 -58.2872) (50 19.8883 -41.7934) (50 -1.76026 -61.2305) (50 52.8706 -58.3816) (50 -2.82931 -43.2484) (50 39.9586 -41.6283) (38.627 -36.0851 55.6013) (38.7419 -44.3385 63.8906) (36.6956 -63.5667 43.6012) (35.0899 -55.5723 36.0734) (38.7411 -55.9092 63.787) (38.6185 -63.971 55.46) (36.7146 -36.3923 43.6888) (35.0929 -44.3639 36.0991) (65.7761 75.3227 14.953) (53.0082 84.7946 7.18018) (36.3222 93.1703 20.308) (37.053 92.882 37.1706) (83.5447 54.9571 -0.204582) (76.6544 64.2192 -12.9205) (70.3409 71.0786 1.47508) (79.3607 60.8431 12.6644) (25.4911 -96.6964 -55.8091) (38.8506 -92.1446 -54.264) (36.2141 -93.2123 -36.9311) (34.7327 -93.7744 -16.0932) (56.9654 -82.1884 -12.8692) (49.9874 -86.6098 -1.35914) (34.3321 -93.9218 4.1825) (20.5118 -97.8737 -36.1001) (9.04165 -99.5904 -55.6649) (61.2701 79.0315 -10.042) (14.1378 -98.9956 -18.6292) (88.8787 45.8321 -12.4096) (92.8747 37.0715 -0.1349) (89.4625 44.6818 12.2368) (22.5155 97.4323 50) (25.016 96.8204 50) (39.2656 91.9685 55.8745) (34.3396 -93.9191 21.8686) (46.1781 -88.6994 12.2251) (35.6132 93.4436 4.12214) (47.4798 88.0095 -7.63112) (34.7811 93.7564 -13.9596) (2.17111 -99.9764 -37.0793) (-4.15257 -99.9137 -18.4073) (-16.4069 -98.6449 -37.1516) (-9.63293 -99.535 -55.7352) (-30.515 -95.2304 -54.0087) (30.5386 95.2229 -54.0167) (34.1021 94.0056 -33.0557) (-35.2517 -93.5805 75) (20.6881 97.8366 -19.0489) (-42.7684 -90.3928 75) (-39.2656 -91.9685 55.8744) (39.2665 -91.9681 55.9636) (76.1299 -64.8401 13.1775) (95.647 -29.1831 -12.5165) (86.8246 -49.6135 -13.4291) (91.9574 -39.2917 -0.568089) (88.4105 -46.7288 12.1154) (81.6519 -57.7318 -0.197758) (99.5185 -9.80141 -12.3868) (99.5907 9.03858 -12.3789) (99.9991 -0.416489 -0.064092) (99.6001 8.93394 12.3255) (96.2174 27.2437 12.3115) (98.264 18.5522 -0.061308) (22.5155 -97.4323 50) (25.016 -96.8204 50) (36.9775 -92.9121 37.5153) (99.5329 -9.65377 12.257) (95.9067 -28.318 12.0851) (98.0268 -19.7673 -0.202037) (60.4894 -79.6306 11.9434) (67.4343 -73.8418 -0.134955) (73.4611 -67.8488 -12.3904) (96.1185 27.5906 -12.3821) (-34.6546 93.8033 -16.1476) (-56.9547 82.1959 -12.8877) (-49.9767 86.616 -1.38088) (-34.3293 93.9228 21.8746) (-46.1796 88.6986 12.2171) (-79.3664 -60.8356 12.6628) (-96.131 -27.5468 -12.3849) (-88.8886 -45.8128 -12.411) (-92.8816 -37.0542 -0.137898) (-83.5527 -54.9449 -0.206588) (-89.468 -44.6708 12.2345) (-60.486 79.6332 11.9276) (-67.4208 73.8541 -0.150617) (-73.4484 67.8625 -12.4043) (-99.5881 -9.06697 -12.3787) (-98.2656 -18.5439 -0.056713) (-36.9782 92.9119 37.517) (-65.7797 -75.3195 14.9518) (-76.661 -64.2113 -12.9207) (-70.347 -71.0725 1.47391) (-61.2739 -79.0286 -10.0423) (-53.0109 -84.7929 7.17859) (-34.285 93.939 4.174) (-36.1727 93.2284 -36.9681) (-76.1193 64.8525 13.1683) (-81.6289 57.7643 -0.210629) (-88.3918 46.7642 12.1066) (-99.6002 -8.93358 12.3277) (-96.2203 -27.2335 12.3122) (-99.9992 0.407363 -0.064789) (-99.5096 9.89181 -12.4091) (-98.004 19.8799 -0.222364) (-95.6263 29.2507 -12.5369) (-91.9278 39.3609 -0.583074) (-86.8061 49.6458 -13.4447) (-99.534 9.64234 12.2585) (-95.8872 28.3838 12.0748) (-25.016 -96.8204 50) (-34.0799 -94.0136 -33.0533) (-20.6573 -97.8431 -19.044) (-34.7716 -93.76 -13.9625) (4.20548 99.9115 -18.4222) (9.68083 99.5303 -55.7605) (-8.98427 99.5956 -55.7105) (-2.08806 99.9782 -37.1245) (16.4596 98.6361 -37.1697) (-37.053 -92.882 37.1703) (-35.6133 -93.4435 4.12026) (-36.323 -93.17 20.3068) (-25.4516 96.7069 -55.8478) (-35.2517 93.5805 75) (-22.5155 -97.4323 50) (-39.2668 91.968 55.9654) (-42.7684 90.3928 75) (-25.016 96.8204 50) (-22.5155 97.4323 50) (-47.479 -88.0099 -7.63341) (-14.0535 99.0076 -18.6679) (-38.8343 92.1515 -54.2819) (-20.4194 97.893 -36.1707) (85 0 8.33333) (82.0711 -7.07107 8.33333) (85 0 -8.33333) (82.0711 -7.07107 -8.33333) (82.0711 7.07107 8.33333) (75 10 -8.33333) (75 10 8.33333) (67.9289 7.07107 -8.33333) (75 -10 8.33333) (75 -10 -8.33333) (82.0711 7.07107 -8.33333) (65 0 8.33333) (67.9289 -7.07107 8.33333) (67.9289 7.07107 8.33333) (67.9289 -7.07107 -8.33333) (65 0 -8.33333) (-67.9289 -7.07107 -8.33333) (-65 0 -8.33333) (-67.9289 -7.07107 8.33333) (-65 0 8.33333) (-75 -10 -8.33333) (-82.0711 -7.07107 -8.33333) (-82.0711 -7.07107 8.33333) (-85 0 8.33333) (-67.9289 7.07107 -8.33333) (-67.9289 7.07107 8.33333) (-75 -10 8.33333) (-82.0711 7.07107 -8.33333) (-75 10 -8.33333) (-85 0 -8.33333) (-75 10 8.33333) (-82.0711 7.07107 8.33333) (-36.2567 58.1386 44.1894) (-40.1038 59.9273 51.2039) (-38.7364 45.8624 59.1039) (-38.5748 40.5611 53.3026) (-38.6983 53.2097 59.4709) (-36.9531 58.2533 55.6466) (-35.0499 49.8411 40.0013) (-36.4184 41.5206 44.6991) (-38.9169 56.2753 75) (-40.559 40.5083 75) (-38.7748 25.5778 75) (-38.6268 -74.3694 75) (-38.6275 74.5675 75) (-38.9258 -37.7032 75) (-40.3789 -22.1533 75) (-38.8583 -55.5405 75)) +1696 +( +((0 1 2) 7) +((3 4 5) 7) +((6 7 8) 7) +((9 8 10) 7) +((11 12 2) 7) +((0 2 13) 7) +((14 4 3) 7) +((15 3 5) 7) +((8 7 10) 7) +((11 16 12) 7) +((13 2 12) 7) +((15 14 3) 7) +((16 4 14) 7) +((10 7 17) 7) +((12 16 14) 7) +((13 12 18) 7) +((15 19 14) 7) +((18 12 14) 7) +((13 18 20) 7) +((15 21 19) 7) +((18 14 19) 7) +((18 22 20) 7) +((19 21 23) 7) +((19 22 18) 7) +((23 21 24) 7) +((22 19 23) 7) +((25 23 24) 7) +((25 22 23) 7) +((26 25 24) 7) +((27 28 29) 7) +((27 30 28) 7) +((28 31 29) 7) +((32 27 29) 7) +((30 33 28) 7) +((27 34 30) 7) +((29 31 35) 7) +((32 36 27) 7) +((32 29 37) 7) +((38 33 30) 7) +((27 36 34) 7) +((34 39 30) 7) +((31 40 35) 7) +((37 29 35) 7) +((32 41 36) 7) +((11 2 40) 7) +((9 42 8) 7) +((42 6 8) 7) +((5 4 43) 7) +((1 40 2) 7) +((9 34 42) 7) +((42 36 6) 7) +((5 43 38) 7) +((36 41 6) 7) +((37 35 1) 7) +((35 40 1) 7) +((9 39 34) 7) +((34 36 42) 7) +((39 38 30) 7) +((38 43 33) 7) +((44 45 46) 2) +((47 48 44) 2) +((49 50 51) 2) +((52 49 51) 2) +((53 45 44) 2) +((48 53 44) 2) +((54 50 49) 2) +((52 55 49) 2) +((53 56 45) 2) +((48 57 53) 2) +((52 51 58) 2) +((50 59 51) 2) +((47 44 60) 2) +((61 44 46) 2) +((62 58 51) 2) +((51 59 63) 2) +((61 60 44) 2) +((64 47 60) 2) +((62 51 63) 2) +((59 65 63) 2) +((66 67 68) 2) +((67 69 68) 2) +((66 68 70) 2) +((71 69 67) 2) +((68 72 70) 2) +((73 66 70) 2) +((71 74 69) 2) +((75 71 67) 2) +((70 72 76) 2) +((73 70 57) 2) +((77 74 71) 2) +((75 77 71) 2) +((76 57 70) 2) +((72 56 76) 2) +((77 55 74) 2) +((54 77 75) 2) +((57 76 53) 2) +((76 56 53) 2) +((49 55 77) 2) +((54 49 77) 2) +((78 79 80) 28) +((81 82 80) 28) +((83 78 80) 28) +((80 82 84) 28) +((83 85 78) 28) +((83 80 86) 28) +((82 87 84) 28) +((88 80 84) 28) +((80 89 86) 28) +((88 89 80) 28) +((90 91 92) 28) +((91 90 93) 28) +((91 79 92) 28) +((92 94 90) 28) +((90 95 93) 28) +((81 91 93) 28) +((80 79 91) 28) +((94 95 90) 28) +((96 94 92) 28) +((93 95 97) 28) +((81 80 91) 28) +((98 10 17) 37) +((99 100 98) 37) +((101 102 103) 37) +((104 105 103) 37) +((106 107 108) 37) +((109 110 106) 37) +((21 111 24) 37) +((110 112 100) 37) +((98 100 10) 37) +((103 102 113) 37) +((104 103 113) 37) +((106 108 114) 37) +((109 106 114) 37) +((115 111 21) 37) +((100 112 10) 37) +((116 113 102) 37) +((117 104 113) 37) +((118 119 120) 37) +((121 122 118) 37) +((118 122 119) 37) +((122 123 124) 37) +((121 125 122) 37) +((122 124 119) 37) +((125 123 122) 37) +((26 125 121) 37) +((119 124 101) 37) +((125 126 123) 37) +((26 24 125) 37) +((105 119 101) 37) +((24 126 125) 37) +((99 106 100) 37) +((105 101 103) 37) +((99 107 106) 37) +((24 111 126) 37) +((106 110 100) 37) +((15 5 127) 37) +((39 9 128) 37) +((129 130 131) 37) +((127 131 132) 37) +((133 129 134) 37) +((5 135 127) 37) +((39 128 136) 37) +((129 131 134) 37) +((131 127 135) 37) +((133 134 137) 37) +((128 137 136) 37) +((5 38 135) 37) +((38 39 136) 37) +((135 134 131) 37) +((136 137 134) 37) +((38 136 135) 37) +((135 136 134) 37) +((114 108 138) 37) +((109 114 139) 37) +((115 140 116) 37) +((115 21 15) 37) +((112 141 10) 37) +((116 140 113) 37) +((117 113 132) 37) +((139 114 138) 37) +((115 15 140) 37) +((10 141 9) 37) +((140 132 113) 37) +((130 117 132) 37) +((139 138 133) 37) +((15 127 140) 37) +((9 141 128) 37) +((132 140 127) 37) +((130 132 131) 37) +((133 138 129) 37) +((142 143 144) 8) +((144 145 142) 8) +((145 146 147) 8) +((147 148 149) 8) +((144 143 150) 8) +((151 145 144) 8) +((146 148 147) 8) +((149 148 152) 8) +((144 150 153) 8) +((151 144 153) 8) +((146 152 148) 8) +((153 150 154) 8) +((151 153 155) 8) +((156 152 146) 8) +((147 149 157) 8) +((142 145 147) 8) +((143 142 158) 8) +((158 147 157) 8) +((157 149 159) 8) +((158 142 147) 8) +((160 143 158) 8) +((157 161 158) 8) +((162 157 159) 8) +((160 158 161) 8) +((161 157 162) 8) +((162 159 163) 8) +((164 161 162) 8) +((164 162 163) 8) +((165 164 163) 8) +((166 167 168) 8) +((167 166 169) 8) +((170 168 167) 8) +((171 166 168) 8) +((169 172 167) 8) +((173 169 166) 8) +((170 174 168) 8) +((170 167 175) 8) +((176 166 171) 8) +((171 168 177) 8) +((178 172 169) 8) +((172 179 167) 8) +((173 180 169) 8) +((176 173 166) 8) +((168 174 177) 8) +((181 182 183) 8) +((155 153 154) 8) +((156 180 152) 8) +((181 183 184) 8) +((175 155 154) 8) +((156 178 180) 8) +((181 184 177) 8) +((183 176 184) 8) +((185 175 154) 8) +((179 155 175) 8) +((180 178 169) 8) +((184 171 177) 8) +((184 176 171) 8) +((170 175 185) 8) +((167 179 175) 8) +((186 187 66) 36) +((188 189 82) 15) +((190 191 192) 15) +((192 189 188) 15) +((193 194 195) 36) +((196 197 198) 12) +((196 186 73) 36) +((199 200 201) 36) +((202 203 201) 36) +((204 205 206) 36) +((207 208 209) 23) +((210 211 212) 36) +((213 67 187) 36) +((214 215 213) 36) +((210 216 217) 19) +((218 219 216) 19) +((220 221 222) 19) +((221 223 218) 19) +((224 225 226) 27) +((227 228 229) 24) +((230 229 231) 24) +((232 233 234) 23) +((235 236 237) 23) +((204 209 205) 36) +((238 203 202) 20) +((202 201 200) 36) +((73 239 196) 12) +((240 197 196) 12) +((241 189 192) 15) +((191 242 192) 15) +((189 87 82) 15) +((186 66 73) 36) +((210 217 211) 36) +((187 67 66) 36) +((215 67 213) 36) +((215 214 243) 16) +((216 244 217) 19) +((220 245 221) 19) +((223 219 218) 19) +((223 221 245) 19) +((228 246 229) 24) +((229 247 231) 24) +((234 233 248) 23) +((235 237 233) 23) +((249 236 235) 23) +((250 226 251) 27) +((78 85 250) 27) +((227 229 230) 24) +((252 253 227) 24) +((230 231 254) 36) +((255 232 234) 23) +((232 256 235) 23) +((256 205 208) 23) +((257 203 205) 36) +((258 201 257) 36) +((259 254 258) 36) +((198 260 186) 36) +((195 198 261) 36) +((188 262 190) 15) +((263 190 264) 15) +((263 264 265) 15) +((265 195 194) 15) +((262 188 81) 15) +((260 266 187) 36) +((210 214 267) 36) +((267 213 266) 36) +((210 268 218) 19) +((233 232 235) 23) +((249 235 256) 23) +((208 205 209) 23) +((249 256 208) 23) +((205 203 206) 36) +((203 257 201) 36) +((201 258 199) 36) +((258 254 199) 36) +((196 198 186) 36) +((193 195 261) 36) +((190 192 188) 15) +((263 191 190) 15) +((269 265 194) 15) +((81 188 82) 15) +((260 187 186) 36) +((210 212 214) 36) +((266 213 187) 36) +((267 214 213) 36) +((210 218 216) 19) +((221 270 222) 19) +((218 268 221) 19) +((225 271 272) 27) +((226 225 272) 27) +((273 274 275) 12) +((274 47 275) 12) +((276 50 277) 16) +((278 279 280) 24) +((281 282 283) 20) +((284 281 283) 20) +((285 274 273) 12) +((48 47 274) 12) +((277 50 54) 16) +((286 287 288) 19) +((289 280 290) 24) +((280 279 291) 24) +((283 282 292) 20) +((284 283 293) 20) +((285 48 274) 12) +((277 54 294) 16) +((295 296 297) 19) +((297 288 298) 19) +((288 287 299) 19) +((287 300 299) 19) +((290 280 291) 24) +((301 290 302) 24) +((303 304 305) 16) +((306 305 307) 16) +((305 304 307) 16) +((65 59 304) 16) +((308 309 310) 12) +((306 307 311) 16) +((304 59 307) 16) +((312 313 314) 20) +((315 314 316) 20) +((309 317 275) 12) +((310 309 275) 12) +((64 310 47) 12) +((311 307 276) 16) +((307 59 276) 16) +((314 313 281) 20) +((318 282 313) 20) +((314 281 316) 20) +((273 275 317) 12) +((310 275 47) 12) +((311 276 277) 16) +((59 50 276) 16) +((313 282 281) 20) +((284 316 281) 20) +((299 319 223) 19) +((302 291 246) 24) +((246 320 247) 24) +((321 322 248) 23) +((237 323 321) 23) +((236 324 237) 23) +((238 202 325) 20) +((238 326 203) 20) +((202 200 325) 20) +((73 57 239) 12) +((239 240 196) 12) +((327 241 192) 15) +((242 327 192) 15) +((75 67 215) 36) +((215 243 328) 16) +((295 245 220) 19) +((223 319 219) 19) +((299 223 245) 19) +((228 302 246) 24) +((246 247 229) 24) +((233 321 248) 23) +((321 233 237) 23) +((291 279 320) 24) +((329 323 324) 23) +((283 292 325) 20) +((283 325 293) 20) +((285 57 48) 12) +((294 54 75) 16) +((328 277 294) 16) +((295 297 298) 19) +((298 288 299) 19) +((299 300 319) 19) +((302 290 291) 24) +((291 320 246) 24) +((330 324 236) 23) +((324 323 237) 23) +((238 325 292) 20) +((325 200 293) 20) +((285 239 57) 12) +((285 240 239) 12) +((331 241 327) 15) +((215 294 75) 16) +((215 328 294) 16) +((295 298 245) 19) +((298 299 245) 19) +((332 333 334) 36) +((335 336 337) 27) +((337 96 92) 27) +((336 338 339) 36) +((340 341 342) 36) +((343 342 341) 36) +((344 345 346) 36) +((347 343 346) 36) +((339 344 348) 36) +((97 349 350) 36) +((349 351 352) 36) +((351 332 353) 36) +((354 333 332) 36) +((336 96 337) 27) +((336 339 348) 36) +((341 340 355) 36) +((356 343 341) 36) +((346 357 344) 36) +((356 346 343) 36) +((344 357 348) 36) +((349 97 358) 36) +((349 359 351) 36) +((360 350 361) 36) +((362 97 360) 15) +((363 350 364) 36) +((364 352 365) 36) +((352 353 366) 36) +((353 367 368) 36) +((332 334 367) 36) +((337 369 335) 27) +((79 337 92) 27) +((338 336 335) 27) +((339 338 370) 36) +((342 371 340) 36) +((372 342 343) 36) +((373 346 345) 36) +((344 374 345) 36) +((346 373 347) 36) +((347 372 343) 36) +((339 374 344) 36) +((360 97 350) 36) +((364 350 349) 36) +((352 364 349) 36) +((352 351 353) 36) +((353 332 367) 36) +((96 375 376) 36) +((96 377 375) 36) +((378 379 355) 36) +((380 356 379) 36) +((380 381 377) 36) +((376 382 358) 36) +((382 383 359) 36) +((384 385 383) 36) +((375 386 376) 36) +((377 381 375) 36) +((379 378 387) 36) +((380 379 381) 36) +((376 386 382) 36) +((383 382 384) 36) +((388 387 378) 36) +((388 385 384) 36) +((375 381 386) 36) +((381 379 387) 36) +((382 386 384) 36) +((388 384 387) 36) +((381 387 386) 36) +((386 387 384) 36) +((351 354 332) 36) +((354 389 333) 36) +((336 348 96) 36) +((340 390 355) 36) +((356 341 355) 36) +((357 346 356) 36) +((348 357 377) 36) +((94 376 95) 36) +((358 97 95) 36) +((358 359 349) 36) +((359 354 351) 36) +((383 389 354) 36) +((383 391 389) 36) +((94 96 376) 36) +((96 348 377) 36) +((355 390 378) 36) +((356 355 379) 36) +((380 357 356) 36) +((380 377 357) 36) +((376 358 95) 36) +((358 382 359) 36) +((359 383 354) 36) +((385 391 383) 36) +((268 365 270) 36) +((366 392 270) 36) +((392 368 393) 36) +((394 395 396) 36) +((272 397 369) 27) +((251 272 398) 27) +((78 251 398) 27) +((399 400 401) 27) +((338 402 403) 36) +((252 230 259) 36) +((394 396 404) 36) +((393 394 404) 36) +((255 373 405) 23) +((405 406 256) 23) +((205 406 407) 36) +((408 257 407) 36) +((409 410 411) 36) +((392 393 410) 36) +((408 370 259) 36) +((195 361 260) 36) +((362 264 262) 15) +((264 360 195) 15) +((268 270 221) 19) +((272 271 397) 27) +((251 226 272) 27) +((78 250 251) 27) +((401 402 338) 36) +((252 227 230) 24) +((259 230 254) 36) +((255 405 232) 23) +((405 256 232) 23) +((256 406 205) 23) +((205 407 257) 36) +((408 258 257) 36) +((409 270 410) 36) +((270 392 410) 36) +((408 259 258) 36) +((260 198 195) 36) +((262 264 190) 15) +((264 195 265) 15) +((93 262 81) 15) +((260 361 266) 36) +((210 267 412) 36) +((267 266 363) 36) +((210 412 268) 36) +((195 360 361) 36) +((362 360 264) 15) +((93 97 362) 15) +((363 361 350) 36) +((412 363 364) 36) +((412 364 365) 36) +((365 352 366) 36) +((366 353 368) 36) +((368 367 394) 36) +((367 334 395) 36) +((369 413 335) 27) +((369 337 398) 27) +((79 398 337) 27) +((338 335 399) 27) +((252 370 338) 36) +((404 371 342) 36) +((372 404 342) 36) +((406 373 345) 36) +((374 407 345) 36) +((411 347 373) 36) +((410 372 347) 36) +((339 370 374) 36) +((93 362 262) 15) +((266 361 363) 36) +((267 363 412) 36) +((412 365 268) 36) +((365 366 270) 36) +((366 368 392) 36) +((368 394 393) 36) +((367 395 394) 36) +((369 397 413) 27) +((272 369 398) 27) +((78 398 79) 27) +((374 370 408) 36) +((410 393 372) 36) +((411 410 347) 36) +((407 374 408) 36) +((406 345 407) 36) +((405 373 406) 23) +((393 404 372) 36) +((404 396 371) 36) +((252 259 370) 36) +((252 338 403) 36) +((335 413 399) 27) +((338 399 401) 27) +((197 414 415) 30) +((414 416 417) 30) +((197 415 265) 30) +((418 273 317) 30) +((419 420 418) 30) +((197 421 414) 30) +((421 416 414) 30) +((197 265 269) 30) +((420 273 418) 30) +((419 422 420) 30) +((197 240 421) 30) +((421 423 416) 30) +((420 285 273) 30) +((420 422 423) 30) +((421 240 420) 30) +((423 421 420) 30) +((240 285 420) 30) +((424 425 426) 30) +((427 425 424) 30) +((428 424 426) 30) +((417 425 427) 30) +((263 427 424) 30) +((191 424 428) 30) +((428 426 429) 30) +((415 417 427) 30) +((427 263 415) 30) +((191 263 424) 30) +((317 191 428) 30) +((418 428 429) 30) +((417 415 414) 30) +((415 263 265) 30) +((428 418 317) 30) +((242 191 317) 30) +((419 418 429) 30) +((411 373 255) 29) +((430 248 431) 29) +((432 295 431) 29) +((431 248 433) 29) +((432 296 295) 29) +((432 431 434) 29) +((248 322 433) 29) +((435 431 433) 29) +((431 436 434) 29) +((435 436 431) 29) +((220 222 437) 29) +((222 409 437) 29) +((220 437 430) 29) +((409 411 437) 29) +((270 409 222) 29) +((295 220 430) 29) +((234 430 437) 29) +((437 411 255) 29) +((295 430 431) 29) +((234 248 430) 29) +((234 437 255) 29) +((292 438 439) 33) +((438 133 439) 33) +((318 236 440) 33) +((112 440 441) 33) +((438 292 442) 33) +((139 133 438) 33) +((330 236 318) 33) +((440 443 318) 33) +((112 110 440) 33) +((442 139 438) 33) +((442 292 282) 33) +((443 440 110) 33) +((443 282 318) 33) +((109 139 442) 33) +((442 282 443) 33) +((109 443 110) 33) +((109 442 443) 33) +((208 326 444) 33) +((208 207 326) 33) +((326 445 444) 33) +((208 444 249) 33) +((326 238 445) 33) +((445 137 444) 33) +((444 441 249) 33) +((238 439 445) 33) +((141 444 128) 33) +((112 441 141) 33) +((440 236 441) 33) +((439 133 445) 33) +((238 292 439) 33) +((141 441 444) 33) +((249 441 236) 33) +((444 137 128) 33) +((445 133 137) 33) +((446 447 448) 5) +((449 74 55) 5) +((450 46 45) 5) +((419 429 450) 5) +((451 450 452) 5) +((446 453 447) 5) +((454 455 449) 5) +((455 74 449) 5) +((419 450 45) 5) +((450 429 452) 5) +((456 457 458) 5) +((451 452 456) 5) +((459 453 446) 5) +((454 453 460) 5) +((454 460 455) 5) +((69 74 455) 5) +((419 45 422) 5) +((461 462 463) 5) +((461 463 58) 5) +((464 462 461) 5) +((462 465 463) 5) +((58 463 52) 5) +((465 466 463) 5) +((464 467 468) 5) +((464 468 462) 5) +((469 465 462) 5) +((463 466 52) 5) +((468 467 448) 5) +((468 469 462) 5) +((466 470 52) 5) +((469 468 448) 5) +((52 470 55) 5) +((448 447 469) 5) +((449 55 470) 5) +((451 46 450) 5) +((471 472 473) 5) +((474 475 473) 5) +((72 474 476) 5) +((72 476 423) 5) +((477 425 417) 5) +((473 472 478) 5) +((473 476 474) 5) +((476 416 423) 5) +((417 416 479) 5) +((480 477 417) 5) +((473 478 481) 5) +((476 473 481) 5) +((479 416 476) 5) +((480 417 479) 5) +((481 478 480) 5) +((481 479 476) 5) +((479 481 480) 5) +((429 426 452) 5) +((456 452 457) 5) +((460 453 459) 5) +((475 455 460) 5) +((69 455 475) 5) +((56 422 45) 5) +((452 426 457) 5) +((460 459 471) 5) +((471 475 460) 5) +((69 475 68) 5) +((423 422 56) 5) +((426 425 457) 5) +((471 459 472) 5) +((475 471 473) 5) +((475 474 68) 5) +((72 68 474) 5) +((72 423 56) 5) +((457 425 477) 5) +((482 483 484) 6) +((485 486 484) 6) +((487 483 482) 6) +((478 482 480) 6) +((483 488 484) 6) +((485 484 489) 6) +((487 482 478) 6) +((484 488 489) 6) +((485 489 490) 6) +((487 478 491) 6) +((488 492 489) 6) +((490 489 493) 6) +((467 494 448) 6) +((472 491 478) 6) +((480 482 495) 6) +((485 496 486) 6) +((495 484 486) 6) +((484 495 482) 6) +((477 480 495) 6) +((486 496 497) 6) +((486 498 495) 6) +((498 477 495) 6) +((498 486 497) 6) +((499 477 498) 6) +((497 499 498) 6) +((457 477 499) 6) +((499 497 500) 6) +((457 499 500) 6) +((457 500 458) 6) +((501 502 503) 6) +((502 501 504) 6) +((502 505 503) 6) +((503 506 501) 6) +((507 504 501) 6) +((502 504 508) 6) +((509 505 502) 6) +((503 510 506) 6) +((507 501 506) 6) +((507 511 504) 6) +((509 502 508) 6) +((508 504 459) 6) +((510 512 506) 6) +((507 506 513) 6) +((459 504 511) 6) +((489 492 493) 6) +((514 448 494) 6) +((446 448 514) 6) +((515 491 472) 6) +((492 513 512) 6) +((493 492 512) 6) +((509 514 494) 6) +((446 514 508) 6) +((511 515 472) 6) +((459 511 472) 6) +((512 513 506) 6) +((510 493 512) 6) +((446 508 459) 6) +((509 508 514) 6) +((507 515 511) 6) +((516 517 340) 4) +((518 395 519) 4) +((520 521 517) 4) +((522 521 523) 4) +((371 516 340) 4) +((516 520 517) 4) +((524 518 519) 4) +((396 395 518) 4) +((523 521 520) 4) +((525 522 523) 4) +((371 526 516) 4) +((522 527 521) 4) +((521 528 517) 4) +((519 395 529) 4) +((517 528 340) 4) +((527 528 521) 4) +((529 395 334) 4) +((530 340 528) 4) +((528 527 530) 4) +((529 334 531) 4) +((390 340 530) 4) +((530 527 532) 4) +((531 334 333) 4) +((533 534 535) 4) +((535 534 536) 4) +((533 537 538) 4) +((533 535 537) 4) +((536 539 535) 4) +((537 540 538) 4) +((535 541 537) 4) +((539 536 542) 4) +((539 543 535) 4) +((541 540 537) 4) +((541 535 543) 4) +((523 542 544) 4) +((523 539 542) 4) +((543 539 520) 4) +((543 526 518) 4) +((524 540 541) 4) +((543 518 541) 4) +((520 526 543) 4) +((371 396 526) 4) +((525 523 544) 4) +((523 520 539) 4) +((526 396 518) 4) +((524 541 518) 4) +((516 526 520) 4) +((545 546 547) 4) +((548 549 550) 4) +((551 552 553) 4) +((547 385 552) 4) +((550 545 554) 4) +((545 547 555) 4) +((548 550 554) 4) +((551 556 552) 4) +((555 547 552) 4) +((554 545 555) 4) +((548 554 557) 4) +((551 558 556) 4) +((555 552 556) 4) +((554 555 559) 4) +((560 557 554) 4) +((561 558 562) 4) +((556 558 561) 4) +((559 555 556) 4) +((560 554 559) 4) +((563 561 562) 4) +((559 556 561) 4) +((560 559 563) 4) +((563 559 561) 4) +((390 530 532) 4) +((564 531 333) 4) +((390 532 565) 4) +((564 333 566) 4) +((390 565 378) 4) +((567 564 566) 4) +((333 389 566) 4) +((565 568 378) 4) +((567 566 569) 4) +((566 389 546) 4) +((568 388 378) 4) +((570 567 569) 4) +((550 569 545) 4) +((391 385 547) 4) +((385 388 552) 4) +((552 388 553) 4) +((571 550 549) 4) +((546 391 547) 4) +((569 546 545) 4) +((570 569 550) 4) +((553 388 568) 4) +((571 570 550) 4) +((389 391 546) 4) +((569 566 546) 4) +((572 176 573) 9) +((574 575 572) 9) +((575 551 553) 9) +((173 176 572) 9) +((572 575 576) 9) +((575 553 577) 9) +((173 572 576) 9) +((576 575 577) 9) +((577 553 568) 9) +((525 578 522) 9) +((173 576 180) 9) +((576 577 579) 9) +((577 568 580) 9) +((574 551 575) 9) +((574 572 573) 9) +((176 183 573) 9) +((574 581 551) 9) +((574 573 581) 9) +((573 183 582) 9) +((558 551 581) 9) +((573 582 581) 9) +((183 583 582) 9) +((558 581 562) 9) +((582 584 581) 9) +((583 584 582) 9) +((182 583 183) 9) +((581 584 562) 9) +((149 585 159) 9) +((149 586 585) 9) +((587 159 585) 9) +((586 588 585) 9) +((152 586 149) 9) +((589 587 585) 9) +((163 159 587) 9) +((586 580 588) 9) +((589 585 588) 9) +((152 579 586) 9) +((589 590 587) 9) +((163 587 591) 9) +((580 565 588) 9) +((590 578 591) 9) +((522 578 590) 9) +((180 576 579) 9) +((527 588 532) 9) +((527 522 589) 9) +((579 577 580) 9) +((588 565 532) 9) +((580 568 565) 9) +((163 591 165) 9) +((587 590 591) 9) +((589 522 590) 9) +((180 579 152) 9) +((527 589 588) 9) +((579 580 586) 9) +((592 593 594) 10) +((593 595 596) 10) +((597 598 599) 10) +((596 600 598) 10) +((593 592 601) 10) +((602 595 593) 10) +((598 600 599) 10) +((601 592 603) 10) +((601 602 593) 10) +((599 600 604) 10) +((605 601 603) 10) +((606 602 601) 10) +((607 599 604) 10) +((606 601 605) 10) +((597 596 598) 10) +((595 600 596) 10) +((594 593 596) 10) +((608 592 594) 10) +((597 609 596) 10) +((594 596 609) 10) +((608 594 610) 10) +((597 611 609) 10) +((609 610 594) 10) +((609 611 612) 10) +((610 609 612) 10) +((612 611 613) 10) +((614 610 612) 10) +((614 612 613) 10) +((615 614 613) 10) +((616 617 618) 10) +((619 617 616) 10) +((620 616 618) 10) +((619 616 621) 10) +((618 622 620) 10) +((616 620 623) 10) +((623 621 616) 10) +((619 621 624) 10) +((622 618 625) 10) +((622 626 620) 10) +((620 626 623) 10) +((621 623 627) 10) +((621 628 624) 10) +((619 624 629) 10) +((630 622 625) 10) +((631 607 604) 10) +((606 605 632) 10) +((606 632 633) 10) +((631 627 607) 10) +((605 629 632) 10) +((633 632 624) 10) +((607 627 634) 10) +((631 628 627) 10) +((630 625 635) 10) +((632 629 624) 10) +((633 624 628) 10) +((634 627 623) 10) +((627 628 621) 10) +((626 634 623) 10) +((630 626 622) 10) +((626 636 637) 11) +((638 639 524) 11) +((626 637 634) 11) +((640 613 641) 11) +((640 642 643) 11) +((638 637 636) 11) +((519 638 524) 11) +((637 607 634) 11) +((641 613 611) 11) +((642 640 641) 11) +((643 642 571) 11) +((644 637 638) 11) +((519 644 638) 11) +((639 638 636) 11) +((645 640 643) 11) +((640 615 613) 11) +((524 639 540) 11) +((626 630 636) 11) +((636 646 639) 11) +((645 615 640) 11) +((639 647 540) 11) +((636 630 646) 11) +((646 647 639) 11) +((647 538 540) 11) +((630 648 646) 11) +((648 647 646) 11) +((635 648 630) 11) +((649 564 650) 11) +((649 531 564) 11) +((650 564 567) 11) +((651 649 650) 11) +((652 531 649) 11) +((650 567 653) 11) +((649 651 654) 11) +((650 655 651) 11) +((529 531 652) 11) +((654 652 649) 11) +((653 567 570) 11) +((655 650 653) 11) +((651 599 654) 11) +((654 607 637) 11) +((641 611 655) 11) +((641 653 642) 11) +((642 570 571) 11) +((644 654 637) 11) +((519 529 644) 11) +((655 611 597) 11) +((651 597 599) 11) +((654 599 607) 11) +((653 641 655) 11) +((653 570 642) 11) +((644 652 654) 11) +((644 529 652) 11) +((655 597 651) 11) +((656 449 657) 32) +((328 657 277) 32) +((306 658 319) 32) +((658 469 659) 32) +((449 470 657) 32) +((277 657 660) 32) +((658 306 661) 32) +((300 306 319) 32) +((465 469 658) 32) +((657 470 660) 32) +((277 660 311) 32) +((661 306 311) 32) +((661 465 658) 32) +((466 660 470) 32) +((660 661 311) 32) +((466 465 661) 32) +((466 661 660) 32) +((662 216 663) 32) +((216 662 243) 32) +((219 663 216) 32) +((663 453 662) 32) +((243 662 656) 32) +((244 216 243) 32) +((219 659 663) 32) +((453 454 662) 32) +((447 453 663) 32) +((662 454 656) 32) +((243 656 328) 32) +((319 659 219) 32) +((659 447 663) 32) +((454 449 656) 32) +((328 656 657) 32) +((319 658 659) 32) +((469 447 659) 32) +((458 664 665) 3) +((458 666 667) 3) +((308 667 241) 3) +((668 669 670) 3) +((671 670 664) 3) +((608 610 669) 3) +((534 533 672) 3) +((673 674 672) 3) +((635 674 648) 3) +((675 635 676) 3) +((675 677 678) 3) +((296 675 678) 3) +((675 674 635) 3) +((679 672 674) 3) +((680 534 672) 3) +((669 610 614) 3) +((664 670 665) 3) +((670 669 681) 3) +((666 241 667) 3) +((458 665 666) 3) +((682 296 432) 3) +((675 296 682) 3) +((592 608 683) 3) +((496 671 497) 3) +((684 683 668) 3) +((685 668 671) 3) +((241 686 687) 3) +((308 310 688) 3) +((688 456 667) 3) +((497 664 500) 3) +((297 678 689) 3) +((677 690 678) 3) +((675 676 677) 3) +((676 635 625) 3) +((674 673 648) 3) +((672 533 673) 3) +((683 608 669) 3) +((497 671 664) 3) +((669 668 683) 3) +((671 668 670) 3) +((308 241 687) 3) +((308 688 667) 3) +((458 667 456) 3) +((458 500 664) 3) +((297 296 678) 3) +((691 692 693) 3) +((694 682 695) 3) +((694 696 697) 3) +((542 697 698) 3) +((542 698 544) 3) +((578 525 544) 3) +((695 436 435) 3) +((643 549 699) 3) +((692 615 693) 3) +((643 699 645) 3) +((615 645 700) 3) +((691 693 87) 3) +((315 701 314) 3) +((694 695 696) 3) +((696 698 697) 3) +((698 578 544) 3) +((433 695 435) 3) +((548 699 549) 3) +((693 615 700) 3) +((700 645 699) 3) +((702 87 693) 3) +((99 703 107) 3) +((701 703 704) 3) +((674 675 679) 3) +((672 679 680) 3) +((536 534 680) 3) +((669 614 681) 3) +((670 681 665) 3) +((189 241 666) 3) +((691 666 665) 3) +((434 682 432) 3) +((682 679 675) 3) +((694 680 679) 3) +((697 536 680) 3) +((681 614 615) 3) +((665 681 692) 3) +((189 666 691) 3) +((691 665 692) 3) +((434 695 682) 3) +((694 679 682) 3) +((694 697 680) 3) +((542 536 697) 3) +((434 436 695) 3) +((643 571 549) 3) +((615 692 681) 3) +((189 691 87) 3) +((304 705 63) 3) +((464 461 705) 3) +((505 509 706) 3) +((619 707 708) 3) +((707 709 708) 3) +((505 706 710) 3) +((710 711 709) 3) +((712 605 713) 3) +((714 712 713) 3) +((490 715 716) 3) +((717 715 714) 3) +((718 288 719) 3) +((304 303 705) 3) +((464 705 720) 3) +((494 706 509) 3) +((619 708 617) 3) +((711 708 709) 3) +((706 711 710) 3) +((605 603 713) 3) +((714 713 717) 3) +((490 716 485) 3) +((715 717 716) 3) +((721 510 722) 3) +((503 722 510) 3) +((493 510 721) 3) +((721 722 723) 3) +((461 58 62) 3) +((723 722 709) 3) +((503 710 722) 3) +((707 629 712) 3) +((707 712 723) 3) +((493 721 715) 3) +((714 721 723) 3) +((63 705 62) 3) +((65 304 63) 3) +((705 461 62) 3) +((619 629 707) 3) +((707 723 709) 3) +((505 710 503) 3) +((710 709 722) 3) +((629 605 712) 3) +((723 712 714) 3) +((493 715 490) 3) +((721 714 715) 3) +((718 286 288) 3) +((310 64 60) 3) +((61 451 688) 3) +((288 689 720) 3) +((690 467 689) 3) +((724 467 690) 3) +((725 724 677) 3) +((726 625 618) 3) +((726 725 676) 3) +((538 647 533) 3) +((727 592 683) 3) +((683 684 727) 3) +((496 685 671) 3) +((668 685 684) 3) +((331 686 241) 3) +((688 310 60) 3) +((451 456 688) 3) +((288 297 689) 3) +((690 689 678) 3) +((724 690 677) 3) +((677 676 725) 3) +((676 625 726) 3) +((673 647 648) 3) +((533 647 673) 3) +((288 303 719) 3) +((303 720 705) 3) +((464 720 467) 3) +((494 724 706) 3) +((708 618 617) 3) +((708 711 726) 3) +((711 706 725) 3) +((713 603 727) 3) +((727 717 713) 3) +((485 716 685) 3) +((684 716 717) 3) +((61 46 451) 3) +((720 303 288) 3) +((467 720 689) 3) +((494 467 724) 3) +((724 725 706) 3) +((726 618 708) 3) +((725 726 711) 3) +((603 592 727) 3) +((717 727 684) 3) +((485 685 496) 3) +((716 684 685) 3) +((61 688 60) 3) +((728 729 730) 3) +((182 181 729) 3) +((731 732 26) 3) +((41 733 6) 3) +((734 143 735) 3) +((736 735 737) 3) +((738 737 733) 3) +((739 732 730) 3) +((730 729 740) 3) +((729 181 741) 3) +((739 26 732) 3) +((41 738 733) 3) +((734 150 143) 3) +((735 736 734) 3) +((737 738 736) 3) +((181 177 741) 3) +((740 739 730) 3) +((741 740 729) 3) +((25 26 739) 3) +((32 738 41) 3) +((742 150 734) 3) +((743 734 736) 3) +((744 289 226) 3) +((17 7 745) 3) +((746 160 161) 3) +((747 746 748) 3) +((747 749 745) 3) +((728 750 85) 3) +((728 751 182) 3) +((750 731 250) 3) +((121 744 26) 3) +((744 226 731) 3) +((6 745 7) 3) +((735 160 746) 3) +((737 746 747) 3) +((733 747 745) 3) +((728 730 750) 3) +((728 182 729) 3) +((750 732 731) 3) +((744 731 26) 3) +((6 733 745) 3) +((735 143 160) 3) +((746 737 735) 3) +((733 737 747) 3) +((730 732 750) 3) +((752 753 754) 3) +((20 22 752) 3) +((37 755 756) 3) +((757 758 742) 3) +((743 755 757) 3) +((759 760 758) 3) +((761 762 760) 3) +((754 753 761) 3) +((20 752 754) 3) +((1 755 37) 3) +((759 758 757) 3) +((763 757 755) 3) +((761 760 759) 3) +((754 761 764) 3) +((20 754 13) 3) +((1 763 755) 3) +((757 763 759) 3) +((764 761 759) 3) +((13 754 764) 3) +((0 763 1) 3) +((764 759 763) 3) +((13 764 0) 3) +((0 764 763) 3) +((756 736 738) 3) +((177 174 762) 3) +((741 177 762) 3) +((739 740 752) 3) +((740 741 753) 3) +((25 739 752) 3) +((32 756 738) 3) +((742 154 150) 3) +((734 743 742) 3) +((736 756 743) 3) +((758 185 154) 3) +((760 170 185) 3) +((762 174 170) 3) +((762 753 741) 3) +((753 752 740) 3) +((25 752 22) 3) +((37 756 32) 3) +((758 154 742) 3) +((757 742 743) 3) +((755 743 756) 3) +((760 185 758) 3) +((762 170 760) 3) +((753 762 761) 3) +((323 765 312) 3) +((766 767 768) 3) +((591 766 165) 3) +((767 322 768) 3) +((769 89 88) 3) +((770 557 771) 3) +((772 773 770) 3) +((769 702 773) 3) +((98 774 704) 3) +((323 312 774) 3) +((321 775 322) 3) +((323 776 321) 3) +((766 768 165) 3) +((768 322 775) 3) +((769 86 89) 3) +((562 584 563) 3) +((557 560 771) 3) +((560 563 777) 3) +((771 772 770) 3) +((772 769 773) 3) +((778 278 280) 3) +((98 17 774) 3) +((314 701 704) 3) +((323 329 779) 3) +((695 767 696) 3) +((766 698 696) 3) +((591 578 698) 3) +((433 767 695) 3) +((548 770 699) 3) +((700 702 693) 3) +((773 700 699) 3) +((84 87 702) 3) +((704 703 99) 3) +((312 314 704) 3) +((323 779 765) 3) +((766 696 767) 3) +((591 698 766) 3) +((433 322 767) 3) +((769 88 84) 3) +((548 557 770) 3) +((770 773 699) 3) +((702 700 773) 3) +((769 84 702) 3) +((98 704 99) 3) +((774 312 704) 3) +((780 118 781) 3) +((280 289 780) 3) +((226 782 783) 3) +((164 165 748) 3) +((776 17 749) 3) +((749 748 784) 3) +((83 785 85) 3) +((786 583 751) 3) +((787 777 751) 3) +((785 787 728) 3) +((121 118 780) 3) +((780 289 744) 3) +((289 782 226) 3) +((164 746 161) 3) +((164 748 746) 3) +((749 17 745) 3) +((747 748 749) 3) +((785 728 85) 3) +((751 583 182) 3) +((787 751 728) 3) +((750 250 85) 3) +((121 780 744) 3) +((731 226 250) 3) +((323 774 776) 3) +((776 775 321) 3) +((784 165 768) 3) +((784 768 775) 3) +((785 86 769) 3) +((563 584 786) 3) +((771 560 777) 3) +((777 563 786) 3) +((772 771 787) 3) +((785 769 772) 3) +((778 780 781) 3) +((785 772 787) 3) +((777 786 751) 3) +((787 771 777) 3) +((584 583 786) 3) +((83 86 785) 3) +((749 784 775) 3) +((748 165 784) 3) +((775 776 749) 3) +((774 17 776) 3) +((224 226 783) 3) +((778 280 780) 3) +((118 120 781) 3) +((513 788 789) 34) +((789 790 791) 34) +((606 633 791) 34) +((492 488 792) 34) +((793 792 794) 34) +((600 793 795) 34) +((513 789 507) 34) +((789 791 796) 34) +((791 633 797) 34) +((792 488 794) 34) +((793 794 795) 34) +((600 795 604) 34) +((600 595 793) 34) +((793 798 792) 34) +((492 792 788) 34) +((790 606 791) 34) +((788 790 789) 34) +((492 788 513) 34) +((793 595 798) 34) +((792 798 788) 34) +((602 606 790) 34) +((788 798 790) 34) +((595 602 798) 34) +((798 602 790) 34) +((491 799 487) 34) +((491 800 799) 34) +((487 799 801) 34) +((800 802 799) 34) +((515 800 491) 34) +((799 803 801) 34) +((487 801 483) 34) +((800 797 802) 34) +((803 799 802) 34) +((515 796 800) 34) +((801 803 795) 34) +((483 801 794) 34) +((507 789 796) 34) +((631 604 803) 34) +((796 791 797) 34) +((628 631 802) 34) +((633 628 797) 34) +((483 794 488) 34) +((801 795 794) 34) +((803 604 795) 34) +((507 796 515) 34) +((802 631 803) 34) +((796 797 800) 34) +((797 628 802) 34) +((156 804 805) 35) +((805 806 807) 35) +((33 43 807) 35) +((145 808 146) 35) +((809 810 808) 35) +((811 40 810) 35) +((156 805 178) 35) +((805 807 812) 35) +((807 43 813) 35) +((145 809 808) 35) +((11 40 811) 35) +((809 811 810) 35) +((31 810 40) 35) +((814 808 810) 35) +((804 146 808) 35) +((806 33 807) 35) +((804 806 805) 35) +((156 146 804) 35) +((31 814 810) 35) +((814 804 808) 35) +((28 33 806) 35) +((814 806 804) 35) +((31 28 814) 35) +((814 28 806) 35) +((179 815 155) 35) +((179 816 815) 35) +((155 815 817) 35) +((816 818 815) 35) +((172 816 179) 35) +((815 819 817) 35) +((155 817 151) 35) +((816 813 818) 35) +((815 818 819) 35) +((172 812 816) 35) +((811 817 819) 35) +((151 817 809) 35) +((813 4 818) 35) +((812 813 816) 35) +((818 16 819) 35) +((178 812 172) 35) +((817 811 809) 35) +((819 11 811) 35) +((151 809 145) 35) +((43 4 813) 35) +((4 16 818) 35) +((812 807 813) 35) +((16 11 819) 35) +((178 805 812) 35) +((686 331 327) 13) +((317 309 242) 13) +((686 327 687) 13) +((309 308 687) 13) +((242 309 327) 13) +((327 309 687) 13) +((197 261 198) 14) +((193 261 197) 14) +((269 193 197) 14) +((269 194 193) 14) +((217 244 211) 18) +((212 243 214) 18) +((211 244 243) 18) +((212 211 243) 18) +((305 306 300) 17) +((305 300 287) 17) +((305 287 719) 17) +((287 718 719) 17) +((305 719 303) 17) +((286 718 287) 17) +((318 313 330) 21) +((779 329 324) 21) +((330 313 324) 21) +((779 324 765) 21) +((324 313 765) 21) +((313 312 765) 21) +((326 206 203) 22) +((204 206 326) 22) +((207 204 326) 22) +((207 209 204) 22) +((403 402 253) 25) +((402 400 253) 25) +((403 253 252) 25) +((401 400 402) 25) +((224 783 225) 26) +((290 782 289) 26) +((225 783 782) 26) +((290 225 782) 26) +((290 271 225) 26) +((290 301 271) 26) +((301 820 397) 31) +((821 123 820) 31) +((822 102 101) 31) +((227 823 822) 31) +((820 301 821) 31) +((271 301 397) 31) +((124 123 821) 31) +((824 822 101) 31) +((227 822 228) 31) +((301 825 821) 31) +((124 821 825) 31) +((824 228 822) 31) +((124 824 101) 31) +((302 825 301) 31) +((124 825 824) 31) +((824 302 228) 31) +((824 825 302) 31) +((826 115 827) 31) +((826 111 115) 31) +((827 115 116) 31) +((827 399 826) 31) +((126 111 826) 31) +((827 116 823) 31) +((826 399 413) 31) +((399 827 253) 31) +((820 126 826) 31) +((823 116 102) 31) +((253 827 823) 31) +((397 826 413) 31) +((400 399 253) 31) +((397 820 826) 31) +((123 126 820) 31) +((823 102 822) 31) +((253 823 227) 31) +((828 105 829) 1) +((247 828 829) 1) +((829 105 104) 1) +((247 829 830) 1) +((315 316 701) 1) +((829 104 830) 1) +((247 830 231) 1) +((701 316 831) 1) +((703 701 831) 1) +((830 104 117) 1) +((247 320 828) 1) +((119 105 828) 1) +((828 320 832) 1) +((119 828 832) 1) +((320 279 832) 1) +((119 832 120) 1) +((832 279 778) 1) +((781 120 832) 1) +((279 278 778) 1) +((781 832 778) 1) +((129 833 834) 1) +((138 833 129) 1) +((833 200 834) 1) +((129 834 130) 1) +((138 835 833) 1) +((293 200 833) 1) +((200 199 834) 1) +((834 199 130) 1) +((108 835 138) 1) +((835 293 833) 1) +((130 199 117) 1) +((108 831 835) 1) +((284 293 835) 1) +((117 199 254) 1) +((108 107 831) 1) +((831 284 835) 1) +((254 830 117) 1) +((703 831 107) 1) +((316 284 831) 1) +((830 254 231) 1) +) +412 +( +(216 244) +(0 1) +(419 422) +(244 217) +(578 591) +(423 416) +(6 7) +(422 423) +(247 231) +(248 234) +(10 9) +(425 426) +(591 165) +(249 236) +(250 226) +(13 0) +(417 425) +(85 250) +(5 15) +(599 597) +(252 253) +(11 16) +(253 227) +(426 429) +(231 254) +(16 4) +(602 595) +(234 255) +(7 17) +(17 10) +(592 603) +(317 242) +(600 604) +(429 419) +(603 605) +(20 13) +(606 602) +(15 21) +(607 599) +(22 20) +(595 600) +(432 296) +(608 592) +(434 432) +(21 24) +(322 433) +(198 261) +(433 435) +(436 434) +(25 22) +(610 608) +(435 436) +(26 25) +(597 611) +(24 26) +(265 263) +(611 613) +(28 31) +(614 610) +(615 614) +(33 28) +(613 615) +(617 618) +(619 617) +(37 32) +(208 249) +(203 206) +(318 330) +(254 199) +(31 40) +(261 193) +(263 191) +(269 265) +(32 41) +(618 625) +(194 269) +(212 214) +(40 11) +(270 222) +(225 271) +(4 43) +(629 619) +(207 326) +(604 631) +(38 5) +(41 6) +(765 312) +(278 279) +(1 37) +(633 606) +(9 39) +(280 278) +(39 38) +(43 33) +(605 629) +(45 46) +(47 48) +(634 607) +(273 285) +(631 628) +(448 446) +(625 635) +(286 287) +(635 630) +(628 633) +(288 286) +(289 280) +(626 634) +(630 626) +(290 289) +(54 50) +(282 292) +(52 55) +(453 447) +(293 284) +(56 45) +(48 57) +(449 454) +(295 296) +(58 52) +(296 297) +(50 59) +(457 458) +(297 288) +(458 456) +(456 451) +(46 61) +(62 58) +(446 459) +(287 300) +(454 453) +(778 278) +(571 643) +(301 290) +(61 60) +(64 47) +(302 301) +(60 64) +(303 304) +(63 62) +(329 779) +(59 65) +(305 303) +(65 63) +(643 645) +(306 305) +(66 67) +(58 461) +(461 464) +(69 68) +(304 65) +(645 615) +(308 309) +(465 466) +(310 308) +(68 72) +(311 306) +(464 467) +(73 66) +(647 538) +(312 313) +(74 69) +(314 312) +(469 465) +(648 647) +(779 765) +(315 314) +(635 648) +(67 75) +(316 315) +(467 448) +(309 317) +(57 73) +(466 470) +(64 310) +(782 783) +(447 469) +(72 56) +(470 449) +(451 46) +(55 74) +(318 282) +(75 54) +(313 318) +(78 79) +(317 273) +(277 311) +(284 316) +(81 82) +(472 478) +(83 85) +(320 247) +(85 78) +(321 322) +(289 782) +(86 83) +(322 248) +(480 477) +(82 87) +(87 84) +(323 321) +(84 88) +(89 86) +(88 89) +(478 480) +(238 326) +(326 203) +(79 92) +(242 327) +(781 778) +(243 328) +(783 224) +(300 306) +(120 781) +(93 81) +(220 295) +(94 95) +(319 219) +(96 94) +(92 96) +(228 302) +(459 472) +(95 97) +(97 93) +(279 320) +(477 457) +(17 98) +(329 323) +(324 329) +(98 99) +(101 102) +(487 483) +(104 105) +(328 277) +(483 488) +(243 244) +(107 108) +(300 319) +(109 110) +(330 324) +(236 330) +(292 238) +(200 293) +(490 485) +(110 112) +(285 240) +(491 487) +(331 241) +(488 492) +(327 331) +(493 490) +(467 494) +(333 334) +(485 496) +(115 111) +(102 116) +(496 497) +(117 104) +(119 120) +(120 118) +(118 121) +(123 124) +(497 500) +(500 458) +(121 26) +(124 101) +(505 503) +(126 123) +(105 119) +(509 505) +(99 107) +(111 126) +(503 510) +(129 130) +(513 507) +(686 687) +(515 491) +(492 513) +(137 133) +(128 137) +(494 509) +(108 138) +(510 493) +(507 515) +(139 109) +(687 308) +(116 115) +(112 141) +(371 340) +(130 117) +(519 524) +(133 139) +(525 522) +(141 128) +(138 129) +(522 527) +(145 146) +(529 519) +(315 701) +(143 150) +(151 145) +(531 529) +(527 532) +(152 149) +(533 534) +(703 107) +(701 703) +(534 536) +(150 154) +(155 151) +(538 533) +(146 156) +(378 388) +(388 385) +(540 538) +(400 253) +(536 542) +(149 159) +(160 143) +(389 333) +(301 271) +(340 390) +(542 544) +(161 160) +(159 163) +(164 161) +(524 540) +(165 164) +(163 165) +(544 525) +(391 389) +(390 378) +(385 391) +(548 549) +(553 551) +(170 174) +(395 396) +(719 718) +(178 172) +(172 179) +(173 180) +(557 548) +(399 400) +(551 558) +(176 173) +(400 401) +(174 177) +(181 182) +(182 183) +(402 403) +(560 557) +(180 152) +(558 562) +(156 178) +(255 373) +(562 563) +(177 181) +(183 176) +(563 560) +(564 531) +(154 185) +(179 155) +(532 565) +(185 170) +(567 564) +(411 409) +(718 286) +(565 568) +(193 194) +(570 567) +(194 195) +(197 198) +(271 397) +(401 402) +(338 401) +(549 571) +(199 200) +(409 270) +(568 553) +(571 570) +(206 204) +(207 208) +(331 686) +(209 207) +(211 212) +(303 719) +(334 395) +(525 578) +(217 210) +(219 216) +(222 220) +(224 225) +(226 224) +(227 228) +(373 411) +(397 413) +(583 584) +(182 583) +(584 562) +(396 371) +(403 252) +(204 209) +(413 399) +(209 205) +(416 417) +(240 197) +(241 189) +(191 242) +(189 87) +(217 211) +(214 243) +(269 197) +)0() +2(subset1 +2 +16 +( +1615 +1588 +1589 +1590 +1591 +1608 +1609 +1592 +1610 +1593 +1611 +1594 +1612 +1595 +1613 +1614 +) subset2 +2 +24 +( +1596 +1597 +1598 +1599 +1600 +1601 +1602 +1603 +1604 +1605 +1606 +1607 +1616 +1617 +1618 +1582 +1619 +1620 +1583 +1621 +1584 +1585 +1586 +1587 +))0() \ No newline at end of file diff --git a/tutorials/tetMesh/socketOctree/system/controlDict b/tutorials/tetMesh/socketOctree/system/controlDict new file mode 100644 index 0000000000000000000000000000000000000000..81d538ef1824ee76994b7d770a63fced164e501b --- /dev/null +++ b/tutorials/tetMesh/socketOctree/system/controlDict @@ -0,0 +1,53 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// ************************************************************************* // + +applicationClass ; + +startFrom latestTime; + +startTime 0; + +stopAt endTime; + +endTime 2000; + +deltaT 1; + +writeControl timeStep; + +writeInterval 100; + +cycleWrite 0; + +writeFormat ascii; + +writeCompression compressed; + +timeFormat general; + +timePrecision 6; + +runTimeModifiable yes; + +nCorrectors 2; + +nNonOrthogonalCorrectors 0; + + +// ************************************************************************* // diff --git a/tutorials/tetMesh/socketOctree/system/fvSchemes b/tutorials/tetMesh/socketOctree/system/fvSchemes new file mode 100644 index 0000000000000000000000000000000000000000..01a0a06c660a62eb4fb5500bf890f709be1c8a27 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/system/fvSchemes @@ -0,0 +1,59 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSchemes; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +ddtSchemes +{ + default Euler; +} + +gradSchemes +{ + default Gauss linear; + grad(p) Gauss linear; +} + +divSchemes +{ + default none; + div(phi,U) Gauss linear; +} + +laplacianSchemes +{ + default none; + laplacian(nu,U) Gauss linear corrected; + laplacian((1|A(U)),p) Gauss linear corrected; +} + +interpolationSchemes +{ + default linear; + interpolate(HbyA) linear; +} + +snGradSchemes +{ + default corrected; +} + +fluxRequired +{ + default no; + p; +} + +// ************************************************************************* // diff --git a/tutorials/tetMesh/socketOctree/system/fvSolution b/tutorials/tetMesh/socketOctree/system/fvSolution new file mode 100644 index 0000000000000000000000000000000000000000..023baf93018bb01ff67a176648e077e7a9e06065 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/system/fvSolution @@ -0,0 +1,45 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + object fvSolution; +} +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +solvers +{ + p + { + solver PCG; + preconditioner DIC; + tolerance 1e-06; + relTol 0; + }; + + U + { + solver PBiCG; + preconditioner DILU; + tolerance 1e-05; + relTol 0; + }; +} + +PISO +{ + nCorrectors 2; + nNonOrthogonalCorrectors 0; + pRefCell 0; + pRefValue 0; +} + +// ************************************************************************* // diff --git a/tutorials/tetMesh/socketOctree/system/meshDict b/tutorials/tetMesh/socketOctree/system/meshDict new file mode 100644 index 0000000000000000000000000000000000000000..a34665c498822b197f897febc1f8349a619ce917 --- /dev/null +++ b/tutorials/tetMesh/socketOctree/system/meshDict @@ -0,0 +1,65 @@ +/*--------------------------------*- C++ -*----------------------------------*\ +| ========= | | +| \\ / F ield | cfMesh: A library for mesh generation | +| \\ / O peration | | +| \\ / A nd | Author: Franjo Juretic | +| \\/ M anipulation | E-mail: franjo.juretic@c-fields.com | +\*---------------------------------------------------------------------------*/ + +FoamFile +{ + version 2.0; + format ascii; + class dictionary; + location "system"; + object meshDict; +} + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +boundaryCellSize 1.5; +keepCellsIntersectingBoundary 1; +maxCellSize 3; +minCellSize 0.375; +removeGluedMesh 0; +surfaceFile "socket.fms"; + +boundaryLayers +{ + maxFirstLayerThickness 0.5; + nLayers 3; + thicknessRatio 1.2; + + patchBoundaryLayers + { + + patch7 + { + allowDiscontinuity 0; + maxFirstLayerThickness 0.5; + nLayers 4; + thicknessRatio 1.1; + } + } +} + +localRefinement +{ + + patch15 + { + additionalRefinementLevels 1; + } + + subset1 + { + cellSize 1.5; + } + + subset2 + { + cellSize 1.5; + } +} + +// ************************************************************************* // diff --git a/userGuide/User Guide - cfMesh v1.0.pdf b/userGuide/User Guide - cfMesh v1.0.pdf new file mode 100644 index 0000000000000000000000000000000000000000..3be6b8914bfd2cd6e34d8eef62d672dd6409e281 Binary files /dev/null and b/userGuide/User Guide - cfMesh v1.0.pdf differ diff --git a/userGuide/meshGenUserGuide.pdf b/userGuide/meshGenUserGuide.pdf deleted file mode 100644 index e19d4f8bd2ef39bd80f57b630b8f958ae6d076c5..0000000000000000000000000000000000000000 Binary files a/userGuide/meshGenUserGuide.pdf and /dev/null differ diff --git a/userGuide/meshGenUserGuide.ps b/userGuide/meshGenUserGuide.ps deleted file mode 100644 index f0dbede60cbdb9f095ce535aa3d4b3ac4fa683ba..0000000000000000000000000000000000000000 --- a/userGuide/meshGenUserGuide.ps +++ /dev/null @@ -1,1269 +0,0 @@ -%!PS-Adobe-2.0 -%%Creator: dvips(k) 5.95a Copyright 2005 Radical Eye Software -%%Title: meshGenUserGuide.dvi -%%Pages: 1 -%%PageOrder: Ascend -%%BoundingBox: 0 0 595 842 -%%DocumentFonts: CMBX10 CMR12 CMBX12 CMR10 CMSY10 -%%DocumentPaperSizes: a4 -%%EndComments -%DVIPSWebPage: (www.radicaleye.com) -%DVIPSCommandLine: dvips meshGenUserGuide.dvi -%DVIPSParameters: dpi=600 -%DVIPSSource: TeX output 2009.12.08:1045 -%%BeginProcSet: tex.pro 0 0 -%! -/TeXDict 300 dict def TeXDict begin/N{def}def/B{bind def}N/S{exch}N/X{S -N}B/A{dup}B/TR{translate}N/isls false N/vsize 11 72 mul N/hsize 8.5 72 -mul N/landplus90{false}def/@rigin{isls{[0 landplus90{1 -1}{-1 1}ifelse 0 -0 0]concat}if 72 Resolution div 72 VResolution div neg scale isls{ -landplus90{VResolution 72 div vsize mul 0 exch}{Resolution -72 div hsize -mul 0}ifelse TR}if Resolution VResolution vsize -72 div 1 add mul TR[ -matrix currentmatrix{A A round sub abs 0.00001 lt{round}if}forall round -exch round exch]setmatrix}N/@landscape{/isls true N}B/@manualfeed{ -statusdict/manualfeed true put}B/@copies{/#copies X}B/FMat[1 0 0 -1 0 0] -N/FBB[0 0 0 0]N/nn 0 N/IEn 0 N/ctr 0 N/df-tail{/nn 8 dict N nn begin -/FontType 3 N/FontMatrix fntrx N/FontBBox FBB N string/base X array -/BitMaps X/BuildChar{CharBuilder}N/Encoding IEn N end A{/foo setfont}2 -array copy cvx N load 0 nn put/ctr 0 N[}B/sf 0 N/df{/sf 1 N/fntrx FMat N -df-tail}B/dfs{div/sf X/fntrx[sf 0 0 sf neg 0 0]N df-tail}B/E{pop nn A -definefont setfont}B/Cw{Cd A length 5 sub get}B/Ch{Cd A length 4 sub get -}B/Cx{128 Cd A length 3 sub get sub}B/Cy{Cd A length 2 sub get 127 sub} -B/Cdx{Cd A length 1 sub get}B/Ci{Cd A type/stringtype ne{ctr get/ctr ctr -1 add N}if}B/CharBuilder{save 3 1 roll S A/base get 2 index get S -/BitMaps get S get/Cd X pop/ctr 0 N Cdx 0 Cx Cy Ch sub Cx Cw add Cy -setcachedevice Cw Ch true[1 0 0 -1 -.1 Cx sub Cy .1 sub]{Ci}imagemask -restore}B/D{/cc X A type/stringtype ne{]}if nn/base get cc ctr put nn -/BitMaps get S ctr S sf 1 ne{A A length 1 sub A 2 index S get sf div put -}if put/ctr ctr 1 add N}B/I{cc 1 add D}B/bop{userdict/bop-hook known{ -bop-hook}if/SI save N @rigin 0 0 moveto/V matrix currentmatrix A 1 get A -mul exch 0 get A mul add .99 lt{/QV}{/RV}ifelse load def pop pop}N/eop{ -SI restore userdict/eop-hook known{eop-hook}if showpage}N/@start{ -userdict/start-hook known{start-hook}if pop/VResolution X/Resolution X -1000 div/DVImag X/IEn 256 array N 2 string 0 1 255{IEn S A 360 add 36 4 -index cvrs cvn put}for pop 65781.76 div/vsize X 65781.76 div/hsize X}N -/p{show}N/RMat[1 0 0 -1 0 0]N/BDot 260 string N/Rx 0 N/Ry 0 N/V{}B/RV/v{ -/Ry X/Rx X V}B statusdict begin/product where{pop false[(Display)(NeXT) -(LaserWriter 16/600)]{A length product length le{A length product exch 0 -exch getinterval eq{pop true exit}if}{pop}ifelse}forall}{false}ifelse -end{{gsave TR -.1 .1 TR 1 1 scale Rx Ry false RMat{BDot}imagemask -grestore}}{{gsave TR -.1 .1 TR Rx Ry scale 1 1 false RMat{BDot} -imagemask grestore}}ifelse B/QV{gsave newpath transform round exch round -exch itransform moveto Rx 0 rlineto 0 Ry neg rlineto Rx neg 0 rlineto -fill grestore}B/a{moveto}B/delta 0 N/tail{A/delta X 0 rmoveto}B/M{S p -delta add tail}B/b{S p tail}B/c{-4 M}B/d{-3 M}B/e{-2 M}B/f{-1 M}B/g{0 M} -B/h{1 M}B/i{2 M}B/j{3 M}B/k{4 M}B/w{0 rmoveto}B/l{p -4 w}B/m{p -3 w}B/n{ -p -2 w}B/o{p -1 w}B/q{p 1 w}B/r{p 2 w}B/s{p 3 w}B/t{p 4 w}B/x{0 S -rmoveto}B/y{3 2 roll p a}B/bos{/SS save N}B/eos{SS restore}B end - -%%EndProcSet -%%BeginProcSet: texps.pro 0 0 -%! -TeXDict begin/rf{findfont dup length 1 add dict begin{1 index/FID ne 2 -index/UniqueID ne and{def}{pop pop}ifelse}forall[1 index 0 6 -1 roll -exec 0 exch 5 -1 roll VResolution Resolution div mul neg 0 0]FontType 0 -ne{/Metrics exch def dict begin Encoding{exch dup type/integertype ne{ -pop pop 1 sub dup 0 le{pop}{[}ifelse}{FontMatrix 0 get div Metrics 0 get -div def}ifelse}forall Metrics/Metrics currentdict end def}{{1 index type -/nametype eq{exit}if exch pop}loop}ifelse[2 index currentdict end -definefont 3 -1 roll makefont/setfont cvx]cvx def}def/ObliqueSlant{dup -sin S cos div neg}B/SlantFont{4 index mul add}def/ExtendFont{3 -1 roll -mul exch}def/ReEncodeFont{CharStrings rcheck{/Encoding false def dup[ -exch{dup CharStrings exch known not{pop/.notdef/Encoding true def}if} -forall Encoding{]exch pop}{cleartomark}ifelse}if/Encoding exch def}def -end - -%%EndProcSet -%%BeginProcSet: special.pro 0 0 -%! -TeXDict begin/SDict 200 dict N SDict begin/@SpecialDefaults{/hs 612 N -/vs 792 N/ho 0 N/vo 0 N/hsc 1 N/vsc 1 N/ang 0 N/CLIP 0 N/rwiSeen false N -/rhiSeen false N/letter{}N/note{}N/a4{}N/legal{}N}B/@scaleunit 100 N -/@hscale{@scaleunit div/hsc X}B/@vscale{@scaleunit div/vsc X}B/@hsize{ -/hs X/CLIP 1 N}B/@vsize{/vs X/CLIP 1 N}B/@clip{/CLIP 2 N}B/@hoffset{/ho -X}B/@voffset{/vo X}B/@angle{/ang X}B/@rwi{10 div/rwi X/rwiSeen true N}B -/@rhi{10 div/rhi X/rhiSeen true N}B/@llx{/llx X}B/@lly{/lly X}B/@urx{ -/urx X}B/@ury{/ury X}B/magscale true def end/@MacSetUp{userdict/md known -{userdict/md get type/dicttype eq{userdict begin md length 10 add md -maxlength ge{/md md dup length 20 add dict copy def}if end md begin -/letter{}N/note{}N/legal{}N/od{txpose 1 0 mtx defaultmatrix dtransform S -atan/pa X newpath clippath mark{transform{itransform moveto}}{transform{ -itransform lineto}}{6 -2 roll transform 6 -2 roll transform 6 -2 roll -transform{itransform 6 2 roll itransform 6 2 roll itransform 6 2 roll -curveto}}{{closepath}}pathforall newpath counttomark array astore/gc xdf -pop ct 39 0 put 10 fz 0 fs 2 F/|______Courier fnt invertflag{PaintBlack} -if}N/txpose{pxs pys scale ppr aload pop por{noflips{pop S neg S TR pop 1 --1 scale}if xflip yflip and{pop S neg S TR 180 rotate 1 -1 scale ppr 3 -get ppr 1 get neg sub neg ppr 2 get ppr 0 get neg sub neg TR}if xflip -yflip not and{pop S neg S TR pop 180 rotate ppr 3 get ppr 1 get neg sub -neg 0 TR}if yflip xflip not and{ppr 1 get neg ppr 0 get neg TR}if}{ -noflips{TR pop pop 270 rotate 1 -1 scale}if xflip yflip and{TR pop pop -90 rotate 1 -1 scale ppr 3 get ppr 1 get neg sub neg ppr 2 get ppr 0 get -neg sub neg TR}if xflip yflip not and{TR pop pop 90 rotate ppr 3 get ppr -1 get neg sub neg 0 TR}if yflip xflip not and{TR pop pop 270 rotate ppr -2 get ppr 0 get neg sub neg 0 S TR}if}ifelse scaleby96{ppr aload pop 4 --1 roll add 2 div 3 1 roll add 2 div 2 copy TR .96 dup scale neg S neg S -TR}if}N/cp{pop pop showpage pm restore}N end}if}if}N/normalscale{ -Resolution 72 div VResolution 72 div neg scale magscale{DVImag dup scale -}if 0 setgray}N/psfts{S 65781.76 div N}N/startTexFig{/psf$SavedState -save N userdict maxlength dict begin/magscale true def normalscale -currentpoint TR/psf$ury psfts/psf$urx psfts/psf$lly psfts/psf$llx psfts -/psf$y psfts/psf$x psfts currentpoint/psf$cy X/psf$cx X/psf$sx psf$x -psf$urx psf$llx sub div N/psf$sy psf$y psf$ury psf$lly sub div N psf$sx -psf$sy scale psf$cx psf$sx div psf$llx sub psf$cy psf$sy div psf$ury sub -TR/showpage{}N/erasepage{}N/setpagedevice{pop}N/copypage{}N/p 3 def -@MacSetUp}N/doclip{psf$llx psf$lly psf$urx psf$ury currentpoint 6 2 roll -newpath 4 copy 4 2 roll moveto 6 -1 roll S lineto S lineto S lineto -closepath clip newpath moveto}N/endTexFig{end psf$SavedState restore}N -/@beginspecial{SDict begin/SpecialSave save N gsave normalscale -currentpoint TR @SpecialDefaults count/ocount X/dcount countdictstack N} -N/@setspecial{CLIP 1 eq{newpath 0 0 moveto hs 0 rlineto 0 vs rlineto hs -neg 0 rlineto closepath clip}if ho vo TR hsc vsc scale ang rotate -rwiSeen{rwi urx llx sub div rhiSeen{rhi ury lly sub div}{dup}ifelse -scale llx neg lly neg TR}{rhiSeen{rhi ury lly sub div dup scale llx neg -lly neg TR}if}ifelse CLIP 2 eq{newpath llx lly moveto urx lly lineto urx -ury lineto llx ury lineto closepath clip}if/showpage{}N/erasepage{}N -/setpagedevice{pop}N/copypage{}N newpath}N/@endspecial{count ocount sub{ -pop}repeat countdictstack dcount sub{end}repeat grestore SpecialSave -restore end}N/@defspecial{SDict begin}N/@fedspecial{end}B/li{lineto}B -/rl{rlineto}B/rc{rcurveto}B/np{/SaveX currentpoint/SaveY X N 1 -setlinecap newpath}N/st{stroke SaveX SaveY moveto}N/fil{fill SaveX SaveY -moveto}N/ellipse{/endangle X/startangle X/yrad X/xrad X/savematrix -matrix currentmatrix N TR xrad yrad scale 0 0 1 startangle endangle arc -savematrix setmatrix}N end - -%%EndProcSet -%%BeginProcSet: color.pro 0 0 -%! -TeXDict begin/setcmykcolor where{pop}{/setcmykcolor{dup 10 eq{pop -setrgbcolor}{1 sub 4 1 roll 3{3 index add neg dup 0 lt{pop 0}if 3 1 roll -}repeat setrgbcolor pop}ifelse}B}ifelse/TeXcolorcmyk{setcmykcolor}def -/TeXcolorrgb{setrgbcolor}def/TeXcolorgrey{setgray}def/TeXcolorgray{ -setgray}def/TeXcolorhsb{sethsbcolor}def/currentcmykcolor where{pop}{ -/currentcmykcolor{currentrgbcolor 10}B}ifelse/DC{exch dup userdict exch -known{pop pop}{X}ifelse}B/GreenYellow{0.15 0 0.69 0 setcmykcolor}DC -/Yellow{0 0 1 0 setcmykcolor}DC/Goldenrod{0 0.10 0.84 0 setcmykcolor}DC -/Dandelion{0 0.29 0.84 0 setcmykcolor}DC/Apricot{0 0.32 0.52 0 -setcmykcolor}DC/Peach{0 0.50 0.70 0 setcmykcolor}DC/Melon{0 0.46 0.50 0 -setcmykcolor}DC/YellowOrange{0 0.42 1 0 setcmykcolor}DC/Orange{0 0.61 -0.87 0 setcmykcolor}DC/BurntOrange{0 0.51 1 0 setcmykcolor}DC -/Bittersweet{0 0.75 1 0.24 setcmykcolor}DC/RedOrange{0 0.77 0.87 0 -setcmykcolor}DC/Mahogany{0 0.85 0.87 0.35 setcmykcolor}DC/Maroon{0 0.87 -0.68 0.32 setcmykcolor}DC/BrickRed{0 0.89 0.94 0.28 setcmykcolor}DC/Red{ -0 1 1 0 setcmykcolor}DC/OrangeRed{0 1 0.50 0 setcmykcolor}DC/RubineRed{ -0 1 0.13 0 setcmykcolor}DC/WildStrawberry{0 0.96 0.39 0 setcmykcolor}DC -/Salmon{0 0.53 0.38 0 setcmykcolor}DC/CarnationPink{0 0.63 0 0 -setcmykcolor}DC/Magenta{0 1 0 0 setcmykcolor}DC/VioletRed{0 0.81 0 0 -setcmykcolor}DC/Rhodamine{0 0.82 0 0 setcmykcolor}DC/Mulberry{0.34 0.90 -0 0.02 setcmykcolor}DC/RedViolet{0.07 0.90 0 0.34 setcmykcolor}DC -/Fuchsia{0.47 0.91 0 0.08 setcmykcolor}DC/Lavender{0 0.48 0 0 -setcmykcolor}DC/Thistle{0.12 0.59 0 0 setcmykcolor}DC/Orchid{0.32 0.64 0 -0 setcmykcolor}DC/DarkOrchid{0.40 0.80 0.20 0 setcmykcolor}DC/Purple{ -0.45 0.86 0 0 setcmykcolor}DC/Plum{0.50 1 0 0 setcmykcolor}DC/Violet{ -0.79 0.88 0 0 setcmykcolor}DC/RoyalPurple{0.75 0.90 0 0 setcmykcolor}DC -/BlueViolet{0.86 0.91 0 0.04 setcmykcolor}DC/Periwinkle{0.57 0.55 0 0 -setcmykcolor}DC/CadetBlue{0.62 0.57 0.23 0 setcmykcolor}DC -/CornflowerBlue{0.65 0.13 0 0 setcmykcolor}DC/MidnightBlue{0.98 0.13 0 -0.43 setcmykcolor}DC/NavyBlue{0.94 0.54 0 0 setcmykcolor}DC/RoyalBlue{1 -0.50 0 0 setcmykcolor}DC/Blue{1 1 0 0 setcmykcolor}DC/Cerulean{0.94 0.11 -0 0 setcmykcolor}DC/Cyan{1 0 0 0 setcmykcolor}DC/ProcessBlue{0.96 0 0 0 -setcmykcolor}DC/SkyBlue{0.62 0 0.12 0 setcmykcolor}DC/Turquoise{0.85 0 -0.20 0 setcmykcolor}DC/TealBlue{0.86 0 0.34 0.02 setcmykcolor}DC -/Aquamarine{0.82 0 0.30 0 setcmykcolor}DC/BlueGreen{0.85 0 0.33 0 -setcmykcolor}DC/Emerald{1 0 0.50 0 setcmykcolor}DC/JungleGreen{0.99 0 -0.52 0 setcmykcolor}DC/SeaGreen{0.69 0 0.50 0 setcmykcolor}DC/Green{1 0 -1 0 setcmykcolor}DC/ForestGreen{0.91 0 0.88 0.12 setcmykcolor}DC -/PineGreen{0.92 0 0.59 0.25 setcmykcolor}DC/LimeGreen{0.50 0 1 0 -setcmykcolor}DC/YellowGreen{0.44 0 0.74 0 setcmykcolor}DC/SpringGreen{ -0.26 0 0.76 0 setcmykcolor}DC/OliveGreen{0.64 0 0.95 0.40 setcmykcolor} -DC/RawSienna{0 0.72 1 0.45 setcmykcolor}DC/Sepia{0 0.83 1 0.70 -setcmykcolor}DC/Brown{0 0.81 1 0.60 setcmykcolor}DC/Tan{0.14 0.42 0.56 0 -setcmykcolor}DC/Gray{0 0 0 0.50 setcmykcolor}DC/Black{0 0 0 1 -setcmykcolor}DC/White{0 0 0 0 setcmykcolor}DC end - -%%EndProcSet -%%BeginFont: CMSY10 -%!PS-AdobeFont-1.1: CMSY10 1.0 -%%CreationDate: 1991 Aug 15 07:20:57 -% Copyright (C) 1997 American Mathematical Society. All Rights Reserved. -11 dict begin -/FontInfo 7 dict dup begin -/version (1.0) readonly def -/Notice (Copyright (C) 1997 American Mathematical Society. All Rights Reserved) readonly def -/FullName (CMSY10) readonly def -/FamilyName (Computer Modern) readonly def -/Weight (Medium) readonly def -/ItalicAngle -14.035 def -/isFixedPitch false def -end readonly def -/FontName /CMSY10 def -/PaintType 0 def -/FontType 1 def -/FontMatrix [0.001 0 0 0.001 0 0] readonly def -/Encoding 256 array -0 1 255 {1 index exch /.notdef put} for -dup 15 /bullet put -readonly def -/FontBBox{-29 -960 1116 775}readonly def -currentdict end -currentfile eexec -D9D66F633B846A97B686A97E45A3D0AA052F09F9C8ADE9D907C058B87E9B6964 -7D53359E51216774A4EAA1E2B58EC3176BD1184A633B951372B4198D4E8C5EF4 -A213ACB58AA0A658908035BF2ED8531779838A960DFE2B27EA49C37156989C85 -E21B3ABF72E39A89232CD9F4237FC80C9E64E8425AA3BEF7DED60B122A52922A -221A37D9A807DD01161779DDE7D31FF2B87F97C73D63EECDDA4C49501773468A -27D1663E0B62F461F6E40A5D6676D1D12B51E641C1D4E8E2771864FC104F8CBF -5B78EC1D88228725F1C453A678F58A7E1B7BD7CA700717D288EB8DA1F57C4F09 -0ABF1D42C5DDD0C384C7E22F8F8047BE1D4C1CC8E33368FB1AC82B4E96146730 -DE3302B2E6B819CB6AE455B1AF3187FFE8071AA57EF8A6616B9CB7941D44EC7A -71A7BB3DF755178D7D2E4BB69859EFA4BBC30BD6BB1531133FD4D9438FF99F09 -4ECC068A324D75B5F696B8688EEB2F17E5ED34CCD6D047A4E3806D000C199D7C -515DB70A8D4F6146FE068DC1E5DE8BC5703711DA090312BA3FC00A08C453C609 -C627A8BECD6E1FA14A3B02476E90AAD8B4700C400380BC9AFFBF7847EB28661B -9DC3AA0F44C533F2E07DCC4DE19D367BF223E33DC321D0247A0E6EF6ABC8FA52 -15AE044094EF678A8726CD7C011F02BFF8AB6EAEEE391AD837120823BED0B5D8 -F8B15245377871A64F78378BB4330149D6941F7A86FBFFC49B93C94155F5FA7D -F22E7214511C0A92693F4CDBF38411651540572F2DD70D924AE0F18E1CD581F3 -C871399127FF5D07A868885B5FF7CDEB50B8323B2533DEF8DC973B1AE84FA0A2 - -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -cleartomark -%%EndFont -%%BeginFont: CMR10 -%!PS-AdobeFont-1.1: CMR10 1.00B -%%CreationDate: 1992 Feb 19 19:54:52 -% Copyright (C) 1997 American Mathematical Society. All Rights Reserved. -11 dict begin -/FontInfo 7 dict dup begin -/version (1.00B) readonly def -/Notice (Copyright (C) 1997 American Mathematical Society. All Rights Reserved) readonly def -/FullName (CMR10) readonly def -/FamilyName (Computer Modern) readonly def -/Weight (Medium) readonly def -/ItalicAngle 0 def -/isFixedPitch false def -end readonly def -/FontName /CMR10 def -/PaintType 0 def -/FontType 1 def -/FontMatrix [0.001 0 0 0.001 0 0] readonly def -/Encoding 256 array -0 1 255 {1 index exch /.notdef put} for -dup 11 /ff put -dup 12 /fi put -dup 13 /fl put -dup 34 /quotedblright put -dup 40 /parenleft put -dup 41 /parenright put -dup 44 /comma put -dup 45 /hyphen put -dup 46 /period put -dup 49 /one put -dup 58 /colon put -dup 65 /A put -dup 68 /D put -dup 69 /E put -dup 70 /F put -dup 73 /I put -dup 77 /M put -dup 84 /T put -dup 87 /W put -dup 92 /quotedblleft put -dup 97 /a put -dup 98 /b put -dup 99 /c put -dup 100 /d put -dup 101 /e put -dup 102 /f put -dup 103 /g put -dup 104 /h put -dup 105 /i put -dup 106 /j put -dup 107 /k put -dup 108 /l put -dup 109 /m put -dup 110 /n put -dup 111 /o put -dup 112 /p put -dup 113 /q put -dup 114 /r put -dup 115 /s put -dup 116 /t put -dup 117 /u put -dup 118 /v put -dup 119 /w put -dup 120 /x put -dup 121 /y put -dup 122 /z put -readonly def -/FontBBox{-251 -250 1009 969}readonly def -currentdict end -currentfile eexec -D9D66F633B846A97B686A97E45A3D0AA052A014267B7904EB3C0D3BD0B83D891 -016CA6CA4B712ADEB258FAAB9A130EE605E61F77FC1B738ABC7C51CD46EF8171 -9098D5FEE67660E69A7AB91B58F29A4D79E57022F783EB0FBBB6D4F4EC35014F -D2DECBA99459A4C59DF0C6EBA150284454E707DC2100C15B76B4C19B84363758 -469A6C558785B226332152109871A9883487DD7710949204DDCF837E6A8708B8 -2BDBF16FBC7512FAA308A093FE5CF7158F1163BC1F3352E22A1452E73FECA8A4 -87100FB1FFC4C8AF409B2067537220E605DA0852CA49839E1386AF9D7A1A455F -D1F017CE45884D76EF2CB9BC5821FD25365DDEA6E45F332B5F68A44AD8A530F0 -92A36FAC8D27F9087AFEEA2096F839A2BC4B937F24E080EF7C0F9374A18D565C -295A05210DB96A23175AC59A9BD0147A310EF49C551A417E0A22703F94FF7B75 -409A5D417DA6730A69E310FA6A4229FC7E4F620B0FC4C63C50E99E179EB51E4C -4BC45217722F1E8E40F1E1428E792EAFE05C5A50D38C52114DFCD24D54027CBF -2512DD116F0463DE4052A7AD53B641A27E81E481947884CE35661B49153FA19E -0A2A860C7B61558671303DE6AE06A80E4E450E17067676E6BBB42A9A24ACBC3E -B0CA7B7A3BFEA84FED39CCFB6D545BB2BCC49E5E16976407AB9D94556CD4F008 -24EF579B6800B6DC3AAF840B3FC6822872368E3B4274DD06CA36AF8F6346C11B -43C772CC242F3B212C4BD7018D71A1A74C9A94ED0093A5FB6557F4E0751047AF -D72098ECA301B8AE68110F983796E581F106144951DF5B750432A230FDA3B575 -5A38B5E7972AABC12306A01A99FCF8189D71B8DBF49550BAEA9CF1B97CBFC7CC -96498ECC938B1A1710B670657DE923A659DB8757147B140A48067328E7E3F9C3 -7D1888B284904301450CE0BC15EEEA00E48CCD6388F3FC3BEFD8D9C400015B65 -0F2F536D035626B1FF0A69D732C7A1836D635C30C06BED4327737029E5BA5830 -B9E88A4024C3326AD2F34F47B54739B48825AD6699F7D117EA4C4AEC4440BF6D -AA0099DEFD326235965C63647921828BF269ECC87A2B1C8CAD6C78B6E561B007 -97BE2BC7CA32B4534075F6491BE959D1F635463E71679E527F4F456F774B2AF8 -FEF3D8C63B2F8B99FE0F73BA44B3CF15A613471EA3C7A1CD783D3EB41F4ACEE5 -20759B6A4C4466E2D80EF7C7866BAD06E5DF0434D2C607FC82C9EBD4D8902EE4 -0A7617C3AEACCB7CCE00319D0677AA6DB7E0250B51908F90A32C4175B6BFB279 -024EAE1B04D721A6C54FD62484F8949B2CE9B87D9CEE04DFF82BF14931B3CA03 -AA5F701B6F80BBCDF2C427C40A51597F0B1BFA25EDD7CE0EAF2EC676BF0059B7 -15DD5462BA30DE78A08DD533DC0E8D85F9DAFC5FD842F417265427E0F1B71834 -D2BF6EFAC3CCC40D3EF3B2E2080F148441BA45E5D0C0F7D8416730AF4BE4FC93 -1E965594E0364F0D4976695D2851ADFE75F0E8AAEAF174FD8B2D51B057733811 -FE1F00D6221A3F0677E7155A03A55E5B877E468A5EC54C6E8CCEA16FC07D58F6 -AD35B345BC12FA254CE192150A06A437F194A50EEB0A766C689C5A1D56F322DF -0BBEAA28E83B5C94175DFB9E11A2C9112FCDC615217D9DC7A1D06EBBC9143453 -6B00B7283BE7F21BAC8C2985E23E6FBFCB7BE1255583782E1588E6AD3BF8B879 -A425CED34F30D932AFDC2EC726D5658146E8E615D349ED779B787232605BEB38 -346E36244A1ED054FAEB7C41A0858354B42706AECDD9AEA0F720675765573824 -EE24E9191AA563B6D8D882C0942F2CC910A787A5AA51B79CAFDCD501C1A5CC0B -61F123B55C946FDD15ADAE146828A24D8F7133E15CED816080FB44B80FE3A910 -6521588B911333405206CE4B824F02383FAC1C41C2FADAC01BA2337CD5A4F65C -CB99C370C79C65244D55D939FAC02E8FF28A0DE31ABFB5DDD867C6E6339110D3 -594B3C8C33D86B0041D42004D797DC1B80539F6719D0743535CDB156BC729EAB -CCB02DBF2DA723C43FE8CC97153277BCDD3547CC94C96C0A8DCC8B6821111329 -6C0BF5FA56824CE23100BC08DC62144E728CA38B22DA0C79708F1CE731852FD2 -B5C6D054D2D9E9466D2D195C1560E30A519BEA6E0615F5B418871F3ABFF3DFBC -0A154872DBC8CE60511138150FDCA3784CB5375C89264E7E7536E7F6C6212281 -8DFE83656D3ECAA83D3E3482DC22737682542860B4CB557AF8A0CCBE9B2BFEC4 -11AADFCC86594BC01F54592675FFA382757CA246B7691E3DF9838F986CC7B4A8 -BF11971D924EC2D0DC87F15A37A75DC7802A7EB330CAC98FA7DB406E3A2DD6B4 -4958F306A92A7FF5B5885D3BA5976E4D90C218A818B03D84FFADF6BFB1F3D48A -D3B3F77A791F414EB736852CFAE54B95E837CD76176902336821AF4A33F3DC44 -787F031D82B6F8EF0234D9DEA6037CAD0C34338D21594D3A339B1435E29E1EE0 -123B0307BC6CC4DADCBEA63B51C167D99239A7B66B1D9FCD24958198AE0AE0E0 -53DB703102D2A1FDB6EDCC3DB5024A0158BBAF988E09EF3C6BFBA45BD8844D9C -65E9305971FF855115ECCD75F2A0DD0231F3CD92A691E62D310A7DCC2AD0E6B0 -436D3E2E004A0F95A1F44B9407398365B690BED5E77E63AF77E1F90953898294 -E671A7D862E55E1034EE1BA40452BBE10F11B1844C898AA2DABAF1EA276C2482 -E1386A77B8873B06E2563B20D635D68E064C6F6BFF54BE4BFD4C92A8852BF41A -C5A5768451477DC18B9C588E24D35BC19A7E4DAF9E775FFFA10EEBF1EE1BDDC3 -BC33423EDEB942E6BB9FCBB2E375714C2181F9A81795A1C73D4141B48ADF2359 -CD98CC009AD6737A9489331DCD51B88FC49065FCD2AD08480FFD40B3F9AC94CE -552F5B25397EDE221658C7966377400A2D9F76293D20C80E0775D3333192D26C -99AA63034EAFAA890E2C6EA8A075E4E5B05A53555381ED2E28C8547C1AD2F658 -57AD41C605258075004DC0853D3025B2C40F9EB17050C469EB6C4C8741040E71 -94DC83C9EC04E5EC7F7B8F5607105D09363E56B28B83097648D634EA74C65529 -CA4F406BDD9F5260C0B5A338D094007FB58BAE1DFE05A73F27E4C7E94757ECB4 -C9DA125C6DDA375DD7E9EDD6725B3E7AFF66019FBCA01D20501BC4FEF231FD2F -D9F254890F67ADA31BE5A4C8318BDAACCD2A8309B39D07F27D5C646C3CE2CE8F -1455E234C962938C0CD29FC591E6D9F28D639F2B7BAB5D1C4574117A4F0B9FFF -BADC4A8F409DC9FE66C14ADA6DA2896C188D6519A8751F1D6C4564905D1C1FD4 -F1DB9262D6035C3E5080FE18765B15883342DD26A9215943E21EEA39AB6D19C9 -17010FA8DBD399643DF13B9236D8A6853ABAD5727347E12C7DCC5101DC4FBDB0 -E1140722144EE18E0DB1CE3795F6C24EE4F97895C9A85B2A02D56AF94577867A -F9EE88A6B3D80C84B322E81D07FC73CDEADF9775283BD6F8870A507A3020744E -FE93E441E439BDC9B8E090F73255B65F6DB25A460D21ADF346D9C900236C40AC -2AC67CC22C7EE99EF5D409F95F3AE7D5F45CCC3D799668F541ACEBC605E41403 -DE3AD9DCED876880C47DF38433B8C364110B61996DDA52E8150839AE62194BBE -C2B833D7DD97183747CC8295B5B489DD76145EE8626D00DACBCF8190549B46F7 -BD230EB15E9EAB023716E688E73C480785B51FF0D862AECA57838062C9A26D44 -0177C3CC2710E217FD0EF457583CEB39AE9981EFF253E8BCAA38528EEE46DFCF -4DE56D712EB91B3E38A6D39520D83815A19061E95284E6B0FCF14909213DF4D6 -E498768BA53CBA01E541BC6346DF4818E8A88B8D9AC8790690CF52F34B9F1820 -6C29194D824B40E19A592F22E399D4A1B2AEB93AD89EFD733F7501AA360F95C9 -D362D3416D038F306FB403208CDB01AB8CD65055806E66EF14F58483DDFCC4E6 -8254BCB55C54182C7270203D7EF408685F414D6BDFAF4FC4B2AD2FD93BA25937 -F097D574EEFA68CAB549FEC7705B7919F1FCA21A26C0F0A7671BFE9B414C31FC -D3520068CD00A8485D8F0FC83B9D211F3559315C3FE40D28333522C43F51A05D -453705199066EE5A92E3079AF751A35B47D5A1E3A48227C63542A41548F43BF8 -86DE049D6E6ED48E1A2D66B44A036106093156445B4F7DC1B87D552447A5AD0C -DC88B874B69C95A512E21C718EB0738B559931BCD17C491FE4739597A25E038F -8E3A59EE9CCA65DDCD05F520056D791FBE96D3D415684138CE3CF2DA6F17BC68 -61408C4BEED38FDAD45BA3F412011394359EB18D58B5A1C6E11B26F826FCEE5E -3233F624F2AC9282CD3C4AF314A5E730C937A250643DA6BF1A8EF85C23932C27 -79ACB13AE160C638CA2BA28044C31B83CADC9804B33ADC549440A4E73070269F -D9AD75E3440860EC5B6D60DD8586E4B89AE754BF109A7EE2DCC680FFCFA7151F -BE4CEBDDE871DD17782BE20E8413A2E0EB0332E07F116B339D0FEB1F8738A43E -D9BBCED2E7568D988462884DEC38CA4CAE6DB76A3D0A54B99F80863646A0895E -9799FCBD96CD6DC23680967E3963CD05B52ACED020C8B48F735F22BC4624F950 -C41F7E8B70ED85E0108E13FDBFE503CE4D834892C2A2E11E5A20C97581BA9F74 -75B661F45935A745E020D214041AAEED0F56BB619FA6C3E16F85E1B827A64CDD -46021449445ED4A8AEA28E96A713003C030A7DE3636B56245A40FD250CF23FF1 -50A5A3731ACB9535E41992259DA4C7B7423A607098663E0925C2D4ECC316579F -5AD685AF7205652C995E290B8421B298096696B05BD180FFAAAE037BAEA46EA4 -26E4834AAAAA3BA1A381F9A34ECABF8208081A12C776F3273C22D38A742C87E8 -B1C3FB18C8BCE2EC517D1E62054CC9EA7761DA5A062AA6827A15EF441DDA047C -73C981A4F0F2C99DD78978D352DFE6B5AAE1395C420E78CF575540C77E6ADD2A -1F75B70CCA16FF3DFF35AB17CD720AA0CE3287BAD61826B8C0DD3B9A92FCAB80 -D50650AE8B349B0854EC57BB80FB3BC7E96ECB4DFBE191B5927E97DF74AAC330 -C0B56BF365F492AA78BCBEC9B48EFD9B82A4EBF6C4CCC9E7C16CF2295EF97619 -63306583DBCB24EF5C98AFE83A83FA238EE49FD21926F65B234937A4FAEBEBCC -E4083FB13C6B1D137435873886A3C955B644B6592019DF124360F50781C86AF2 -E082FB3A87DA2E17DE1CE357367AFB4FC1EFEFD7BB7CAC73DDC598CDB1BF579B -AB3EACCAA7E99BB39E0FA50D0F2E379FD89AD94F83FFA5994AA1A08C0E79BF8D -82B43042423574F1D0C76ABFCABDF2D9AC08426F6C48B860B9FC667D48A3FC60 -23656780E1CCD0608F63C4FBCCDBEE4E37C1DCDE92FF07BD806C61DB06C3644C -B55C855D5E5C63CD62790ED661C23E4372E7E2D2A419877CA09BDFE58AF77B90 -8F66830A84EB2FBF9DDAF55D7ABBB6C232674AFD21ADB250D7011C22869B01C7 -890500B92DDD45051E4C1C45FF8F04BF0FEE4D03D2EB5BD8D53D824BB4A9FAF1 -821BDEEC7065029F2C9F0FE8946421B7C5BDB86CD347A4468C1965307AA37E40 -4BF0D792DBAFCAB165D585C1DE86B82029727C8F5D9A50A84E5E6E58CADB5F42 -49F4B98922DB2D2534F725BDECF4405F7787408DCF754B16BAD69CC8651C769B -44A48E4A7840B09222BAB05735752DB4AC284E11AC0D5BDCEAEBD30C4ACC5336 -A8AA0137D56C82DCD94B8437852196C2BD99EE4004CDB3C9F5C26F88161F3BA3 -45342F599F37358A3409E72847803C52ADCB828BBCA9ADD2BD8A471854F79B88 -A786AD4B57A910B5AEED5D4C6AC40658D1FCF0BA96D550F56024D2A00FCE7973 -18FFED31C70B49F3A1E02079ACDFDA25F9511905AE62D0D0369E75AB172B5568 -D9CA59EB190685C1F728D868D217565168A0D28BFB75D37AB6BE2E5E16E2F66E -D091ABC6A5A179C4039DC8D7705401F27CFAAD00DCB9C57ED53FA1E67153AD49 -C6AF97EDE8595B9167B516DF9B4488A8AAD163279881B8777EB674F3D0428BD2 -D7C3146C56DC356DCCAA06B85B98A9B4932429A0CA3F00C969951A6B71B576B1 -811903B3BBEF85BF3A80832916B4D9D3D5D71475D6693AFE842E1BEB4FF0E9CD -69B547BFC3FBF561E7BCC7630386F6AE385C2585954BC268C4BAF1B2CB57F0DF -AC17E73417A862E0D93DDD010E50680D6AC0F88D5754090ADD64EF78B74F2FDD -484B5A9D8E156EDD5D0237D73ABC5D7F2159EEDC8F4205D84A2D17E0C8A705AB -9D3711A6A6FC34F1C62B3AE8D9E1DBF3E58BB956576E9AF521E61E7511D6CF4B -D3586F3F1C45F23D4F2E06F0616B5D80A2298894570B5F213B3BCE5CF41D46C1 -3E0E8825EF80EA3C7C5FCB69B81AD0480CA18210C28E3624C4F5AEB8C57A9418 -5B3893C3F310249E04ED883BC7AEB57385D8479BD5FE0304F9286EDE5BC0D5ED -2DD53B69C20F98ECF94527F290EC82244AB2CFD90290DF8BF0E47C18F905EA21 -427B4783CB5A0CE84460513687DAEE378E949C373DDB78F88CE6E717F82BC1D1 -0363F48CB62298509CD7CF860EC7465B6D59C09CB5168F81D405305AC3E02D57 -DEA6D0A11110F621427386E3A9728C9864815901DFCB9638EF701AAA0640BC96 -B0D60D5F01F5D18558B0A791467C3E162A5129AD85962B180AA12B2CA1ADC613 -DA025947FF755D3E5698F25D589402B407401A2F8BD70546715F4DB36AD76D8C -7D14EE7AC0A7DFAE0A57C4D3D6114CEE9F89CD94C5BDFCEE7233D46B171B4524 -992DA85E904233A2F1B04C5055237584818D87D661386A5715B9C8F2775A6A80 -89432C2D4CD47FF12B85D3AF6321DE65AEDFE28988A199DF9EA9BAAFE65AFD00 -E5A4D122618103EF11EB7FB6167AB0D514F260A326309350C34C2F23C7F88706 -220706DCA04095AC754F6922D4705DAE3338B7D2E1A34CC8AF0059199CAE6C6B -7B34D20D465B4A7B777CDBE614D7C9E22AB6AE523B317ACD2EE55D8E88B3AE7B -55825E1EB54BF3D6FC356E66EED83AD02A3CF79318080AEFFF31132E83AFFED6 -6AEE52896A3A148DE79EB8A63A8FF18B1EFD11AFBF3F13D77E5E0FD453CAE551 -B06AD12FFADBD8E90FA6A979B33FD2B6933E2B367B88957C29A663E6793A1322 -23F64DEFD28669F0E7AD14F466B4CFC13324113FE3B6C41267ADAC6BF98CE815 -CFE4A8BE6A13D12DB4DEC5BD3C085FB0762A4223B31B41B5DA851F2D0CBF2473 -8A077BCE71B204EC0C69ED5A94FAB1B40BB9C19F340DF1B5C2A9C3D31C644C64 -175C06AFA621986B60AACFC5533C35A991ADB6A173ABC7A5840B2F195589B8A6 -EB178D3C393336BE10E5D8D534A4BC50139B039BF0B35F29F7321DBBE82B6386 -C68C57A5D3E1C8E12CAA2A6F3FE12B1805FDA29C989B3A4CDB0029315D16E3B2 -BCCC7BF4390EC93241643D4E6966BB7979742F57F3AE3E3A8C08FEF8FED2D744 -8337DE8FD50A1092456CD2D6E917B5EEABA5827E4D8466EBDE31FD78F2D62CFF -8859EBCEA9FA275F3FABA3FB586867C64685D454F4FD4C627C689B974D0BA5AD -2E1695269014C7D810465099C034FC09CF288DADB55C98A02E06AECE56FF954B -C1F6DAA6723652DDF39A330D8F3E69065004143DC04D7B675EEB15956151515C -EEB1C20AA0AE3B1E901CBAC18EB2967D6645A711A5A528CAF0E90976F6AA930A -FE8EDF12C64C2BC48F0471B8381F8821ACA5DEEEF38BCC0D85BA4BE94303550A -CB023F1E27E4FB33CC23E5F261129600153035F939FDEADBE9229BFF33DA898D -B349707631E1FEE49B2B2AEC67613EB33B0B3A4B60FB71DDE6053CDAD9B59FD7 -DC7514B66248C931170F7C7223DF9CE26612A4240260388B14D75733A6E0AFCB -383894CF0C760880F04C97EB05DAE42C1F42B409002F6BE73837D9EBD053080C -60965007E10C3AFC2AA01A7BAFD961CA65A80706EE8BA54C15A218C3A2BB9D94 -B4E2D93A5EBB0C011C32C56587F67671B9B8BC1198EEEB6D4D67C8A4710D5529 -14150658BC4D6D28357477D55854C712012A42D2B488AD9CB2D970B15DA6AF92 -A79D394204F70F3A30BC1467EF2F858FA64BB466B57486713F3EDD4374D8CB3A -D590D3CE61AD9CA589EDC7B9D27795A571A16767B1F165AEEB1232A223BA3FF8 -BA32AFCAEB89CF4FEA3CC0F3F9AF8A7B56A5985B3BA03DD118E43DCE4BA0C8C3 -8FE6FB7099FD11F95FEF6AD0DC2436690692A16801DFB9EE8A1B79728CA5ADBE -35788A2149987432D829B2B735D3344D937F66AEF876A8CC1FB1E0A1BD71E3C8 -35B057BB347C077740FC712E653C8F9AF59E33B3165A5F4446478E49A291838C -27001EE3A99DEAE0F01D4A1666F480C1BF4EB4C16349D96B127FC3D414B0FCD0 -311B15D5096576273A945F6E0C7C34303510184022905CF82B62B0AB091A8A29 -A93974D5A9AC972A788527F2ECA3496A0A9BD7057B8CB30C31D31B6E6C99B53D -BB15415008C85B5F932031F3663444470D6D7C41B4FBD711D3DF2D103EDBDC80 -90834726375889D9B0C674F19692D77CB75E83B70CF429F489F6584CD7C42BF3 -278C6C3893ED6D96D6F5E1D9372074CB33AC97FBA6ABA3C99132E16123AAEBD5 -EB70AE0F19DEC2911BD917746FC05ED9F3E1D5A06FB578FB3D3A839EC4D2214E -127A2E3D09DD5B259F088F2A1145BBD6E05D4A8D5C3926ED2B60BF6D3C2CFFE4 -2C71A683CA0CAD7D0417ED54906022A09F310644A19D035496E1E07CFA2A0602 -8A024BDDA8CAF96F81E7FAF00A8BDCA261E5E513C7674C178A01328EBB2C3481 -7E3864BC358082FD2233330A998CC2D806D911E54E83EFA134ECE5D4C88E43FD -91E7566810DDFD9E309C745BE786C2F535F5CB58E5124ED1FD3E720CC4B98203 -59D177F274A5657411ECDA3AC1CCD9B7B6C66ED68F2CCD8A0E388ABF0767B448 -49235A6940FC3B6AB508E9F194F46DA7E316F57F9A13B221F6CD9B098FEA371F -741AE3395DA6E980B95B57E64E481FD8E053BA4AD35A4F76425E7B7CCA82F32F -64AB13864503205D2AE4EC65E8A67C18B676F8A4C82FF302CAD1A78770CD4811 -3837B0F6EB261DF5A4EFFDF0D6E46F862D5FF185A749BA7753AF0D0C879D6B62 -4F46ED2ECE6831DE371A86DB754E03249FF8A86D1C70E367ECD3CB0C7A931802 -45281C78773E6EFC34F9BD474BAC91D3B7BA3F1519238CB2737EB929AF8ECCD3 -027654CE3E6512BACB4138E248A46EC2909FA5C930FA78C1923D4F0358E9C272 -CFE150D3D147392AC1B6F10F85E599AEE0EED57A6625E86112E311737AA5CE8A -5D663DAE65B491783A82CFA230B0EC04EB7FC06BAE8F6107CA6B796B100A680F -0545415F98ED43A586D512EFDF30A705EBA7DC1F729B7D837C368B95A51E1724 -48CE999413DE3FD6B66E8CFE827591AB6CEAED07663343D7B93EAB3A8818ECB5 -3846F8D3D2083A91E1336ED9DD3BF45D8C25F478BB9381CAE1CB77FC8BC7696E -A0CB8880D481461640CB24A25BA956741A9770CA5849C27076DD916DFD3232A4 -054017E5AF7FA06389FA17CA569DE8E7A3870E0F8093526EE63A0604E09FF8F5 -0A40614BC449EF4745E57A93B0E2F67637441F4892D8CAA0B8BFD90A9B8D1AA2 -35ADFE7C76DB741378F0861383631E0638D745BE976C7500BDC4952F2456AC60 -911943F20A87D38505F465BBD813E94D7923D5226F568BC142BCA731D5BE670C -6E66D51FCC5AC9C6BC881C9CFDC76FC7D69506AED67B1C62E24E67DDF44B2E99 -47F02E64114D9AF5D264BCC6374C5E19398014FF738EA921199FE044F7E9EFFF -512D6DDD608CD2D5C1ECDD37A489FE0CC04FCF57931DF22783E8348BC922803D -042FA932B7D46997266ECEA317AF377F390DFDF544A9585373FDE6B06BBF653A -1FF485EC9482CD5E06E3E53AC30593A146D93D615B909D7CF4178B0BD41BC2E1 -20087CDD69910F627B755F09323CCF94D1128CDA15024E65CDE897C2AEE6DFA7 -25C3AF6A530B071860CE5244487B5DDE903A9C375FB17AD84B6DB119E264CB95 -A8688C59E38DCE6E8F82545D91429A4166A1EB60D11BBAB075A3F1C8E2CCF176 -BA114066562575A8276D85F81B8D4F1208F1380D9C4D22C7B459AD3928C01408 -2F8469CABDBCB1C0654C5C5406047201AA63AEF4D544FD83278C3F52009C2784 -B1B06B48D337617CA50B5DC9419A9B4C97A7A2F03C85380F937ABF52F5F8E401 -B0883B804028739A645DD7501894E93AA5677D34F6FDAC340700ED3F23672206 -1DE7563800297C720D33AE3D4D39CEE21227F63A42900EF7CA3A6AEB5616A711 -256AB3881E4004247922C109439FEDAAD82EE17B0BC7A8ED8021EB6B3AC3C9C8 -EE0475A519A89D0B5759F1642041B9756621B4701FF8B2F28BA6B64ACD6AF0E7 -91E13B4E9AB00BDDD4CEE9D40B9A8C023E26F64E37EF96C3D5394558EC95C054 -715E496F31677F784E905242FCF92FB25DFFE6407E704A24E0E50789CC097E5C -AB051B38268FD0F63050DA7DFAB6AC8A76DDD2B1600E034418A69880845919FC -A4B4F325A1A682ED6C14651C673F587CEC96DB66EF960C81DE0B972E9A9AEF9C -6529E82FE6ECF64644DFE46348C0B164CC748D1BD8469C7DCA131ED307C78B76 -B4C56351694156A59CAF44B349248375A0A86CAB51621152E9EDA7D952DDE89F -285680C8E038B8311C9236391FC5FE9A3A2AABD19078C18199C0D2A4C09729B2 -824309AD81BFE60A7462A7C86EED698E0F2B94C45AF0E8FD0464840066DC4C1B -5AF460B8915C23EDB6A7C955E72AC3D947DA80F69AE7D9D9E9B09B66EE15951C -B2EAE4C411F6142B89B76FE6C4BCB15D95EAB37231011645070D265F6F5AE9B7 -3E73ECCC1E7EA9BDA3C0895D72028213A8A059187043BE3C13E0B681C8F90F37 -D875ABAB13D0748D6FB807691724B9D79A660AADEBB229446CD2CE492254D971 -31D7D92FBB0F16A48006D10DB266499B2134B3D71B34F2BFC6E50EFA23C3CFB7 -287E22F17631D88214A804B93584E8CE4D8E9CD0B20241C74980D8EFDA1EFA78 -DDA967789704A2E26BED5141B68513D21F3F45716F8D327543CFDF31873ADE12 -A231A65D1C13A8BF2315F81496B6DC1B119C0454F020E044C49022B7D213C365 -27B09876AE13E9EA7B564A04223BCA9E4AE1C4CDAF6BE7541FDC9871FF17BB85 -E7FB2C9059DB15D85BEBB2556243BF25E155CD54F147D56D268D23FDE6AA4F45 -9FF6D2FF954A0BAFC1C27FD69B211A537DB14D0A45D446ED8878600D0AD77730 -B20B972CE6EF28A0EA4B8C69E5269E904CECD6C467687D0AEBD60DD6540F27B6 -B400422AD81C8778E83BF378ABE82C50C3758CDB459A4330849EC53D95561AF2 -7E48E50EA667A72C037126F8C24AF2C1913C4185DE9AEDFBAD7522E9FD57E5FD -5FF315AA16DE2AC08CA627ED64159EB09EC4CA0C144AE313F31F511350735779 -98FF7083A199291A45CA16BC9473ADBF1A1AC49441C3AB9A817589691FCA708A -CCED2A6143559FBBC0463CE1C26FBB683EE1E6DC0AC1D13695F138DF37AF80DE -DE5F80650AF4ECD32AC0475D727AF61AA192239718541111AB49D23BD4703A7D -4F3972ADE786C2AA2EABC30A0084AD34C08B7ACB5BBDCB1596F4DC07403F87A4 -627F51CE3B9DD3DDE459637A28564A2B39855656602ADC7918F3C534A7C26A99 -F201E96274F395C6E2ACDFA2E0E9C21D25372E30A6BAE6A755641AA6274D8D2A -03B1F097BB2FD082043E9FFEB2377E166F28FC1B1B4C950953D35D6BAFAF589F -02CDF1428B7D0CA23858257974AE2AB2695E24BF6F4CD9FB8AB0985743E8BB72 -E1A6D9CF59FCE81B84C8CE17AB377AFE5D5CBBC7A61934662B4A8376FB007BDA -FD313C7BD389751689C34BE1E1C069E0988FD0E9C92197FB0CB96C2B8091B371 -CB73CD874D4A74B658752E46FDF812CF397DB9284CB4908BB3F29F5779FF9594 -13A26072524068576524BE64461E129F3A1539029D4A9A1A35EFE12C733460AE -D735619A86DFFBEFA0073B9C111F62C91869527A6FE230B5CAD9C776BF5AEB7C -4473EA60E6ED9DECC9E7AEE42C6FA0954994F9DB73BA868538E4036F5295A35B -24A619EC98C367059CBCF10A7C49536D930C3D4231C681542F2108CCEB5673A4 -9B910E482E6C4556D8497C900B025412699A78BEFE070AEBAE5E0376FACD9D6D -52168F660AC8DFC63F3DE4BE870D610D2D670650D8AF77CB9985F9F23C6F1C8C -C87D7F2E1C917907FCB2029EF3F4A8DC664D0CB1058EA6C1FA7E67AADA1298B8 -D87DC1FC8C35EBD068D15EE554789CC6C2F08E6F5B857BEF04E3C69617C5E0EB -CA92D5C097EC1B24BB7109A2F3DF18C96118B3F5B13D9AD30145883B58FF5AB1 -61A0764746C03FE25B5B27A44A00E058975A10EB1F4D1E3D6DF34FE9E18CBD75 -F99B3265A925305A57F60B0630092ADF75DFD3444D3F10BFC14EA2592929A5BA -EFD9F05012F7CBA93543BBF6BC3C7CD28622474806490CE19DF971E992D51097 -B5FEA9CF8EE7D4E6B5FA358207B153AE10A7D67CF61FD7EEBFF1AAF6818899D5 -288418661DEE68C2E2910D299BB1C64C355627A5898D5F6A75278ABD0B1675FC -D74156F6D73FADD845980F8D6CC5293CC8C866D9786EA4855A87D0FD9E747B76 -CA95BD849EB57B530EBDFF2C6C862F93FC3A5FAF37BD0F8B3EA4427428BCA646 -B8211FB1027701F9A1B597F4C849770C81C2CF81973B5361BB9D4FC8C1E8DFCF -6A5B8F9346CFAC43CA935E3DE75DE85583C4F1CCEA1A3CA5EA59031C8C47C7DE -4D3C73786AB28786A8AA37A3B8836D43C78BE757945DD8FF8092A9805F8C921F -677D833DFDEE1752DA1CC0D44D8CBAE1A4AD211C363350B64690E5E1B392331E -E20572D50B52AAE6BE377E15B86AE39216BD2A1F1F4B1627B36187F6408D1749 -AFEF220F3A33A8C497EC466AAAB4AA60057E8BA8F21A9085D02F64F5C4FA1CB4 -4665F9A4354B3B601B4AFC2F84FF80FEC2F2AE659B7032EF5F2702B3567A9426 -397AA2F1FE301591C1AFAFC9B28BD2293C5681D29ECBC805B9C7416EF1CA6428 -902E0A1936C6313C220B9984D8B2332DFC7C6603DCFA7438DFD3AFAD701B0256 -5E3F14B06329C781419FC3EB738CC5692BC208A77FE0436568337FF413E94656 -0FC61E3941837BEAE1CC3F01D1ED683C9295CF0D22BB98B614565DDB9F314441 -D2FE97388AFE01FE0A594894FBDB3BFDDDF1D3455E48723A4A66E364 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -cleartomark -%%EndFont -%%BeginFont: CMBX12 -%!PS-AdobeFont-1.1: CMBX12 1.0 -%%CreationDate: 1991 Aug 20 16:34:54 -% Copyright (C) 1997 American Mathematical Society. All Rights Reserved. -11 dict begin -/FontInfo 7 dict dup begin -/version (1.0) readonly def -/Notice (Copyright (C) 1997 American Mathematical Society. All Rights Reserved) readonly def -/FullName (CMBX12) readonly def -/FamilyName (Computer Modern) readonly def -/Weight (Bold) readonly def -/ItalicAngle 0 def -/isFixedPitch false def -end readonly def -/FontName /CMBX12 def -/PaintType 0 def -/FontType 1 def -/FontMatrix [0.001 0 0 0.001 0 0] readonly def -/Encoding 256 array -0 1 255 {1 index exch /.notdef put} for -dup 19 /acute put -dup 70 /F put -dup 74 /J put -dup 97 /a put -dup 99 /c put -dup 101 /e put -dup 105 /i put -dup 106 /j put -dup 110 /n put -dup 111 /o put -dup 114 /r put -dup 116 /t put -dup 117 /u put -readonly def -/FontBBox{-53 -251 1139 750}readonly def -currentdict end -currentfile eexec -D9D66F633B846A97B686A97E45A3D0AA052A014267B7904EB3C0D3BD0B83D891 -016CA6CA4B712ADEB258FAAB9A130EE605E61F77FC1B738ABC7C51CD46EF8171 -9098D5FEE67660E69A7AB91B58F29A4D79E57022F783EB0FBBB6D4F4EC35014F -D2DECBA99459A4C59DF0C6EBA150284454E707DC2100C15B76B4C19B84363758 -469A6C558785B226332152109871A9883487DD7710949204DDCF837E6A8708B8 -2BDBF16FBC7512FAA308A093FE5F0364CD5660F74BEE96790DE35AFA90CCF712 -B1805DA88AE375A04D99598EADFC625BDC1F9C315B6CF28C9BD427F32C745C99 -AEBE70DAAED49EA45AF94F081934AA47894A370D698ABABDA4215500B190AF26 -7FCFB7DDA2BC68605A4EF61ECCA3D61C684B47FFB5887A3BEDE0B4D30E8EBABF -20980C23312618EB0EAF289B2924FF4A334B85D98FD68545FDADB47F991E7390 -B10EE86A46A5AF8866C010225024D5E5862D49DEB5D8ECCB95D94283C50A363D -68A49071445610F03CE3600945118A6BC0B3AA4593104E727261C68C4A47F809 -D77E4CF27B3681F6B6F3AC498E45361BF9E01FAF5527F5E3CC790D3084674B3E -26296F3E03321B5C555D2458578A89E72D3166A3C5D740B3ABB127CF420C316D -F957873DA04CF0DB25A73574A4DE2E4F2D5D4E8E0B430654CF7F341A1BDB3E26 -77C194764EAD58C585F49EF10843FE020F9FDFD9008D660DE50B9BD7A2A87299 -BC319E66D781101BB956E30643A19B93C8967E1AE4719F300BFE5866F0D6DA5E -C55E171A24D3B707EFA325D47F473764E99BC8B1108D815CF2ACADFA6C4663E8 -30855D673CE98AB78F5F829F7FA226AB57F07B3E7D4E7CE30ED3B7EB0D3035C5 -148DA8D9FA34483414FDA8E3DC9E6C479E3EEE9A11A0547FC9085FA4631AD19C -E936E0598E3197207FA7BB6E55CFD5EF72AEC12D9A9675241C7B00AD58FAF645 -1297991B5D01701E82228D0313FC7C66B263BC79ACDDF9AAC48A3CBF42B96E38 -583E1D059953076D68148DC8B6C9527B3A74CE7DEF788A11531F44120BDF0F61 -0B2F3ED94EEBCDE4ACD23834C242AA4314B9EF98E4BE72DB76EBDD0A028CEA9D -B4C38C1F2D24B8FDE686832FE96204552C820E45B6BAF0C3308742AE2BFDE813 -E71A29FD148B9DBEFCB126CDF69A9EFA387AF688A60D2C9854F51D54553AFE5C -767334B723A5DF119C443AC99A6E0F2064C0BD0B1C35088039988DCE53304BB2 -A5FB82BB7F7C652D77C9F0FBF3023729ED4F09C3E05B5175628B540C727BCB03 -0A0FAE4365FFFDA41D1E271BEB02941E47AB56207655FE82706E364B6341C923 -C085A0B87F153B25210DDD22A530C8482E29192FF869D6D2AF33974FA76AF7BA -A95B71B268E61B8184E16716F1F16E4BBC02FCD2838B014708118453C589D381 -FFF9522159D252E880946401CB275BD2A67E587B08D53EFB15F99FBB1A77A68D -37A10D169BA39097349F27677576B7DCDC7A55713C55519312C3644F7DAA3CE1 -6B69E58DEBF7BF2FBCE9329364D306B385CC2B1F61CDC67E3B7AE9F844107F6A -1851CFF89E9581410704C03B1FCFF5BCBE52566A6D638DA98112E016597B8500 -2168FFDCD2C163F0850639B5EDF832E29B8775AE110EDD8E97A942D8C2D892E2 -1AC5C4274CAB2B8C2413B09F271E2583E24DF07C05BF0AFADE625C48FAF0BF27 -8A9831DE03FF1519D11B41842E03157F7CE0396F104C8F61CF9C492815FE9749 -123948BB88F8BF7D7D3CA76CF725CA16A6215DED748218CC6FC7F4246DEF5EED -9EC2F5B4A17F9BE99CE7FF39F7E6555AAD262DD883BDF5CEF62D74F4EDC9C327 -45AE459D28CA232D277C2EECD66B2F9BE6481C49B30AEE341F3B4F2D81F77680 -73FB9DBC3EDCDCE228FBB45440BEFC4A6908008F3DD1F914F10CD58E9E41B4B9 -079EFD3F7183F316CF87623A76F79B71A72078A8E3574166B2BFD4C86B490788 -473C64D13CBC0D5D27CE20A36A14D2CE4E0A0E39627C9F55C1A512B81B268F8D -EC51B4F6D5D4A5672C152616091367BD8D94C425892C6B2FF324D8C94E3E7D33 -2129E49D9BBEEFF130825F1AACFC2B300AC2DE4B7D249441E1DC93A237874C4A -0A0101869724325A62A1506F2A5540000CD3427D1EA5344F020CDEAC16CA8622 -0D72197C9E584A55A2ECFD2C69F6FAA4193840EC8501D4FA58D292265EA588DF -E2325CDD0975DDA7A0909EF384506B995E1CD71FBCECCDB0C7EEC5F266552901 -805ED7DE21D70D5EC8FD2D92880F3B106FC2FB68E30D06E768205C29BCE3BA38 -65F7088695B0A6EBA6F369BB87F2CC2B988578C87D9FC44C08D5F8B1AC27E725 -9F3AC78055D8C9CC90D821E98E55D2B6F1F422EDF271DE703AEDA0268280A9A1 -C18FA69309EC07700A01EE8F41CC20951A9B879C5C58950CE4BABD4FB476A8FE -00AC1325A524B88A82D5A1A6F4288E8705C8A02A2C1BDCCB4B492A2E64364503 -738A8775B92753110D66F1C930CC6DEB0DFEBA01C6F804F1669BB2D8E000417E -58D1C4F35F6AB80C3ACD016DB3F25CC1DAD2D1E23A4E8C11CA022A5FDA6584B1 -F4C0110CA4991C349D678DA8BE0337E0D13D582CF6529302EFBB245BA856E586 -AB05E21710F37BCAC71CE791769B67A28E26CA737F8FAEADC01168C0148F2042 -45EA6C912E4D9B88D8237DD10B7AE706C4717E80A131DE454EE1FCF926197F0B -CD6B47B87DE71866C2E687BB374FA3EEDD59BE5AA03CA2EE12CCC6C894E7BC33 -E4509C9BA55346CD9092B6660C7E4B7250AE5FCF3D13D1B3DC7EA25091BB03AA -3C0FF59DFA3DB825C86A25A88904D85CD21C8B85364D2AB6AC3B6120DA236DE3 -5F88E7773D5152FC3A5F875F8DF852C80D4EE224522BC508A746A665801D7211 -4CEF8E0E6F74EE6E74CDA2B72A33CDC8C0828FCE01036D9C921906B1A58B72E3 -A44C1FA4A8BF751B91E6D700628694CCF35C440599B9E86D16BF855A61E36692 -38C9272CC5032039573096FE6838E1CBFB0F016CEED58E92CE6941BB218FD0CA -43989AC05AA4794F023439CCAAF62CDC99C09736D0E5C36F995DAF5F9EAB2B23 -B140644ED0D112C2E35B9D3D932C2842A417FDED96405EBC60456F3CAE4F09D1 -E3E6E947B86F734884DA2258E9479C2028C4F7F47584AE497E9E62C465A6A727 -426B33AF1F5DDF39B9ADEB826B5B005E152B872AAA413DD3DC72F121AA22E39A -920FA0CBB799FBB748EE5E824BB587F10B32A02A9316DAB9FDBE31DE44D134B9 -3E76D95632F319CB3D2D4C33191E9F142516204C74AD5509AD3EAED61C3BA370 -3D6E8B51EEC3AE8F244DA5614DD50366C6434A0C5C63961B93C5EBBFD46666CC -B78CD0F2ADC0415052F1969185CB5DA157F6218D532055B8147F34B41B8A6B98 -8E2B09762FA01F8E46164D83E1B6194368AFB117798505F74996E3EF74ACAE00 -C2544D8F1EFFF96A4251323CD088F5FB65A73F3378A8E5FFA708FC44B3FDA1C5 -CA86410E77A8E3114E386399102C7C2722AF63B08D97507B1463A65246993D98 -B1C1780C99DF66AA5A23783BDD30B878A76A069E8A426A39BEECFC1DA5B9F691 -7315C81482322A1CDE44153827BD9D56C076E1CB2EC701BC44A93F4D120A23EC -81B58FE060977DEF78E6A0F0216949BC91963288E874B7CCE7C67A6B67EC2531 -188139 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -cleartomark -%%EndFont -%%BeginFont: CMR12 -%!PS-AdobeFont-1.1: CMR12 1.0 -%%CreationDate: 1991 Aug 20 16:38:05 -% Copyright (C) 1997 American Mathematical Society. All Rights Reserved. -11 dict begin -/FontInfo 7 dict dup begin -/version (1.0) readonly def -/Notice (Copyright (C) 1997 American Mathematical Society. All Rights Reserved) readonly def -/FullName (CMR12) readonly def -/FamilyName (Computer Modern) readonly def -/Weight (Medium) readonly def -/ItalicAngle 0 def -/isFixedPitch false def -end readonly def -/FontName /CMR12 def -/PaintType 0 def -/FontType 1 def -/FontMatrix [0.001 0 0 0.001 0 0] readonly def -/Encoding 256 array -0 1 255 {1 index exch /.notdef put} for -dup 58 /colon put -dup 65 /A put -dup 104 /h put -dup 111 /o put -dup 114 /r put -dup 116 /t put -dup 117 /u put -readonly def -/FontBBox{-34 -251 988 750}readonly def -currentdict end -currentfile eexec -D9D66F633B846A97B686A97E45A3D0AA052A014267B7904EB3C0D3BD0B83D891 -016CA6CA4B712ADEB258FAAB9A130EE605E61F77FC1B738ABC7C51CD46EF8171 -9098D5FEE67660E69A7AB91B58F29A4D79E57022F783EB0FBBB6D4F4EC35014F -D2DECBA99459A4C59DF0C6EBA150284454E707DC2100C15B76B4C19B84363758 -469A6C558785B226332152109871A9883487DD7710949204DDCF837E6A8708B8 -2BDBF16FBC7512FAA308A093FE5CF4E9D2405B169CD5365D6ECED5D768D66D6C -68618B8C482B341F8CA38E9BB9BAFCFAAD9C2F3FD033B62690986ED43D9C9361 -3645B82392D5CAE11A7CB49D7E2E82DCD485CBA04C77322EB2E6A79D73DC194E -59C120A2DABB9BF72E2CF256DD6EB54EECBA588101ABD933B57CE8A3A0D16B28 -51D7494F73096DF53BDC66BBF896B587DF9643317D5F610CD9088F9849126F23 -DDE030F7B277DD99055C8B119CAE9C99158AC4E150CDFC2C66ED92EBB4CC092A -AA078CE16247A1335AD332DAA950D20395A7384C33FF72EAA31A5B89766E635F -45C4C068AD7EE867398F0381B07CB94D29FF097D59FF9961D195A948E3D87C31 -821E9295A56D21875B41988F7A16A1587050C3C71B4E4355BB37F255D6B237CE -96F25467F70FA19E0F85785FF49068949CCC79F2F8AE57D5F79BB9C5CF5EED5D -9857B9967D9B96CDCF73D5D65FF75AFABB66734018BAE264597220C89FD17379 -26764A9302D078B4EB0E29178C878FD61007EEA2DDB119AE88C57ECFEF4B71E4 -140A34951DDC3568A84CC92371A789021A103A1A347050FDA6ECF7903F67D213 -1D0C7C474A9053866E9C88E65E6932BA87A73686EAB0019389F84D159809C498 -1E7A30ED942EB211B00DBFF5BCC720F4E276C3339B31B6EABBB078430E6A09BB -377D3061A20B1EB98796B8607EECBC699445EAA866C38E02DF59F5EDD378303A -0733B90E7835C0AAF32BA04F1566D8161EA89CD4D14DDB953F8B910BFC8A7F03 -5020F55EF8FC2640ADADA156F6CF8F2EB6610F7EE8874A26CBE7CD154469B9F4 -ED76886B3FB679FFDEB59BB6C55AF7087BA48B75EE2FB374B19BCC421A963E15 -FE05ECAAF9EECDF4B2715010A320102E6F8CCAA342FA11532671C7C4DAFC5AA7 -E5E7238BDE3D0B9D54F1D91A121EB700FCCF3EDC67D0110BF708E4794E470151 -937339E8F4F1AB874DC9CCE83662D9121027884F839B550C4040C672EC076F94 -130D051B14B5DFAF569D2E583C868287C2AEC1D30D9AB67C92559A38810CE910 -66CDEDA75F72A531C8C9CF26056677D77C199DB601543C17476C5DCAD20C09A8 -3739BF2A949E82F79E75656E50B2FD6976632E20A2E93F0E04E088B5A3C361D3 -F4BF672704A4B3B305D44B29FEFFF694D2249173A562FD281C851C8C4E38D8FE -0DAA4BB321BF13CCA57744C4C1C7D4E7E7925D8D072F50488E15D4E12B8428A7 -B0D39D08EB6AE1422D09FB5F14E064C0C95B7AB08F3F575089E42C0BF8FDEF12 -3A41639800FD6B3EC325D7BCB6F38EEF0F3D22F08E3AE6FBD8F160115612DF13 -7D2CE018D185091427647502939588F18F7C654078349ED67836E9C0E168F0A3 -282786168E4F8D5497C73CEDFD88D5DCC83DFB10920B066EF4E7C142A3F7EA78 -660ECF7F4E7E300468E7DACB1D3D16DDC969B3E3AD5ABF3E5082E227278D803E -9B589EFEE78490488CEA719E55C5BC95816CE02AE234F7EB720351FE50D23097 -30D40834FA8E59D223ADAC35D54962D666DFC966F3C613DA8671715A4303E716 -995D28A9870E47D9B21F546B7441A8ACBEA3E4E1A8E0975B5F8F9F77394C9831 -DD26D0105CF70981E33056DA1023BAED7E016D9B63205F765836E501BDBFCD55 -CA900FCD2FE9054956125591940BA4A93E1A41319A9C0AAC4F24345E0F683A50 -B7036757D20B5164290D0F725DA9ECBA798D4262FB46E6C9013C85A10F7A24C0 -5DA8A1BECD84ED47A7C4B391106E278E5EB58533BD3555A4C664D53B263109B6 -848F973CAC98C2A4C638F0D25C7F7F5D1CD974F58D46E6F50DAFB9AC26B836C2 -95C214AE3EAA21DE1B2F71991B5B561184B0CD3D2B1828CCBE599E839447038B -97F6F507E1A723FE30CDFB7DCCED5F23AA55C353111C6AC689F5574E7DAC63DE -4AE738EE045922E28E07F77E598C07F4A84C38F8B0A6DCB940971E4FDE2B8CAD -6EB3D3252F733A5360BA7B654A9715411F11B247DB7FFBF3C3275782A2CEA8EB -812B9246FE212E03F156AAA176186E8BA4205CFA4207B2E85F3CDF6D551A5DD8 -18C271566F8F36314B7681D0A45F47CE9CC56B6A47234300E06203B758BC5092 -6CE1A580AA56329561D629C00778C99EC6DF5B7E4A3C78741034C10ADB91E204 -7897779DD98C7E82B8494FF8A7325612BCD41A081A9BEB4C42DCB170F4B82830 -BE259FC72F043C6A77C3D23562C380D21489EDDC389BCAFE3B9C84F0444A5216 -C2C6A127B5314B18698DD346148ABDB81B02C9894B5193F2FB6F8CB4B990FC6A -86AAD4BA0FF61987164E905B5E29760509EA463449A416EC9F26A00EF8E335CC -17FB46518AD95160E33A5FAABDCF528CF2DDA28F8E3E6A8DF95EB9E161D94EA8 -C3D5559541D54847847E4BBA0038388B6FDE716D707FAF2BA26FD044D199A887 -CA2802C57CBF83722D3A71F350C21F679DA0F021DAB8DB3167 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -cleartomark -%%EndFont -%%BeginFont: CMBX10 -%!PS-AdobeFont-1.1: CMBX10 1.00B -%%CreationDate: 1992 Feb 19 19:54:06 -% Copyright (C) 1997 American Mathematical Society. All Rights Reserved. -11 dict begin -/FontInfo 7 dict dup begin -/version (1.00B) readonly def -/Notice (Copyright (C) 1997 American Mathematical Society. All Rights Reserved) readonly def -/FullName (CMBX10) readonly def -/FamilyName (Computer Modern) readonly def -/Weight (Bold) readonly def -/ItalicAngle 0 def -/isFixedPitch false def -end readonly def -/FontName /CMBX10 def -/PaintType 0 def -/FontType 1 def -/FontMatrix [0.001 0 0 0.001 0 0] readonly def -/Encoding 256 array -0 1 255 {1 index exch /.notdef put} for -dup 12 /fi put -dup 65 /A put -dup 66 /B put -dup 67 /C put -dup 68 /D put -dup 69 /E put -dup 70 /F put -dup 71 /G put -dup 72 /H put -dup 73 /I put -dup 77 /M put -dup 78 /N put -dup 79 /O put -dup 80 /P put -dup 82 /R put -dup 83 /S put -dup 84 /T put -dup 85 /U put -dup 97 /a put -dup 98 /b put -dup 99 /c put -dup 100 /d put -dup 101 /e put -dup 102 /f put -dup 103 /g put -dup 104 /h put -dup 105 /i put -dup 106 /j put -dup 107 /k put -dup 108 /l put -dup 109 /m put -dup 110 /n put -dup 111 /o put -dup 112 /p put -dup 114 /r put -dup 115 /s put -dup 116 /t put -dup 117 /u put -dup 120 /x put -dup 121 /y put -dup 122 /z put -readonly def -/FontBBox{-301 -250 1164 946}readonly def -currentdict end -currentfile eexec -D9D66F633B846A97B686A97E45A3D0AA052A014267B7904EB3C0D3BD0B83D891 -016CA6CA4B712ADEB258FAAB9A130EE605E61F77FC1B738ABC7C51CD46EF8171 -9098D5FEE67660E69A7AB91B58F29A4D79E57022F783EB0FBBB6D4F4EC35014F -D2DECBA99459A4C59DF0C6EBA150284454E707DC2100C15B76B4C19B84363758 -469A6C558785B226332152109871A9883487DD7710949204DDCF837E6A8708B8 -2BDBF16FBC7512FAA308A093FE5F00F963068B8B731A88D7740B0DDAED1B3F82 -7DB9DFB4372D3935C286E39EE7AC9FB6A9B5CE4D2FAE1BC0E55AE02BFC464378 -77B9F65C23E3BAB41EFAE344DDC9AB1B3CCBC0618290D83DC756F9D5BEFECB18 -2DB0E39997F264D408BD076F65A50E7E94C9C88D849AB2E92005CFA316ACCD91 -FF524AAD7262B10351C50EBAD08FB4CD55D2E369F6E836C82C591606E1E5C73F -DE3FA3CAD272C67C6CBF43B66FE4B8677DAFEEA19288428D07FEB1F4001BAA68 -7AAD6DDBE432714E799CFA49D8A1A128F32E8B280524BC8041F1E64ECE4053C4 -9F0AEC699A75B827002E9F95826DB3F643338F858011008E338A899020962176 -CF66A62E3AEF046D91C88C87DEB03CE6CCDF4FB651990F0E86D17409F121773D -6877DF0085DFB269A3C07AA6660419BD0F0EF3C53DA2318BA1860AB34E28BAC6 -E82DDB1C43E5203AC9DF9277098F2E42C0F7BD03C6D90B629DE97730245B8E8E -8903B9225098079C55A37E4E59AE2A9E36B6349FA2C09BB1F5F4433E4EEFC75E -3F9830EB085E7E6FBE2666AC5A398C2DF228062ACF9FCA5656390A15837C4A99 -EC3740D873CFEF2E248B44CA134693A782594DD0692B4DBF1F16C4CDECA692C4 -0E44FDBEF704101118BC53575BF22731E7F7717934AD715AC33B5D3679B784C9 -4046E6CD3C0AD80ED1F65626B14E33CFDA6EB2825DC444FA6209615BC08173FF -1805BDFCCA4B11F50D6BD483FD8639F9E8D0245B463D65A0F12C26C8A8EE2910 -757696C3F13144D8EA5649816AAD61A949C3A723ABB585990593F20A35CD6B7E -0FA0AD8551CEE41F61924DC36A464A10A1B14C33FAFB04862E30C66C1BC55665 -6D07D93B8C0D596E109EE2B1AAB479F7FAA35279ADB468A624BE26D527BFF5ED -E067598E1B8B78188FA4BCFB0B51692D07B0BEBB930C6F0997B437E2C51B876B -61A563A2673932C2045833FAA35DB22ADE12102335D5DC734AE3AC5EEE6658D7 -92EB62131E1DFBA441F53EFF9021D9D4C491F26BE8F54C61165CAD778CE8695C -EEAF70E3B20C64D4C2B34A084B5770BAB2A974E898F62BFE90F132A37E2DCA4F -43E13DB13C94DFA8ECE2B7374827AE168634FA007F8981ADA046CED3448BF453 -FCD9A4F194FA648F9FC0971734BB69CB75348A88CC361FF06E984C86AF0EA429 -DAA5808CCE3583664AEFE0C59EDA04A147FB51227A5AB0C13942323E9B3733DD -3EE7DF7F774DE5D0D0980DA8C0192983F1E3EF18481EAF1EFEDA0068BCBDB28A -7FC7D9191EFFC574588DEC1E180341DC959F8EF56ED5B19F50AA82A4653649B7 -CDCA11A1FF27AFA7FF189A7E8A7C099AEEE0CAF3E121798B2721ABE8808D20A4 -AB6E704C0C376BD242C4966325D4C939669E28B55BC335405C400A9983B89EBB -B13D8C5F3A148E38E9ABD86D0171C927F1051266CBBD5C5D12522AF7CC17918F -410BABDD5FDD279338E8B17434DBF20B8E06B58D9E13B731E3C07E4CC350C431 -CE2034CB23828A19AE93124011BF053A3C5705D9BEF6D95205FB8360391C84B3 -7C6D719C0FB459A312AAC3C4256EAB293B6DC729CC5070524D1BDA41091E8B42 -2B6C4A092995AFB40CCF35730350CBA197F3D5BC5BB83CEDDBC6FBDE23A885CE -61D416B3A6CEC46474A0F42D5B923A61832262F234001DBCED9A7A00F5511F3D -C2178422A46CA5494AA8C37F51C40339CF9392A7098DF8596EA97C440989CA06 -EEEB5025B29EBF6038EFDDFD6F70989D63440E9C14E2A1040FAF427EB41259E3 -FF3BA255BD4C04BAAC47326181EC7CA1FFB32CBCAB92B1F8CDE6ED0DD3FE6D5F -EE14B739FC25BB13CD94A0C0DD7CEDD886AAC62248C64B8439064D1038886DB3 -187F017A79318B69963296B4812128EACEFBAAE983646E021F24BDAA2B78E8FE -2BCD5BFB302103D7DD28668DA7A60C446A27BFF8D6C66F4FBC61D271B91F0470 -16F567DABCD1E8B04CFBEF602BD9CE44B724B3EB8D30CE573EBB13BAA047F947 -90B24F2E49C20E2474EE9D019565E6FF25BDB3F74DF05BB9E148E1C5883A9EA1 -53AD383463F47D6C1077CB8D8DE48F71A5D42C54BEF4C0058EDAA735809798FB -356002E6B41BC6D5E3D302754016876574C8C392A0414E143FBA08528B2B8B51 -A7AD38CA71F2B75A78F4D62307B2F042B16FDB1C8E12927C72111F43C114633A -691AA1555B859E966976B61EC54FEF9378D020323942B77D128365D9ADD11318 -804215490E24EA6838C88452624554F96AC88DB08986DC1640057B3C8854C489 -3C79A8D23818954DBD431EF9E34251DDF50C242BF5A06316E58369328EDD7E2D -38B82585181D54F1F36A85EF4686598F875C9C782EB39A105A71C22CF37FCB46 -FE4F0B8A76A44DDDC2601A2ECE46F12BA384BB5001FA6FC3016B0400EFF87A6C -602AE0AA7A295CD9623713A2D88CD7DD162202E50E93D69FCD8544378162F816 -B3EF7F33E5D0304268849FC3D2FF083959421C75DF6E802602B472EC8FA3A3E0 -EA6F3C42B2D0D086F3E6865AD0E290792925260E004559D156D9A0FF1B36C9B5 -83D2672E28C339FAF0364CA000D54927BC1B45649C1952077E675C5CF90D1793 -96702FA1B4AE189F6716CF9973A32BBA7F0B4DB0FDD0669F8AAB4CC0E1C7DB15 -6763E03B264804D5BD7ED3987E880B59D5887EA1DFEE13626ECC45E3D79EC43E -3880CA33456B5D3CC6F8E4E1DBF523535E79933407C27D52C83630E262043ECD -BE8C2AFAEFE5D55EA404CCC1407BAF7C537908549DBCB35305FC74AD5C1F0962 -9714108017C64DCAA41E09CEB9456EEEC43E962A7995A44CBA8FAA54F73829AE -F167B167AC950CC7B91D874B2752A129E87E899742661067F992A9101BFEC5DB -276731C1D7D458BB59E2A675366E3FC87BE2E2A02978517F42E18DCC8D754492 -0A4279D696B40FCBFBAD8D71178F4E2ED80AA24075C702E1E5F96B0A80E249BB -333AA10694CB80B29A362AF7EDFA488C8ED189455EAB276492257EF17D38FE15 -D2D93FE011AFFE342B3F0404F152DC464CB0354352ED68A6DCA303DD72BE8F32 -9B9111513BC6668B6FB72204DAAF082FD5A78841C39C1712C0F8651B997DD821 -7A42D9D493E0AA519053A90830933304755072A1A3F7487E22E53EE170C5CAF6 -3EFA0330350945AF072CD07A28BEE084343FABF4FBE71CD7B71B515BA9756583 -3D7823D36B32FADCFA528949B056A44F5C98AA7D4983F55ED59B6F6BBAA97C87 -D669A4A48EEDB52DAE3D261B170B308F6C993FBA945C18CD4C47FCBE8125140C -EF17B8A91516DE85BAE14428BF36BB96FFE4AEA55325F8D27A46811A47D6CDCD -D86BA100254F55EA60D683DD53A77F258D33BA22F96D9A5B610D735E534DD758 -B542ED33B51820F48B3D5445A622A0CA56E02E5846C8E7A020EC6D6D717734C1 -60E68BF95C247C5754D644B6974008FB408B3E1BEC89C885507010D7B9D7E2C1 -47E0208E1E17CE505CB1731BA87434C8B60974432831FC4BDD58393E2AE2E23E -994859614E7EA2DF695FC80C269D793AEC046F7BCA5D7937BB9155AC3096525A -AFA7A2B0086711F9417238C0723CED665A0581C57FB2636395C38678AAF13325 -1FB25B23C193DE5BF4074C550673A599E40203D0DB554EA0C1CA425F604697C6 -D40390363030E58EC29AA9736C668C4DA128DDD51A9FAF7776722C7F15B68CEE -A050AAFBADF84E09275BC34AB0437F0E16C1BDB144B68FA9851408EBDF51F403 -C670E263C2AD886014D16975AF8D46252D36555158FF5B330E7896D6034234FF -E7C26C59FEEB8EA012E2934B9F8BBE4B0853D4986AC4BE231F1906AE9A7FE13B -57A8F68A5CB8CC2E1631464293C0B4C4A1AABA053814D20449F5B318E8ECC4B0 -5F240D1DBAB24AD35B4C566BD119C616D722CFEA8EE734733675E3C1A8697168 -529A73385332E0CF608864883534CC155C786CC52BF24AAA0AAE07A2243E1888 -B621AB938B89AE76925EDE639986E1C13D37005DA0097D8E58FC53A8751CFC34 -36EC937A01B5922D4362973AB6F1431D00548A667B43ED082248C91BF37914DD -910CED4FA6E630E12D52F868A88E20E3C2A770AF3461EA2B829B78B37AB39AF3 -4C744D6BAC414E9383E3910CB455222C6C4A5BE6788894C2D7697C4D7C34C665 -3131AE4C458DA55BD0AC6EED0FA8A7D9FE05D0130B14EC485A13D29141D2E7D7 -2D0217B46FEFEC84CE77C2540A6C23579B2543F414D997C94E71CE309C2C854F -BA7DD8DEBDCA3CC9E797C5A939C1442B934CD95E2F9348C309595B37BD08E561 -A34788F2ACE938092BCC2458CBB3700549D42FD95AEA3CA54438810F4FF1AF4E -75BF96182752018EFF07013A4165F3C278EA67F17680FD987EE2B038FDBFCB0B -721093A5FD1F3F5F3EF9A377A2060126FC58D9D7B0E1FE061BF9AA06E727FD04 -3464C84CF6D4880DCF3402AE1D21B1D3739BE183BECD107CBF14EC4F13809C9F -ACD8084313A689D014A06158B2011EF8E28B984448828656E224048B55CB114D -25001FC08125E54AF7AF35AB580A34ADCF35E53ED5D5D33F280E7D638D439D52 -28235E0FA8FAA6E947B13058834B135CD9F09328535488EF6529CAF6CE8F4DA1 -15ED74F2994A847A3EF405CDD127E364357C5577CD05EF2E5F7B3D8F2E9E95AC -5836C63883C0D8A7A7E4BB23CBFAA8E2DEF26A3DBC2DC3175D49F2A0B54C127E -6F05F16E2A2BE5557CEBCFAAFD2E38CA974EEE37816EFAF7DB1D466CCA6B5C77 -409D6E60698C511BEC796FF1A24C8D0BF6059A4C1AE197F7843BD1B07FB893B6 -D334F4A73EBAEA1278E23E5F761A8A2A39C3344B8AD31DF771B13C0E65F6C669 -1DD8249E24BE398E82EC949957B4533C02D455DA8A791AF122AEAC5DCF963EAD -4BFAD6595EA3EEFA03DADD85FBD82B9B7587EC62AC290308A43569CB7F0FD59F -EE3236452FFFC0BF7EB92C208B4AEB956058DE5A8DC2D4064B56A8216E525042 -BA145BFC54DC2E820BDF2D74474A044E1830773F0B09739B36536899E7D71B61 -C898C8AEAA68580424FD23F3B9DADC4B40E18BB2B28D9CD05B8644DD050D07DC -682865BA399193B8D44E09A67D548CB82CDF36430C2F8A3CD2FA12FD7165E7FD -10D4FADBDD951236703F0BF539D48E46C7A15CBE4B7FC55D3F6927A209438374 -562B5DD7E9B5C4A4BA40E9EA39E0854B46C56D3C13D2D285B0C88CEC9B2F613A -8BB5A743F0C632C3F13EF4878A59914934EB1551CF54465B1FB2110E68ABCB58 -B77F4EC2C4173511D7B59E4090621D176AE9B44427DD00748FDF090F61754C46 -569DBB028B7594BDE655DE79478418010FB251B38CDBC7843825C13AA673BC17 -2274A2A699264607ACFA6FF61693935FB06B950E46AE0F2478C010E5B6BB2F76 -3B8EDA1764C4B4F79165733B5D837C6821636DCC0FDD2F3B4ACB30F315A00CFE -927162AD97E97760062DC9B5302F3E8C7779091529078F4C2A7A28FFE90286B9 -E127863A971C0985B8C0EBADB1965F1C18F2CA161ACDD56EBEA38CD42BFD285D -2FB0B581D719BCA123E21018B63442134036F9DE34B9AF8D66BF76E8D8DC9847 -E91581807DCACC7E75601308F543E816190CF9BDACE7567EDB5721EE95F7F2C8 -5D4367CA048181B9CBD2EED12EFC37D21AF57AA17815AE80D2B661EC4114D3DE -18DF851ED3CF345363B5731A76F6E625E439F784706774DFB89FBC8677212B98 -F38FB13A4CBA793B4A7B3A286B180F18EE2BF1A3D753DAA2E73578EBBAA047A7 -C46EF4D10F3A761DA725A318D369ABF048F1D65CCD5530212F791A4662DA6EA1 -C793E1AEBF89C1B63B1CA7261540AC808BE6C60FFF6F9958A1EAAA4C19B14C02 -DCC451AE07767790BEC3301E456ED2933C88E4C1AF803383AAAB52395B1A6287 -964BF499F01DC3B76C2481C16E15A3C003C0E445DB83732C7D7C53DFFB325532 -A95ED14D734559BD3169276AF2C394067DB010F572220938D4DFF1057254012B -3EA973CA8DAF74AAA72326ABE156599ABB72855C3A25880DD320F067D879F3AC -7DEBDD7123D7B9523E6868074344329A303B8014D1142DFCD43BCB6AF19636D8 -21FC6ED53FFFB52AC8F3A09965840E3BAB80B8327DC9A151F18C7166785072E0 -563C959269C681A3FB6E32E582E07EA76EA774FE8D417D738EF3E1E05BFD77B0 -B6589C66D819B847CE226153CDB07E0E0859C95D8A5694671EB8D8157474A041 -A08CDA4C87B46DB60AF293579EB15B9AA4E1274057F2F5E0398113502F9653D3 -7A950E142036C796EF712158CC803FE75B1C3B3C81D4A461B02874234906BF21 -4CA6C813DDA69F81F6B19B2836FA4C68BBD16F8AE64B1380E3D53845F9EE0EC9 -3455647EBB1142C34AF674DD5DFD379151D9974BB82C3E215E10B72CFA538B09 -70ABEB277900B217965C5C9075DE606DDEB0CF6CBB57D5953FFC864456ADECD4 -FF3F4D754130BA8C4F9BDA987DF386169A56C84025246DEE12F7A1E67CD03DA2 -4C77AD17B25C19C527183915C00625DC1A7906F11EFA1D7A616223E7DC673F50 -779C15BFB1045ECD4D305F412DA90D34E75A9428E2D9E1111A5DD6AB17A3DF8E -824856B613B363D8C931CF6F3DDC69BC678BAC74ECE2E11A6386FC2023678630 -7D1509119C5D24313A1F73E375DA2F48E28AF6D62449110E127F1629B947019E -DBB952C097ADD6613C9D20EECAF26FD84A85F0CC2EBC871E32146D5226A2D813 -40F7A62884656DD2DA31EEA0A740B74DC8C9F2A413C9EF46D2455381AD0C2843 -2530467351897ACD85CC1EA1C01A1485420CFBB92121161E3EB50BF1BE3F9589 -719F25C8E54F7999042F5FF461D7F1CDACC42546B978D8C1188EA27BC38E9BC9 -22D91763D1B795A4EBF6EE5B1259B66728B323082E403BAFE83D93E367AF2424 -35C6DCB7E10B95191D49C36E6F26B908F8E4D60F98F8EA5449E1B6C4C45D3B8A -6F75D9A040F87181756FE7471205EDE5ED3A2EFD5913016F786E021255421673 -CF9CA94D6E9689F4C27DFBD7DE26337315264D98B4F02D4A459FE7EA909DE8C5 -6D553E02E188298D41B70397CF438FDDAEA990F4E59C9DA1D3BC4654D473222E -E9382C7164A9E2746F09B0A198A01E2DC485701D0FD793A1471DF32C291EEE70 -35117152E68BD31F54CD4BA2CD8D65047A6E4791141B63C735A2C6E11A6A4B00 -DC5ED0673BB712CEE608FAAA9584E5E6A064D76A33A5C72B3C2DF19CF28243EB -DECA4F1B556950EE6A90904E58531211CCE2DC09EF56CFE9F0FA8A5002C7EEEB -9C8547CA493C3F5A0FC951578503EBE9B4A4EEDE049A4DBEF53C734F30EDB31C -38897F46B5CA0D30F82C443B9C31D7D9D98A2C9BFECE48AD95D905FAD1A2DCB0 -16BC34F665FA35A06D409C5D7B2DD968F396B70D676CEBBFCC172799F62D34AF -AF2D9B9C3E557CE1AFDAFF845D64425C71F698BAFC310FC3F01D6847EEAA1293 -D9F365DD69E67D155B6C910DE9AEE24F0CE6CF69B72DCF2A38D34F31320F6043 -8147FCF9FA36D515FE8507A43F73D284D57F719ECD7F8DF806A8CAF0DE71B4AD -8DE440D9CEB722C806E3063660BC67AFC6D7CE0D46095C96DE736B431F70F763 -894B5B5F3CDB9A633A8C222E3E61697E5B9EF0D565001AC49095DB271B8A22ED -3F1AAB312DEB4C0F3ED3E10BC82A128455BDAC6688BE22021BBEC95CFD994787 -9CC3BDB86BF6130D6F288805A506488A4E75B61E9AB7185C04161B55DC279190 -8E0D5C566CE851B4F2ED5A24F968304C4B7D35696D777796FA22A49F1DF73728 -80F10173E06657540F7725DB7395838929890BB3B70118DBC353689D4C9C1CB1 -AAD3C13742A1F0218AD24DB86E25019B1A5CC4DAB0BF3D0918CBC688BBB82734 -D027FF8CCA7DB8326C8E9B4CB36D071E436CD83BC47EF720FA45DC3799BB7765 -6B31238D0E9879C52AD2E8D15364799A77CE8F2FAFB629E0327B3051BEF1B0EE -2578CC8F0A7B44FCAB86FB93BC6C30DDDECED80E1BF51332208A1AFFD76CB00B -AF6B773D41B24951450E129837A04CFDE7EDD9E0743AE6DF05AF20259E37C2A0 -2F5AA8A57A1B2CE148296764B1351D290A9052C590B8F6D935C4FEEE5B8DE775 -EAEC88FF612E761BF215479C35E01F7730BDF0C99E18A670EB6FEBD6DB04F2AE -C253EAD3197F1EBD6FDF07DCF13FECB7A2DC1ABD936CA9563B7824CB05306A37 -B9DE073D3AB568FCF2962DCC0E6ECAD5D94D1D6EE8FE4C9117F09B960FD1C576 -D47AA3CD49105FDF1BF551055AB8BECD2C20CBC7D9A456E5BDBCA27A9AC1B811 -5A2553A0665FAE3183C9168C662526BD02E327D7E48E2FA4F468E339CB6AA027 -E5A4B6CA3FF208876BB91E0E6CCEDB3CAC04CE0545F0A8729DFFC54DB5A29CCA -29B2EE9091A623435B2181B350BACD984E82D47C5DB8D931A40E63181ED77842 -8B86B1CF23D6E7F09FE3E81D3AFF679D49A024C576CBD46101AA0F2DEEDC3A06 -A64BB5C68CAFA79A6814B28C86D572A825D108667CDCD164D4B281CF787378F4 -31B49C559BE1987C1B27C2057400F1ECB24A1F5838BBB93077F677E5DDB6C5E0 -0F80C0FB36EE42F0BBCA978A7E8FAEDC029DDEC84BD08A1AACF750DF16068884 -23C3FEC0936790C86E55BDF3BBBE317E92348514350501C852EA9C92493FCFA6 -5CBDF0967F4B9CF5345D580171099C8FB55E29DA909E2E806F05ABE8A103DE85 -937683EC3F1B2E1C663771FC9B4A224F2215B0CF2D4065683B15AC1A0CBCD9C4 -BABC1B9A0DFE025F3B8D73899510BD688F4B5782EAEF3CBAEB1A1BE8C4B48AA6 -603979C3DEB325B9A06EE99DD8BF5F619489ED547C89D2C23DBF7F641C304717 -39144A603B1601EB75C3E092E2DBFCA0957CC04ACDF4F4C4B3569B0A83AC472E -7125285EF05D1AA6EDD0B38DF6C4E7D0E8B6FFB3FEC50A1647A602B7C8E056BC -D7CD1C0159BF4954E23DABA6762DC361198261400E4C27572708650D18D33122 -74F3FB15A3C032774DF47734358893496619291549A1258459274418ECBF04CF -D2FD5FC58C6F8B9466393AAD6EEE72AB26F3D5120B05CFC042CCE32031D0F9C1 -DAE18A1D5F72B7431169F87DBFB525523598202FC2EE6209E6DEEA5FA0109481 -07AEAD311C35EF18D8621998457F7AF99E2595413DCD9EC0423E26AC056AAE72 -7A481D693352CEC394D220BC9F9F25355EE8132E6DDD4137384C7E122F6F6450 -598D0BB20A52D278574193D00DB0ADB4F3521640123E7A17D20EC82D4B2B1D80 -5A18858F61C6ADE763F6FB42F57EEB7E3A940FDA720CB32D50DD802D743A963F -D04A00A130E6CBF8A59395292BDFD0D7ECD6E8EF5AD1A150116B04B1F94252D6 -C1F0585FD85528D71203E8ACA82E34C8ADDF30B4E5EAA7B1C8469E0779A0778B -69120F13D4F4F35E2504E9D07C0AC2305B34954D40B1D4525876942C9CF66F1B -7F3BA92F0A7168FB491930A1D4DFEBC862F619682006428DECE52CDAF3DE0472 -6155780C2A251E474A4B6C961E096EBDC56C6BFBDAA71B65DA4DAA2634F448EB -435DCCEEB233A16423B81B1019A2C8218C0A3D648E368F8870D3150D6B3E7E51 -FFB599093F5DCBE1E73575D4DD07A9256D3805E9F366CFEFC0B0D6BF6BC520E2 -2AE99F722A8D574F7A0FB6FCF50B9A1D9D3EC96843E6389C88C117FDA94744D3 -B2DA601F592C28E631D19A4510B29AF20B4389942A610640292F03A9AFAAAD98 -9213040F95A9EE6276EB2395D5FAA368FF184DE2808570BB7194D863067823F1 -539FB91438B2063E05FAB0823B784380C032E64D95F0ED46EF945F47FB970BC2 -BC260111D9B161027EF2B87B1B2103AA32FEDAA665252A42FF0BB0F43AC77F11 -18C36EAB9372C5DA363A45BB989137EE0E22EC1449E81EAB4FD227D918618B7E -7E3D688DBCF7DCF5D7C838F09CCD481A6F749E42FA01D93321D34CDFC087C543 -D173DD11A43FC877A321542F4BB95528203C3809970B6939E0A7DB703F1EF923 -514F90C78F65584154AC6A44E93D923D5E29BE9774A06989A235B83AA2950946 -79070868B9A39DB6D2C47AC878DA9BE3C31C5F8929CDB079424C281E4E7F10D5 -A979F10C7194E8C788B218107DABF60FBA56045912DDE8124AFF65BB47A7ADA3 -8281275AF58BEE8E0E3CEE854FEBBF6207C57C918473644B6D4B80FE72979089 -8B5EAECCD273F73EB0351C286FDB828C5FDBEFED59D8C437EC70D335E31C5847 -A5F2EE540206784FD732405A845445B300E348AAAE58E95A690D60D1745DF813 -4471E27B78BCF494B01754FB298F6BF3EF3F6F140080097D55E48E56A97BDA82 -EA9082A527CFFAFEBD50C374CC36BFA9816B8171D31BD09AA14F7F041BE63076 -4C436D492B1B5B763CA50DCF1966B5AE854572343A34F7D5C0F7A65B48F2DF21 -D8539EA22706137215B01C5DCEDEFE73C5D1A8DED6D937A2CF5B646EBD636497 -FD9F43536A2B16EAF61E92E1A1614ADCDA1A3EB0CDABF1C9619811C7A303CCC6 -C2A19A8709137A116D7C04095A8CD80C6A63D43DAD5BD17EF76E35CCA991D1A9 -E51BDC1E77D05CAC62D5DF8AC4C58DEDA04F2D9F64E48F358037005176ADF69B -69334C21068F8C5B3682220485047006AEA322262ED3C5FF0D27C5628401A5F8 -E855B8C0E9F071739A3459AF94A64FC46F7166A9FBAC749D9DCFAD17E241CB39 -FB6CD9B41B22BFBD8A933DE71D535AAE7FA3D0C94C5A258C93B2D1856D86B436 -25EBE81706B482A3C094C607F8A253FBB979D48460A6DF67EAB2371CA6A52FE2 -353375C742B71EB9677770D07295A5606A615E47B5F55269EFD55051378088C2 -2A221E89B7832FC52B094DE78DBED8633359B886A2F9E7C73541FB8C1F23D351 -A95D8AA11CCBFE2DA97EAC1060F14079857FD3E7D8A35478E36C7197898051BE -420C9E5A5D1DB5B8AFCB2C043702298DB8B8DA88D990C87AF394502EF6501A96 -9F0EB35FB4351997718488B58EC78C8809D3BF957897EA506D2BD0D25154F2B8 -8C69787C92F88D2158CF2938E25D244E2D74B7F98C6E9013D08153C1D9528657 -293000C21BF442C93C813EBB36FBBE4C8BAE67EC4EECB2C454B4129F266E1CE8 -F12F5D28DDAF3E21A546B5EA7AB8F75FF6793EE8D24D8EE61500C676C89F68E7 -BB8D86B5B0BBE85A7E7C9F9116CAA991223F5481214C84284D6A757614C07C51 -395F942DC454166DA7C0F717A9CE43AC9C1866285A21A1BDCC7CD4E1C17D758E -4CC5BAED0A535AAA16812F83307A12D2F63FFE98F0FB548CA92F10C77DE187D3 -59F613393994076E74AA882722AC925CC41532D0E6B836C005E514A991790C99 -6FDB0BAD510752594593FD1991C7A3E361DD80482626CCBB63698F6E42B3D307 -C486D47BB02E4B4A07AEBCE6CD3B8E6504300C42F11AB748FB285B3DE7C4ACE9 -B3C3787138392458426A2D3B7C57A972D027149EDA707141BE868F0A25057A23 -B1C187B10C8B5E13BF402882335BA70DAE8D7015255DE618FCE25D0AC88C060C -6749DF726EE7B31396A589E78ECDD51ECD4A8F02A702D0D41B034EED77B66B6C -5EDEEB7E43D8AF4D5F6BBD5FB3730936C5EE4415A87AAE4C4491A19A21E87CEC -3F8C539C8D1A2FA801E16D5CDEADE95633701E9F58FF49255EBBD9696DE47260 -AFEB9FCD40DE360BEFCEF66E17B50D3D74CEA3419CEC86D337651C234ABEEB81 -09E595F7C8D1AFBFE3ACF948F9908F5EC7498F8CD92E63342ACF7D0B3DF289BC -ED8FF26780CC9E487F097D57B58AAB4969E907616CAF003C97D30C858E1AAC3F -28C478149AFBA9DFE899CA06A4B6E4E71F02A66F6ADED4AE8AF5403EF2F9A757 -BA5CC7DC1DC49AAE077C4C5A206A70B9025211B1343973B96E9DEF5AE4EEDC4D -888BB71B1222A9A9F3E2F764A5E61052BB16EC50507439B4D2F42455F622252A -8E6D8888735433D334318B9D53CE5578C1E2A437BE420C467425B1B7CCB21113 -2F03C3CE58CE1AF82CD6152BDB88B77670A02DE82FF630C3DC4C5D8D2ECDF614 -A4B8FC9C82324EA5B0B2E8A359A9F1B6 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -0000000000000000000000000000000000000000000000000000000000000000 -cleartomark -%%EndFont -TeXDict begin 39158274 55380987 1000 600 600 (meshGenUserGuide.dvi) -@start /Fa 240[45 15[{}1 90.9091 /CMSY10 rf /Fb 133[40 -48 48 66 48 51 35 36 36 48 51 45 51 76 25 48 28 25 51 -45 28 40 51 40 51 45 4[45 4[93 2[66 6[83 3[33 2[59 62 -69 2[68 6[25 8[45 2[25 30 25 2[35 35 5[45 20[51 51 53 -11[{}46 90.9091 /CMR10 rf /Fc 138[62 44 1[46 2[56 62 -3[34 31 3[51 1[50 1[54 22[58 3[70 50[56 19[{}13 99.6264 -/CMBX12 rf /Fd 138[54 38 1[38 2[49 6[54 38[73 6[27 58[{}7 -99.6264 /CMR12 rf /Fe 133[46 55 55 2[58 41 41 43 1[58 -52 58 87 29 55 32 29 58 52 32 48 58 46 58 51 11[80 73 -58 78 1[71 79 82 99 3[40 82 82 66 69 80 76 74 79 52[58 -12[{}41 90.9091 /CMBX10 rf end -%%EndProlog -%%BeginSetup -%%Feature: *Resolution 600dpi -TeXDict begin -%%BeginPaperSize: a4 -a4 -%%EndPaperSize - end -%%EndSetup -%%Page: 1 1 -TeXDict begin 1 0 bop Black Black Black Black 876 -36 -a Fe(MESH)35 b(GENERA)-9 b(TION)34 b(USER)h(GUIDE)p 1225 -223 1074 4 v 1227 197 a Fd(Author:)44 b Fc(F)-9 b(ranjo)38 -b(Jureti)m(\023)-53 b(c)p Black Black -128 629 a Fb(Mesh)31 -b(generation)h(is)e(a)h(set)g(of)f(to)s(ols)h(for)g(mesh)e(generation)j -(whic)m(h)e(are)h(then)f(assem)m(bled)h(in)m(to)g(a)g(mesh)-128 -742 y(generation)h(w)m(ork\015o)m(w.)41 b(A)m(t)31 b(the)g(momen)m(t)g -(the)g(only)f(supp)s(orted)f(mesher)g(is)i(a)g(cartesian)g(mesher)f -(whic)m(h)-128 855 y(generates)i(the)f(mesh)f(from)f(an)i(o)s(ctree)g -(templated)g(re\014ned)f(to)h(the)f(user-sp)s(eci\014ed)g(tolerance.) --128 968 y(The)g(pro)s(cess)g(of)h(mesh)f(generation)h(starts)g(from)f -(a)h(surface)f(triangulation)i(\(usually)e(an)g(.stl)i(\014le\))e(and)g -(it)-128 1080 y(is)h(it)g(also)g(needed)f(to)h(create)h(a)f(meshDict)g -(\014le)g(whic)m(h)f(con)m(tains)h(information)g(ab)s(out)f(required)g -(cell)-128 1193 y(resolution)h(at)h(v)-5 b(arious)30 -b(parts)g(of)g(the)h(geometry)-8 b(.)43 b(The)29 b(meshDict)j(\014le)e -(is)h(con)m(tained)g(in)f(the)h(\\system")-128 1306 y(directory)g(of)g -(y)m(our)f(w)m(orking)h(case.)42 b(The)30 b(en)m(tries)h(of)f(the)h -(meshDict)g(\014le)g(are:)p Black 9 1494 a Fa(\017)p -Black 46 w Fe(surfaceFile)f Fb(is)h(the)f(name)h(of)f(the)h(\014le)f -(con)m(taining)i(surface)f(triangulation)g(of)g(y)m(our)f(geometry)-8 -b(.)43 b(In)100 1607 y(order)29 b(to)i(capture)f(corners)f(and)g(edges) -i(of)f(the)g(surface)g(it)g(is)g(necessary)g(to)h(divide)e(the)h -(surface)g(in)m(to)100 1720 y(di\013eren)m(t)h(partition)g(whic)m(h)f -(can)g(b)s(e)g(done)g(b)m(y)h(using)e(surfaceF)-8 b(eaturesEdges.)43 -b(It)30 b(is)g(p)s(ossible)g(to)100 1833 y(sp)s(ecify)g(the)g(angle)i -(tolerance)g(for)e(edge)h(marking.)p Black 9 2020 a Fa(\017)p -Black 46 w Fe(maxCellSize)f Fb(is)h(the)f(maxim)m(um)g(cell)i(size)f -(an)m(ywhere)f(in)h(the)f(domain.)p Black 9 2208 a Fa(\017)p -Black 46 w Fe(b)s(oundaryCellSize)h Fb(is)f(the)h(size)g(whic)m(h)f -(applies)g(to)i(all)f(b)s(oundary)d(cells.)p Black 9 -2396 a Fa(\017)p Black 46 w Fe(patc)m(hCellSize)i Fb(allo)m(ws)i(the)e -(user)g(to)h(sp)s(ecify)f(\014ner)g(cell)h(size)g(at)h(desired)d(patc)m -(hes.)p Black 9 2583 a Fa(\017)p Black 46 w Fe(decomp)s(oseP)m -(olyhedraIn)m(toT)-9 b(etsAndPyrs)33 b Fb(is)d(used)g(in)g(case)h(when) -f(the)g(user)g(do)g(not)h(w)m(an)m(t)100 2696 y(an)m(y)f(arbitrary)h(p) -s(olyhedra)e(in)h(the)h(mesh.)40 b(With)31 b(the)f(option)h(switc)m -(hed)g(on,)f(the)h(arbitrary)100 2809 y(p)s(olyhedra)e(are)i(decomp)s -(osed)f(in)m(to)h(tetrahedra)g(and)f(p)m(yramids.)p Black -9 2997 a Fa(\017)p Black 46 w Fe(k)m(eepCellsIn)m(tersectingP)m(atc)m -(hes)h Fb(is)f(in)m(tended)h(to)g(help)f(in)g(generating)h(meshes)f(in) -h(thin)100 3110 y(regions.)40 b(This)27 b(option)i(means)f(that)h(o)s -(ctree)g(b)s(o)m(xes)f(in)m(tersected)i(b)m(y)e(the)g(giv)m(en)h(patc)m -(hes)g(will)f(also)i(b)s(e)100 3222 y(used)f(as)i(mesh)f(cells)h(and)f -(this)g(help)g(the)h(user)e(to)j(get)f(a)g(singly-connected)h(mesh)e -(in)g(thin)g(regions.)p Black 9 3410 a Fa(\017)p Black -46 w Fe(k)m(eepCellsIn)m(tersectingBoundary)h Fb(is)f(similar)h(to)g -(the)g(previous)f(option,)h(but)e(with)i(a)100 3523 y(di\013erence)g -(that)g(all)g(b)s(oundary-in)m(tersected)f(o)s(ctree)h(b)s(o)m(xes)g -(are)g(used)e(as)i(mesh)f(cells.)p Black 9 3711 a Fa(\017)p -Black 46 w Fe(c)m(hec)m(kF)-9 b(orGluedMesh)32 b Fb(is)f(an)f(option)h -(whic)m(h)f(can)h(remo)m(v)m(e)h(cells)f(whic)m(h)f(mak)m(e)i(the)e(t)m -(w)m(o)i(disjoin)m(t)100 3824 y(domain)e(parts)g(connected.)p -Black 9 4011 a Fa(\017)p Black 46 w Fe(ob)6 b(jectRe\014nemen)m(ts)31 -b Fb(con)m(tains)g(the)g(list)g(of)f(ob)5 b(jects)31 -b(whic)m(h)g(can)f(b)s(e)g(used)g(to)h(re\014ne)e(some)100 -4124 y(in)m(terior)i(mesh)f(parts.)40 b(The)30 b(supp)s(orted)f(ob)5 -b(jects)31 b(are)f(lines,)h(sppheres,)e(cones)i(and)f(b)s(o)m(xes.)p -Black 9 4312 a Fa(\017)p Black 46 w Fe(subsetFileName)g -Fb(is)g(the)h(name)f(of)h(the)f(\014le)h(con)m(taining)h(surface)e -(subsets)g(whic)m(h)g(can)g(then)g(b)s(e)100 4425 y(used)f(for)h(lo)s -(calised-mesh)i(re\014nemen)m(t)e(near)g(the)h(surface.)p -Black 9 4612 a Fa(\017)p Black 46 w Fe(subsetCellSize)f -Fb(a)h(list)g(whic)m(h)f(is)h(used)e(to)i(set)g(the)g(cell)g(size)h -(for)e(a)g(subset.)p Black 1739 6192 a(1)p Black eop -end -%%Trailer - -userdict /end-hook known{end-hook}if -%%EOF diff --git a/userGuide/meshGenUserGuide.tex b/userGuide/meshGenUserGuide.tex deleted file mode 100755 index 6cb7ee59bf337a9155b55a6fed569328de245140..0000000000000000000000000000000000000000 --- a/userGuide/meshGenUserGuide.tex +++ /dev/null @@ -1,57 +0,0 @@ -\documentclass[11pt,a4paper,dvips,oneside]{article} -\usepackage{setspace} -\usepackage{epsfig} -\usepackage{framed} -\usepackage[normalem]{ulem} -\usepackage{color} -\usepackage[a4paper,left=2cm,right=3cm,top=2cm,bottom=2cm]{geometry} -% -\renewcommand{\baselinestretch}{1.0} -% -\begin{document} -\begin{center} -{\bf MESH GENERATION USER GUIDE} \\ -\vspace{0.2in} -\uline{{\large Author: \bf Franjo Jureti\'{c}}} -\end{center} -% -\vspace{0.2in} -% -\begin{flushleft} -Mesh generation is a set of tools for mesh generation which are then assembled -into a mesh generation workflow. At the moment the only supported mesher is a -cartesian mesher which generates the mesh from an octree templated refined to -the user-specified tolerance. - -The process of mesh generation starts from a surface triangulation (usually an -.stl file) and it is it also needed to create a meshDict file which contains -information about required cell resolution at various parts of the -geometry. The meshDict file is contained in the ``system'' directory of your -working case. The entries of the meshDict file are: -\begin{itemize} -\item {\bf surfaceFile} is the name of the file containing surface triangulation - of your geometry. In order to capture corners and - edges of the surface it is necessary to divide the surface into different - partition which can be done by using surfaceFeaturesEdges. It is possible to - specify the angle tolerance for edge marking. -\item {\bf maxCellSize} is the maximum cell size anywhere in the domain. -\item {\bf boundaryCellSize} is the size which applies to all boundary cells. -\item {\bf patchCellSize} allows the user to specify finer cell size at desired - patches. -\item {\bf decomposePolyhedraIntoTetsAndPyrs} is used in case when the user do not want any arbitrary polyhedra in the mesh. With the option switched on, the arbitrary polyhedra are decomposed into tetrahedra and pyramids. -\item {\bf keepCellsIntersectingPatches} is intended to help in generating - meshes in thin regions. This option means that octree boxes intersected by the - given patches will also be used as mesh cells and this help the user to get a - singly-connected mesh in thin regions. -\item {\bf keepCellsIntersectingBoundary} is similar to the previous option, but - with a difference that all boundary-intersected octree boxes are used as mesh cells. -\item {\bf checkForGluedMesh} is an option which can remove cells which make the two disjoint domain parts connected. -\item {\bf objectRefinements} contains the list of objects which can be used to refine some interior mesh parts. The supported objects are lines, sppheres, cones and boxes. -\item {\bf subsetFileName} is the name of the file containing surface subsets which can then be used for localised-mesh refinement near the surface. -\item {\bf subsetCellSize} a list which is used to set the cell size for a subset. -\end{itemize} - -\end{flushleft} -% -% -\end{document} diff --git a/utilities/FLMAToSurface/FLMAToSurface.C b/utilities/FLMAToSurface/FLMAToSurface.C index 584efa4abcce266741a87f316024dc814e64bac6..6cff65f122caaa2fcd01324fb43d9120fafd57b8 100644 --- a/utilities/FLMAToSurface/FLMAToSurface.C +++ b/utilities/FLMAToSurface/FLMAToSurface.C @@ -1,172 +1,146 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - Reads the AVL's surface mesh - -\*---------------------------------------------------------------------------*/ - -#include "argList.H" -#include "Time.H" -#include "objectRegistry.H" -#include "triSurf.H" -#include "triFaceList.H" -#include "labelListPMG.H" -#include "IFstream.H" -#include "OFstream.H" - -using namespace Foam; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -int main(int argc, char *argv[]) -{ - argList::noParallel(); - argList::validArgs.clear(); - - argList::validArgs.append("input surface file"); - argList::validArgs.append("output surface file"); - argList::validArgs.append("subset file name"); - argList args(argc, argv); - - fileName inFileName(args.args()[1]); - fileName outFileName(args.args()[2]); - fileName subsetFileName(args.args()[3]); - - if( inFileName.ext() != "flma" ) - { - Info << "Cannot convert this mesh" << endl; - return 0; - } - - label counter; - - IFstream inFile(inFileName); - - inFile >> counter; - - //- read vertices - pointField points(counter); - for(label pointI=0;pointI<counter;++pointI) - { - point p; - inFile >> p.x(); - inFile >> p.y(); - inFile >> p.z(); - - points[pointI] = p; - } - - //- read facets - inFile >> counter; - triFaceList triangles(counter); - forAll(triangles, triI) - { - inFile >> counter; - - if( counter != 3 ) - { - Info << "Facet " << triI << " is not a triangle!!" << endl; - Warning << "Cannot convert this surface!" << endl; - return 0; - } - - for(label j=0;j<3;++j) - inFile >> triangles[triI][2-j]; - } - - triSurface ts(triangles, points); - ts.write(outFileName); - - //- read cell types - inFile >> counter; - forAll(triangles, triI) - inFile >> counter; - - //- start reading selections - std::map<word, labelListPMG> subsets; - inFile >> counter; - for(label selI=0;selI<counter;++selI) - { - //- read selection name - word selName; - inFile >> selName; - - //- read selection type - label selType; - inFile >> selType; - - //- read selection entries - label size; - inFile >> size; - labelListPMG entries(size); - for(label i=0;i<size;++i) - inFile >> entries[i]; - - //- store cell selections - if( selType == 2 ) - { - Info << "Adding subset " << selName << endl; - subsets.insert(std::pair<word, labelListPMG>(selName, entries)); - } - } - - OFstream outFile(subsetFileName); - - std::map<word, labelListPMG>::const_iterator iter; - counter = 0; - for(iter=subsets.begin();iter!=subsets.end();++iter) - ++counter; - - outFile << counter << nl; - for(iter=subsets.begin();iter!=subsets.end();++iter) - { - outFile << iter->first << nl; - outFile << iter->second << nl; - } - -/* for(iter=subsets.begin();iter!=subsets.end();++iter) - { - labelList faceMap, pointMap; - boolList useTri(triangles.size(), false); - - const word& sName = iter->first; - const labelListPMG& elmts = iter->second; - - forAll(elmts, elI) - useTri[elmts[elI]] = true; - - faceMap.setSize(elmts.size()); - pointMap.setSize(elmts.size()); - - triSurface subSurface = ts.subsetMesh(useTri, pointMap, faceMap); - - subSurface.write(sName+".stl"); - } -*/ - Info << "End\n" << endl; - return 0; -} - -// ************************************************************************* // +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + Reads the AVL's surface mesh + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "Time.H" +#include "triSurf.H" +#include "triSurfModifier.H" +#include "triFaceList.H" +#include "labelLongList.H" +#include "IFstream.H" + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +int main(int argc, char *argv[]) +{ + argList::noParallel(); + argList::validArgs.clear(); + + argList::validArgs.append("input surface file"); + argList::validArgs.append("output surface file"); + argList args(argc, argv); + + fileName inFileName(args.args()[1]); + fileName outFileName(args.args()[2]); + + if( inFileName.ext() != "flma" ) + { + Info << "Cannot convert this mesh" << endl; + return 0; + } + + //- create the surface mesh + triSurf ts; + triSurfModifier tsm(ts); + + label counter; + + IFstream inFile(inFileName); + + inFile >> counter; + + //- read vertices + pointField& points = tsm.pointsAccess(); + points.setSize(counter); + forAll(points, pointI) + { + point& p = points[pointI]; + + inFile >> p.x(); + inFile >> p.y(); + inFile >> p.z(); + } + + //- read facets + inFile >> counter; + geometricSurfacePatchList patches(1); + patches[0].name() = "patch"; + LongList<labelledTri>& triangles = tsm.facetsAccess(); + triangles.setSize(counter); + forAll(triangles, triI) + { + inFile >> counter; + + if( counter != 3 ) + { + Info << "Facet " << triI << " is not a triangle!!" << endl; + Warning << "Cannot convert this surface!" << endl; + return 0; + } + + for(label j=0;j<3;++j) + inFile >> triangles[triI][2-j]; + + triangles[triI].region() = 0; + } + + //- read cell types + inFile >> counter; + forAll(triangles, triI) + inFile >> counter; + + //- start reading selections + inFile >> counter; + for(label selI=0;selI<counter;++selI) + { + //- read selection name + word selName; + inFile >> selName; + + //- read selection type + label selType; + inFile >> selType; + + //- read selection entries + label size; + inFile >> size; + labelLongList entries(size); + for(label i=0;i<size;++i) + inFile >> entries[i]; + + //- store cell selections + if( selType == 2 ) + { + Info << "Adding subset " << selName << endl; + const label setID = ts.addFacetSubset(selName); + + forAll(entries, i) + ts.addFacetToSubset(setID, entries[i]); + } + } + + //- write the surface + ts.writeSurface(outFileName); + + Info << "End\n" << endl; + return 0; +} + +// ************************************************************************* // diff --git a/utilities/FLMAToSurface/Make/options b/utilities/FLMAToSurface/Make/options index 7ae7395c2e1efecaf6620499a181c68fa07f0253..612aeaf2b2df08824ed96dffdb088a47b413ec2f 100644 --- a/utilities/FLMAToSurface/Make/options +++ b/utilities/FLMAToSurface/Make/options @@ -3,4 +3,7 @@ EXE_INC = \ -I$(FOAM_SRC)/triSurface/lnInclude EXE_LIBS = \ - -ltriSurface -lMeshLibrary -lmeshTools + -ltriSurface \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/FPMAToMesh/FPMAToMesh.C b/utilities/FPMAToMesh/FPMAToMesh.C index 4acd3d6bfa18e9666e744e28b188c4eeeedfa9cf..b072c6e9f83534638e4b7adfff0ce6699e43614a 100644 --- a/utilities/FPMAToMesh/FPMAToMesh.C +++ b/utilities/FPMAToMesh/FPMAToMesh.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Writes the mesh in fpma format readable by AVL's CfdWM + Writes the mesh in fpma format readable by AVL's CfdWM \*---------------------------------------------------------------------------*/ @@ -64,12 +63,12 @@ int main(int argc, char *argv[]) points.setSize(counter); forAll(points, pointI) { - point p; - file >> p.x(); - file >> p.y(); - file >> p.z(); - - points[pointI] = p; + point p; + file >> p.x(); + file >> p.y(); + file >> p.z(); + + points[pointI] = p; } //- read the number of faces @@ -82,14 +81,14 @@ int main(int argc, char *argv[]) forAll(faces, faceI) { file >> counter; - - face f; - f.setSize(counter); - - forAll(f, pI) - file >> f[pI]; - - faces[faceI] = f.reverseFace(); + + face f; + f.setSize(counter); + + forAll(f, pI) + file >> f[pI]; + + faces[faceI] = f.reverseFace(); } //- read the number of cells @@ -101,14 +100,14 @@ int main(int argc, char *argv[]) forAll(cells, cellI) { - file >> counter; - - cell& c = cells[cellI]; - - c.setSize(counter); - - forAll(c, fI) - file >> c[fI]; + file >> counter; + + cell& c = cells[cellI]; + + c.setSize(counter); + + forAll(c, fI) + file >> c[fI]; } //- read selections @@ -119,66 +118,66 @@ int main(int argc, char *argv[]) for(label setI=0;setI<counter;++setI) { - word sName; - file >> sName; - - label type; - file >> type; - - label nEntries; - file >> nEntries; - - switch( type ) - { - case 3: - { - //- face selection - const label id = pmg.addFaceSubset(sName); - - patchNames.setSize(patchNames.size()+1); - patchNames[patchNames.size()-1] = sName; - subsetToPatch.insert(id, patchNames.size()-1); - - Info << "Reading face selection " << sName << endl; - - for(label i=0;i<nEntries;++i) - { - label entryI; - file >> entryI; - pmg.addFaceToSubset(id, entryI); - } - } break; - case 2: - { - //- cell selection - const label id = pmg.addCellSubset(sName); - - for(label i=0;i<nEntries;++i) - { - label entryI; - file >> entryI; - pmg.addCellToSubset(id, entryI); - } - } break; - case 1: - { - //- node selection - const label id = pmg.addPointSubset(sName); - - for(label i=0;i<nEntries;++i) - { - label entryI; - file >> entryI; - pmg.addPointToSubset(id, entryI); - } - } break; - }; + word sName; + file >> sName; + + label type; + file >> type; + + label nEntries; + file >> nEntries; + + switch( type ) + { + case 3: + { + //- face selection + const label id = pmg.addFaceSubset(sName); + + patchNames.setSize(patchNames.size()+1); + patchNames[patchNames.size()-1] = sName; + subsetToPatch.insert(id, patchNames.size()-1); + + Info << "Reading face selection " << sName << endl; + + for(label i=0;i<nEntries;++i) + { + label entryI; + file >> entryI; + pmg.addFaceToSubset(id, entryI); + } + } break; + case 2: + { + //- cell selection + const label id = pmg.addCellSubset(sName); + + for(label i=0;i<nEntries;++i) + { + label entryI; + file >> entryI; + pmg.addCellToSubset(id, entryI); + } + } break; + case 1: + { + //- node selection + const label id = pmg.addPointSubset(sName); + + for(label i=0;i<nEntries;++i) + { + label entryI; + file >> entryI; + pmg.addPointToSubset(id, entryI); + } + } break; + }; } //- create patches from face selections VRWGraph boundaryFaces; - labelListPMG boundaryOwner; - labelListPMG boundaryPatches; + labelLongList boundaryOwner; + labelLongList boundaryPatches; const labelList& owner = pmg.owner(); DynList<label> faceSubsets; @@ -186,26 +185,26 @@ int main(int argc, char *argv[]) forAll(faceSubsets, setI) { - labelListPMG setFaces; - pmg.facesInSubset(faceSubsets[setI], setFaces); - - forAll(setFaces, i) - { - boundaryFaces.appendList(faces[setFaces[i]]); - boundaryOwner.append(owner[setFaces[i]]); - boundaryPatches.append(subsetToPatch[faceSubsets[setI]]); - } - - pmg.removeFaceSubset(faceSubsets[setI]); + labelLongList setFaces; + pmg.facesInSubset(faceSubsets[setI], setFaces); + + forAll(setFaces, i) + { + boundaryFaces.appendList(faces[setFaces[i]]); + boundaryOwner.append(owner[setFaces[i]]); + boundaryPatches.append(subsetToPatch[faceSubsets[setI]]); + } + + pmg.removeFaceSubset(faceSubsets[setI]); } meshModifier.reorderBoundaryFaces(); meshModifier.replaceBoundary ( - patchNames, - boundaryFaces, - boundaryOwner, - boundaryPatches + patchNames, + boundaryFaces, + boundaryOwner, + boundaryPatches ); pmg.write(); diff --git a/utilities/FPMAToMesh/Make/options b/utilities/FPMAToMesh/Make/options index d357c996b28f7691493585779e251df887f1690d..e0ad8cce2ee975c0ede26fb45222e7d766557200 100644 --- a/utilities/FPMAToMesh/Make/options +++ b/utilities/FPMAToMesh/Make/options @@ -1,5 +1,8 @@ -EXE_INC = -I../../meshLibrary/lnInclude \ - -I$(LIB_SRC)/meshTools/lnInclude +EXE_INC = \ + -I../../meshLibrary/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude -EXE_LIBS = -lMeshLibrary \ - -lmeshTools +EXE_LIBS = \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/cellSetIntersectedByPlane/Make/files b/utilities/cellSetIntersectedByPlane/Make/files index 6e0e7ee3c43255a4d93f5e821ddc549bae5a8fef..f9f4eb21f0e2519f871e76cfd090915e7662fa7c 100644 --- a/utilities/cellSetIntersectedByPlane/Make/files +++ b/utilities/cellSetIntersectedByPlane/Make/files @@ -1,4 +1,4 @@ cellSetIntersectedByPlane.C -EXE = $(FOAM_USER_APPBIN)/cellSetIntersectedByPlane +EXE = $(FOAM_APPBIN)/cellSetIntersectedByPlane diff --git a/utilities/cellSetIntersectedByPlane/Make/options b/utilities/cellSetIntersectedByPlane/Make/options index 7a0df88846531acc83b5cd3508b45f95eb0aed34..5070bb3a4868fad685c168b92cbffc3d06ac7e12 100644 --- a/utilities/cellSetIntersectedByPlane/Make/options +++ b/utilities/cellSetIntersectedByPlane/Make/options @@ -1,2 +1,11 @@ -EXE_INC = -I$(LIB_SRC)/finiteVolume/lnInclude -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I$(FOAM_USER_LIB)/meshGeneration/meshLibrary/lnInclude -EXE_LIBS = -lMeshLibrary -ltriSurface -lfiniteVolume -lmeshTools +EXE_INC = \ + -I$(LIB_SRC)/finiteVolume/lnInclude \ + -I$(LIB_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude \ + -I$(FOAM_USER_LIB)/meshGeneration/meshLibrary/lnInclude + +EXE_LIBS = \ + -lmeshLibrary \ + -ltriSurface \ + -lfiniteVolume \ + -lmeshTools diff --git a/utilities/cellSetIntersectedByPlane/cellSetIntersectedByPlane.C b/utilities/cellSetIntersectedByPlane/cellSetIntersectedByPlane.C index b5d6ff659613bb98730d915a9ed46ee765dd59df..f2bf44e974abcbf0792ea09165b65b6cad104762 100644 --- a/utilities/cellSetIntersectedByPlane/cellSetIntersectedByPlane.C +++ b/utilities/cellSetIntersectedByPlane/cellSetIntersectedByPlane.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Application Prints topology of cells in a given cell set @@ -45,78 +44,78 @@ using namespace Foam; int main(int argc, char *argv[]) { //argList::validArgs.append("cellSet"); - + # include "setRootCase.H" # include "createTime.H" - - Info<< "Reading mesh for time = " << runTime.value() << endl; - polyMesh mesh(runTime); - - cellSet cs - ( - IOobject - ( - "c0", - runTime.timeName(), - "polyMesh/sets", - runTime, - IOobject::NO_READ - ) - ); - - vector n, origin; - Info << "Normal x coord" ; - cin >> n.x(); - Info << endl << "Normal y coord "; - cin >> n.y(); - Info << endl << "Normal z coord"; - cin >> n.z(); - - Info << "Origin x coord" ; - cin >> origin.x(); - Info << endl << "Origin y coord "; - cin >> origin.y(); - Info << endl << "Origin z coord"; - cin >> origin.z(); + + Info<< "Reading mesh for time = " << runTime.value() << endl; + polyMesh mesh(runTime); + + cellSet cs + ( + IOobject + ( + "c0", + runTime.timeName(), + "polyMesh/sets", + runTime, + IOobject::NO_READ + ) + ); + + vector n, origin; + Info << "Normal x coord" ; + cin >> n.x(); + Info << endl << "Normal y coord "; + cin >> n.y(); + Info << endl << "Normal z coord"; + cin >> n.z(); + + Info << "Origin x coord" ; + cin >> origin.x(); + Info << endl << "Origin y coord "; + cin >> origin.y(); + Info << endl << "Origin z coord"; + cin >> origin.z(); //Info<< "Reading cell set from " << setName << endl << endl; - //cellSet cs(mesh, setName); - - //- printCells contained in the cellSet - const pointField& points = mesh.points(); - const edgeList& edges = mesh.edges(); - const labelListList& edgeCells = mesh.edgeCells(); - - forAll(edges, eI) - { - const edge& e = edges[eI]; - bool visibleS, visibleE; - if( ((points[e.start()] - origin) & n) >= 0.0 ) - { - visibleS = true; - } - else - { - visibleS = false; - } - - if( ((points[e.end()] - origin) & n) >= 0.0 ) - { - visibleE = true; - } - else - { - visibleE = false; - } - - if( visibleS ^ visibleE ) - { - forAll(edgeCells[eI], ecI) - cs.insert(edgeCells[eI][ecI]); - } - } - - cs.write(); + //cellSet cs(mesh, setName); + + //- printCells contained in the cellSet + const pointField& points = mesh.points(); + const edgeList& edges = mesh.edges(); + const labelListList& edgeCells = mesh.edgeCells(); + + forAll(edges, eI) + { + const edge& e = edges[eI]; + bool visibleS, visibleE; + if( ((points[e.start()] - origin) & n) >= 0.0 ) + { + visibleS = true; + } + else + { + visibleS = false; + } + + if( ((points[e.end()] - origin) & n) >= 0.0 ) + { + visibleE = true; + } + else + { + visibleE = false; + } + + if( visibleS ^ visibleE ) + { + forAll(edgeCells[eI], ecI) + cs.insert(edgeCells[eI][ecI]); + } + } + + cs.write(); Info << "End\n" << endl; return 0; diff --git a/utilities/copySurfaceParts/Make/files b/utilities/copySurfaceParts/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..a504ac4664354771e594025abccc6199e745a860 --- /dev/null +++ b/utilities/copySurfaceParts/Make/files @@ -0,0 +1,3 @@ +copySurfaceParts.C + +EXE = $(FOAM_USER_APPBIN)/copySurfaceParts diff --git a/utilities/copySurfaceParts/Make/options b/utilities/copySurfaceParts/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..ab3de10c7030c93790a4db67abb80f5bb77efb30 --- /dev/null +++ b/utilities/copySurfaceParts/Make/options @@ -0,0 +1,10 @@ +EXE_INC = \ + -I../../meshLibrary/lnInclude \ + -I$(LIB_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude + +EXE_LIBS = \ + -ltriSurface \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/copySurfaceParts/copySurfaceParts.C b/utilities/copySurfaceParts/copySurfaceParts.C new file mode 100644 index 0000000000000000000000000000000000000000..9eeec2ed776b52da18b9b141775c25d7b5f58d98 --- /dev/null +++ b/utilities/copySurfaceParts/copySurfaceParts.C @@ -0,0 +1,80 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + Finds feature edges and corners of a triangulated surface + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "IFstream.H" +#include "fileName.H" +#include "triSurf.H" +#include "demandDrivenData.H" + +#include "triSurfaceCopyParts.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // +// Main program: +using namespace Foam; + +int main(int argc, char *argv[]) +{ + argList::noParallel(); + argList::validArgs.clear(); + argList::validArgs.append("input surface file"); + argList::validArgs.append("output surface file"); + argList::validArgs.append("patch/subset name"); + argList args(argc, argv); + + const fileName inFileName(args.args()[1]); + const fileName outFileName(args.args()[2]); + + if( outFileName == inFileName ) + { + FatalErrorIn(args.executable()) + << "Output file " << outFileName + << " would overwrite the input file." + << exit(FatalError); + } + + wordList patches(1); + patches[0] = args.args()[3]; + + triSurf originalSurface(inFileName); + + triSurfaceCopyParts copyPart(originalSurface); + + triSurf copy; + + copyPart.copySurface(patches, copy); + + copy.writeSurface(outFileName); + + Info << "End\n" << endl; + + return 0; +} + + +// ************************************************************************* // diff --git a/utilities/extrudeEdgesInto2DSurface/Make/files b/utilities/extrudeEdgesInto2DSurface/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..1234dbed0b51c638a44bb2c4afd05a166cfd13ec --- /dev/null +++ b/utilities/extrudeEdgesInto2DSurface/Make/files @@ -0,0 +1,3 @@ +extrudeEdgesInto2DSurface.C + +EXE = $(FOAM_USER_APPBIN)/extrudeEdgesInto2DSurface diff --git a/utilities/extrudeEdgesInto2DSurface/Make/options b/utilities/extrudeEdgesInto2DSurface/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..221fe612d3dc18e1108857e121b8f4b3b2707e45 --- /dev/null +++ b/utilities/extrudeEdgesInto2DSurface/Make/options @@ -0,0 +1,10 @@ +EXE_INC = \ + -I../../meshLibrary/lnInclude \ + -I$(FOAM_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude + +EXE_LIBS = \ + -ltriSurface \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/extrudeEdgesInto2DSurface/extrudeEdgesInto2DSurface.C b/utilities/extrudeEdgesInto2DSurface/extrudeEdgesInto2DSurface.C new file mode 100644 index 0000000000000000000000000000000000000000..0ff651237a55ff7866aa0d9aa1c7096379d7b5a6 --- /dev/null +++ b/utilities/extrudeEdgesInto2DSurface/extrudeEdgesInto2DSurface.C @@ -0,0 +1,74 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + Reads the surface mesh, remove the selected facets + and writes the modified mesh into a new file + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "Time.H" +#include "triSurf.H" +#include "triSurfaceExtrude2DEdges.H" +#include "demandDrivenData.H" + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +int main(int argc, char *argv[]) +{ + argList::noParallel(); + argList::validArgs.clear(); + + argList::validArgs.append("input surface file"); + argList::validArgs.append("output surface file"); + + argList args(argc, argv); + + fileName inFileName(args.args()[1]); + fileName outFileName(args.args()[2]); + + //- read the input surface + triSurf origSurf(inFileName); + + //- remove the selected facets + triSurfaceExtrude2DEdges extruder(origSurf); + + const triSurf* newSurfacePtr = extruder.extrudeSurface(); + + if( !newSurfacePtr ) + FatalError << "Extruding of the edge mesh failed!" << exit(FatalError); + + //- write the modified surface mesh + newSurfacePtr->writeSurface(outFileName); + + deleteDemandDrivenData(newSurfacePtr); + + Info << "End\n" << endl; + + return 0; +} + +// ************************************************************************* // diff --git a/utilities/meshToFPMA/Make/options b/utilities/meshToFPMA/Make/options index d357c996b28f7691493585779e251df887f1690d..e0ad8cce2ee975c0ede26fb45222e7d766557200 100644 --- a/utilities/meshToFPMA/Make/options +++ b/utilities/meshToFPMA/Make/options @@ -1,5 +1,8 @@ -EXE_INC = -I../../meshLibrary/lnInclude \ - -I$(LIB_SRC)/meshTools/lnInclude +EXE_INC = \ + -I../../meshLibrary/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude -EXE_LIBS = -lMeshLibrary \ - -lmeshTools +EXE_LIBS = \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/meshToFPMA/meshToFPMA.C b/utilities/meshToFPMA/meshToFPMA.C index 583188be683fcf5d1c2a761d6096d553604640af..0a69f40db544ad50d3868783eb6608dd72eb6d38 100644 --- a/utilities/meshToFPMA/meshToFPMA.C +++ b/utilities/meshToFPMA/meshToFPMA.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Writes the mesh in fpma format readable by AVL's CfdWM + Writes the mesh in fpma format readable by AVL's CfdWM \*---------------------------------------------------------------------------*/ @@ -41,7 +40,7 @@ int main(int argc, char *argv[]) # include "setRootCase.H" # include "createTime.H" - polyMeshGen pmg(runTime); + polyMeshGen pmg(runTime); pmg.read(); if( Pstream::parRun() ) @@ -49,9 +48,9 @@ int main(int argc, char *argv[]) polyMeshGenModifier(pmg).addBufferCells(); createFIRESelections(pmg); } - - writeMeshFPMA(pmg, "convertedMesh"); - + + writeMeshFPMA(pmg, "convertedMesh"); + Info << "End\n" << endl; return 0; } diff --git a/utilities/patchesToSubsets/Make/options b/utilities/patchesToSubsets/Make/options index fc3c4db1c5a81af7ca7dbdd1bd4d112673bec230..221fe612d3dc18e1108857e121b8f4b3b2707e45 100644 --- a/utilities/patchesToSubsets/Make/options +++ b/utilities/patchesToSubsets/Make/options @@ -4,4 +4,7 @@ EXE_INC = \ -I$(LIB_SRC)/meshTools/lnInclude EXE_LIBS = \ - -ltriSurface -lMeshLibrary -lmeshTools + -ltriSurface \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/patchesToSubsets/patchesToSubsets.C b/utilities/patchesToSubsets/patchesToSubsets.C index cb514fa362e887d01c7ae8f055fbee26df3b5292..2fd58a322ffa616a11b9b8595a9efb36c831229c 100644 --- a/utilities/patchesToSubsets/patchesToSubsets.C +++ b/utilities/patchesToSubsets/patchesToSubsets.C @@ -1,80 +1,84 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - Reads the AVL's surface mesh - -\*---------------------------------------------------------------------------*/ - -#include "argList.H" -#include "Time.H" -#include "objectRegistry.H" -#include "triSurf.H" -#include "triFaceList.H" -#include "labelListPMG.H" -#include "IFstream.H" -#include "OFstream.H" - -using namespace Foam; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -int main(int argc, char *argv[]) -{ - argList::noParallel(); - argList::validArgs.clear(); - - argList::validArgs.append("input surface file"); - argList::validArgs.append("output subset file"); - argList args(argc, argv); - - fileName inFileName(args.args()[1]); - fileName subsetFileName(args.args()[2]); - - triSurf origSurf(inFileName); - - wordList patchNames(origSurf.patches().size()); - forAll(origSurf.patches(), patchI) - patchNames[patchI] = origSurf.patches()[patchI].name(); - - forAll(patchNames, patchI) - { - labelListPMG subsetFacets; - forAll(origSurf, triI) - { - if( origSurf[triI].region() == patchI ) - subsetFacets.append(triI); - } - - origSurf.addFacetsToSubset(patchNames[patchI], subsetFacets); - } - - origSurf.writeFaceSubsets(subsetFileName); - - Info << "End\n" << endl; - - return 0; -} - -// ************************************************************************* // +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + Reads the AVL's surface mesh + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "Time.H" +#include "triSurf.H" +#include "triFaceList.H" +#include "labelLongList.H" +#include "IFstream.H" +#include "OFstream.H" + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +int main(int argc, char *argv[]) +{ + argList::noParallel(); + argList::validArgs.clear(); + + argList::validArgs.append("input surface file"); + argList::validArgs.append("output surface file"); + argList args(argc, argv); + + fileName inFileName(args.args()[1]); + fileName outFileName(args.args()[2]); + + if( outFileName.ext() != "fms" ) + Warning << "The subsets cann only be saved in the .fms format" << endl; + + triSurf origSurf(inFileName); + + wordList patchNames(origSurf.patches().size()); + forAll(origSurf.patches(), patchI) + patchNames[patchI] = origSurf.patches()[patchI].name(); + + forAll(patchNames, patchI) + { + labelLongList subsetFacets; + forAll(origSurf, triI) + { + if( origSurf[triI].region() == patchI ) + subsetFacets.append(triI); + } + + const label subsetId = origSurf.addFacetSubset(patchNames[patchI]); + + forAll(subsetFacets, i) + origSurf.addFacetToSubset(subsetId, subsetFacets[i]); + } + + origSurf.writeSurface(outFileName); + + Info << "End\n" << endl; + + return 0; +} + +// ************************************************************************* // diff --git a/utilities/plyToSurface/Make/files b/utilities/plyToSurface/Make/files index a7cf93ed464f38cf75a5dafa14e5969687b6e71d..6bd1ecfa2b254ffb5873e5a8c70e96e2954becf1 100644 --- a/utilities/plyToSurface/Make/files +++ b/utilities/plyToSurface/Make/files @@ -1,3 +1,3 @@ plyToSurface.C -EXE = $(FOAM_USER_APPBIN)/plyToSurface +EXE = $(FOAM_APPBIN)/plyToSurface diff --git a/utilities/plyToSurface/Make/options b/utilities/plyToSurface/Make/options index 7e13b02670b729547c096c549c9604dfc4210e3f..c48855f90f5c629a09249c9e739f5525780a3f31 100644 --- a/utilities/plyToSurface/Make/options +++ b/utilities/plyToSurface/Make/options @@ -1,5 +1,5 @@ EXE_INC = -I$(FOAM_USER_LIB)/pMesh3D/pMeshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude + -I$(LIB_SRC)/triSurface/lnInclude -EXE_LIBS = -ltriSurface -lmeshTools -lMeshLibrary +EXE_LIBS = -ltriSurface -lmeshTools -lmeshLibrary diff --git a/utilities/plyToSurface/plyToSurface.C b/utilities/plyToSurface/plyToSurface.C index b4c6ac3675218d7c5619b4e03a6dccaf866e43e4..ef83f84224b41832f036f2ed2024265df5e5c57c 100644 --- a/utilities/plyToSurface/plyToSurface.C +++ b/utilities/plyToSurface/plyToSurface.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Converts STAR CD surfaces into stl or other formats + Converts STAR CD surfaces into stl or other formats \*---------------------------------------------------------------------------*/ @@ -61,56 +60,56 @@ int main(int argc, char *argv[]) } IFstream surfFile(inFileName); - - //- parse the number of vertices - token t; - do - { - surfFile >> t; - } while( !t.isLabel() ); - pointField points(t.labelToken()); - Info << "Surface has " << points.size() << " points" << endl; - - //- find the number of elements - do - { - surfFile >> t; - } while( !t.isLabel() ); + + //- parse the number of vertices + token t; + do + { + surfFile >> t; + } while( !t.isLabel() ); + pointField points(t.labelToken()); + Info << "Surface has " << points.size() << " points" << endl; + + //- find the number of elements + do + { + surfFile >> t; + } while( !t.isLabel() ); List<labelledTri> triFaces(t.labelToken()); - Info << "Surface has " << triFaces.size() << " facets" << endl; - - //- read vertices - do - { - surfFile >> t; - } while( t.isWord() && (t.wordToken() != "end_header") ); - - forAll(points, pointI) - { - point& p = points[pointI]; - - surfFile >> p.x(); - surfFile >> p.y(); - surfFile >> p.z(); - } - - //- read triangles - forAll(triFaces, triI) - { - label nPts; - surfFile >> nPts; - if( nPts != 3 ) - { - Info << "Facet " << triI << " is not a triangle!!" << endl; - Warning << "Cannot convert this surface!" << endl; - return 0; - } - - for(label i=0;i<nPts;++i) - surfFile >> triFaces[triI][i]; - - triFaces[triI].region() = 0; - } + Info << "Surface has " << triFaces.size() << " facets" << endl; + + //- read vertices + do + { + surfFile >> t; + } while( t.isWord() && (t.wordToken() != "end_header") ); + + forAll(points, pointI) + { + point& p = points[pointI]; + + surfFile >> p.x(); + surfFile >> p.y(); + surfFile >> p.z(); + } + + //- read triangles + forAll(triFaces, triI) + { + label nPts; + surfFile >> nPts; + if( nPts != 3 ) + { + Info << "Facet " << triI << " is not a triangle!!" << endl; + Warning << "Cannot convert this surface!" << endl; + return 0; + } + + for(label i=0;i<nPts;++i) + surfFile >> triFaces[triI][i]; + + triFaces[triI].region() = 0; + } triSurface surf(triFaces, points); diff --git a/utilities/preparePar/Make/options b/utilities/preparePar/Make/options index ed06409344964a1a108bf4a6c4f22e1fdad0891f..6127fa06587ca85913b46773b11d7b61017d9199 100644 --- a/utilities/preparePar/Make/options +++ b/utilities/preparePar/Make/options @@ -4,4 +4,7 @@ EXE_INC = \ -I$(FOAM_SRC)/triSurface/lnInclude EXE_LIBS = \ - -ltriSurface -lmeshTools -lMeshLibrary + -ltriSurface \ + -lmeshTools \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary diff --git a/utilities/preparePar/preparePar.C b/utilities/preparePar/preparePar.C index 25510e46f096701e2873009275ac8ff59f04a5dc..d80f1fc4f66a4cc2e00ffc6d4e6d942a03374237 100644 --- a/utilities/preparePar/preparePar.C +++ b/utilities/preparePar/preparePar.C @@ -1,101 +1,100 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Application - Prepares the case for a parallel mesh generation run - -Description - - creates processor* directories which contain data for processors - -\*---------------------------------------------------------------------------*/ - -#include "argList.H" -#include "Time.H" -#include "objectRegistry.H" - -#include <sstream> - -using namespace Foam; - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // - -// Main program: - -int main(int argc, char *argv[]) -{ -# include "setRootCase.H" -# include "createTime.H" - - objectRegistry registry(runTime); - - IOdictionary meshDict - ( - IOobject - ( - "meshDict", - registry.time().system(), - registry, - IOobject::MUST_READ, - IOobject::NO_WRITE - ) - ); - - IOdictionary decomposeParDict - ( - IOobject - ( - "decomposeParDict", - registry.time().system(), - registry, - IOobject::MUST_READ, - IOobject::NO_WRITE - ) - ); - - const label nProcessors - ( - readLabel(decomposeParDict.lookup("numberOfSubdomains")) - ); - - for(label procI=0;procI<nProcessors;++procI) - { - fileName file("processor"); - std::ostringstream ss; - ss << procI; - file += ss.str(); - Info << "Creating " << file << endl; - - //- create a directory for processor data - mkDir(runTime.path()/file); - - //- copy the contents of the const directory into processor* - cp(registry.path()/"constant", runTime.path()/file); - } - - Info << "End\n" << endl; - return 0; -} - - -// ************************************************************************* // +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Application + Prepares the case for a parallel mesh generation run + +Description + - creates processor* directories which contain data for processors + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "Time.H" + +#include <sstream> + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +// Main program: + +int main(int argc, char *argv[]) +{ +# include "setRootCase.H" +# include "createTime.H" + + IOdictionary meshDict + ( + IOobject + ( + "meshDict", + runTime.system(), + runTime, + IOobject::MUST_READ, + IOobject::NO_WRITE + ) + ); + + IOdictionary decomposeParDict + ( + IOobject + ( + "decomposeParDict", + runTime.system(), + runTime, + IOobject::MUST_READ, + IOobject::NO_WRITE + ) + ); + + const label nProcessors + ( + readLabel(decomposeParDict.lookup("numberOfSubdomains")) + ); + + for(label procI=0;procI<nProcessors;++procI) + { + fileName file("processor"); + std::ostringstream ss; + ss << procI; + file += ss.str(); + Info << "Creating " << file << endl; + + //- create a directory for processor data + mkDir(runTime.path()/file); + + //- copy the contents of the const directory into processor* + cp(runTime.path()/"constant", runTime.path()/file); + + //- generate 0 directories for + mkDir(runTime.path()/file/"0"); + } + + Info << "End\n" << endl; + return 0; +} + + +// ************************************************************************* // diff --git a/utilities/printCellsInSet/Make/files b/utilities/printCellsInSet/Make/files index 0fd5ad16e666c27f8682ffc71627610dde170cf9..3ad226d3361ba1f9b989fbb54390b91b1d4f4752 100644 --- a/utilities/printCellsInSet/Make/files +++ b/utilities/printCellsInSet/Make/files @@ -1,4 +1,4 @@ printCellsInSet.C -EXE = $(FOAM_USER_APPBIN)/printCellsInSet +EXE = $(FOAM_APPBIN)/printCellsInSet diff --git a/utilities/printCellsInSet/Make/options b/utilities/printCellsInSet/Make/options index 7a0df88846531acc83b5cd3508b45f95eb0aed34..1a817013e4d7793ea329504dfb024da31159498a 100644 --- a/utilities/printCellsInSet/Make/options +++ b/utilities/printCellsInSet/Make/options @@ -1,2 +1,7 @@ -EXE_INC = -I$(LIB_SRC)/finiteVolume/lnInclude -I$(LIB_SRC)/triSurface/lnInclude -I$(LIB_SRC)/meshTools/lnInclude -I$(FOAM_USER_LIB)/meshGeneration/meshLibrary/lnInclude -EXE_LIBS = -lMeshLibrary -ltriSurface -lfiniteVolume -lmeshTools +EXE_INC = \ + -I$(LIB_SRC)/finiteVolume/lnInclude \ + -I$(LIB_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude \ + -I$(FOAM_USER_LIB)/meshGeneration/meshLibrary/lnInclude + +EXE_LIBS = -lmeshLibrary -ltriSurface -lfiniteVolume -lmeshTools diff --git a/utilities/printCellsInSet/printCellsInSet.C b/utilities/printCellsInSet/printCellsInSet.C index 951fad65cd18daf536562a2ee9aa5c5e5b724431..84bf72edd42850de6e7f02be8b827174e4aa5d0d 100644 --- a/utilities/printCellsInSet/printCellsInSet.C +++ b/utilities/printCellsInSet/printCellsInSet.C @@ -1,26 +1,25 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Application Prints topology of cells in a given cell set @@ -45,33 +44,33 @@ using namespace Foam; int main(int argc, char *argv[]) { argList::validArgs.append("cellSet"); - + # include "setRootCase.H" # include "createTime.H" - - Info<< "Reading mesh for time = " << runTime.value() << endl; - polyMesh mesh(runTime); + + Info<< "Reading mesh for time = " << runTime.value() << endl; + polyMesh mesh(runTime); word setName(args.args()[3]); Info<< "Reading cell set from " << setName << endl << endl; - cellSet cs(mesh, setName); - - //- printCells contained in the cellSet - const cellList& cells = mesh.cells(); - const faceList& faces = mesh.faces(); - - forAll(cells, cellI) - if( cs.found(cellI) ) - { - const cell& c = cells[cellI]; - Info << "Cell " << cellI << " consists of faces " << c << endl; - - forAll(c, fI) - Info << "Face " << c[fI] << " is " << faces[c[fI]] << endl; - - Info << nl << endl; - } + cellSet cs(mesh, setName); + + //- printCells contained in the cellSet + const cellList& cells = mesh.cells(); + const faceList& faces = mesh.faces(); + + forAll(cells, cellI) + if( cs.found(cellI) ) + { + const cell& c = cells[cellI]; + Info << "Cell " << cellI << " consists of faces " << c << endl; + + forAll(c, fI) + Info << "Face " << c[fI] << " is " << faces[c[fI]] << endl; + + Info << nl << endl; + } Info << "End\n" << endl; return 0; diff --git a/utilities/removeSurfaceFacets/Make/files b/utilities/removeSurfaceFacets/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..7d73577bf92a58baf1d36aa5d9152dc29884b35d --- /dev/null +++ b/utilities/removeSurfaceFacets/Make/files @@ -0,0 +1,3 @@ +removeSurfaceFacets.C + +EXE = $(FOAM_USER_APPBIN)/removeSurfaceFacets diff --git a/utilities/removeSurfaceFacets/Make/options b/utilities/removeSurfaceFacets/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..221fe612d3dc18e1108857e121b8f4b3b2707e45 --- /dev/null +++ b/utilities/removeSurfaceFacets/Make/options @@ -0,0 +1,10 @@ +EXE_INC = \ + -I../../meshLibrary/lnInclude \ + -I$(FOAM_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude + +EXE_LIBS = \ + -ltriSurface \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/removeSurfaceFacets/removeSurfaceFacets.C b/utilities/removeSurfaceFacets/removeSurfaceFacets.C new file mode 100644 index 0000000000000000000000000000000000000000..8fae8f439bf920bd10fc7901f0ecf46e9ab6ec03 --- /dev/null +++ b/utilities/removeSurfaceFacets/removeSurfaceFacets.C @@ -0,0 +1,72 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | cfMesh: A library for mesh generation + \\ / O peration | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. +------------------------------------------------------------------------------- +License + This file is part of cfMesh. + + cfMesh is free software; you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by the + Free Software Foundation; either version 3 of the License, or (at your + option) any later version. + + cfMesh is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. + +Description + Reads the surface mesh, remove the selected facets + and writes the modified mesh into a new file + +\*---------------------------------------------------------------------------*/ + +#include "argList.H" +#include "Time.H" +#include "triSurf.H" +#include "triSurfaceRemoveFacets.H" + +using namespace Foam; + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +int main(int argc, char *argv[]) +{ + argList::noParallel(); + argList::validArgs.clear(); + + argList::validArgs.append("input surface file"); + argList::validArgs.append("output surface file"); + argList::validArgs.append("Subset/patch name"); + + argList args(argc, argv); + + fileName inFileName(args.args()[1]); + fileName outFileName(args.args()[2]); + word patchName(args.args()[3]); + + //- read the input surface + triSurf origSurf(inFileName); + + //- remove the selected facets + triSurfaceRemoveFacets rsf(origSurf); + + rsf.selectFacetsInPatch(patchName); + + rsf.removeFacets(); + + //- write the modified surface mesh + origSurf.writeSurface(outFileName); + + Info << "End\n" << endl; + + return 0; +} + +// ************************************************************************* // diff --git a/utilities/starSurfaceToSTL/Make/files b/utilities/starSurfaceToSTL/Make/files index 47e992c1d65cdffa8313e222f7981acd19213350..f1dc3fd088d02c82eb38e5e5815b90f5a336584a 100644 --- a/utilities/starSurfaceToSTL/Make/files +++ b/utilities/starSurfaceToSTL/Make/files @@ -1,3 +1,3 @@ starSurfaceToSTL.C -EXE = $(FOAM_USER_APPBIN)/starSurfaceToSTL +EXE = $(FOAM_APPBIN)/starSurfaceToSTL diff --git a/utilities/starSurfaceToSTL/Make/options b/utilities/starSurfaceToSTL/Make/options index 7e13b02670b729547c096c549c9604dfc4210e3f..c48855f90f5c629a09249c9e739f5525780a3f31 100644 --- a/utilities/starSurfaceToSTL/Make/options +++ b/utilities/starSurfaceToSTL/Make/options @@ -1,5 +1,5 @@ EXE_INC = -I$(FOAM_USER_LIB)/pMesh3D/pMeshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude + -I$(LIB_SRC)/triSurface/lnInclude -EXE_LIBS = -ltriSurface -lmeshTools -lMeshLibrary +EXE_LIBS = -ltriSurface -lmeshTools -lmeshLibrary diff --git a/utilities/starSurfaceToSTL/starSurfaceToSTL.C b/utilities/starSurfaceToSTL/starSurfaceToSTL.C index 5f48a9fa46b4c7575f79e545273c6acf505ed09f..445b3889a125a3f888dd66bdd4df8289c58cbea4 100644 --- a/utilities/starSurfaceToSTL/starSurfaceToSTL.C +++ b/utilities/starSurfaceToSTL/starSurfaceToSTL.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Converts STAR CD surfaces into stl or other formats + Converts STAR CD surfaces into stl or other formats \*---------------------------------------------------------------------------*/ diff --git a/utilities/subsetToPatch/Make/options b/utilities/subsetToPatch/Make/options index ed06409344964a1a108bf4a6c4f22e1fdad0891f..6127fa06587ca85913b46773b11d7b61017d9199 100644 --- a/utilities/subsetToPatch/Make/options +++ b/utilities/subsetToPatch/Make/options @@ -4,4 +4,7 @@ EXE_INC = \ -I$(FOAM_SRC)/triSurface/lnInclude EXE_LIBS = \ - -ltriSurface -lmeshTools -lMeshLibrary + -ltriSurface \ + -lmeshTools \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary diff --git a/utilities/subsetToPatch/subsetToPatch.C b/utilities/subsetToPatch/subsetToPatch.C index ee2d3c7a76631184837117d14102d4bbae419a44..5e71f89cd12c067575a238bc0696dce4b948446c 100644 --- a/utilities/subsetToPatch/subsetToPatch.C +++ b/utilities/subsetToPatch/subsetToPatch.C @@ -1,41 +1,41 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Creates surface patches from surface subsets + Creates surface patches from surface subsets \*---------------------------------------------------------------------------*/ #include "argList.H" #include "Time.H" #include "triSurf.H" +#include "demandDrivenData.H" using namespace Foam; // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -triSurf* makePatchFromSubset +void makePatchFromSubset ( triSurf& origSurf, const DynList<word>& subsetNames @@ -46,37 +46,39 @@ triSurf* makePatchFromSubset ( origSurf.patches().size() + subsetNames.size() ); - + //- set names of the new patches forAll(origSurf.patches(), patchI) newPatches[patchI].name() = origSurf.patches()[patchI].name(); - + forAll(subsetNames, subsetI) newPatches[origSurf.patches().size()+subsetI].name() = subsetNames[subsetI]; - + //- create new triangles - List<labelledTri> newTriangles(origSurf.localFaces()); - + LongList<labelledTri> newTriangles(origSurf.facets()); + //- set patches for all triangles forAll(subsetNames, subsetI) { - const labelListPMG& subsetFaces = - origSurf.facesInSubset(subsetNames[subsetI]); - + const label subsetID = origSurf.facetSubsetIndex(subsetNames[subsetI]); + + labelLongList subsetFaces; + origSurf.facetsInSubset(subsetID, subsetFaces); + const label regionI = origSurf.patches().size() + subsetI; - + forAll(subsetFaces, fI) { newTriangles[subsetFaces[fI]].region() = regionI; } } - + //- remove patches with no elements labelList nTrianglesInPatch(newPatches.size(), 0); forAll(newTriangles, triI) ++nTrianglesInPatch[newTriangles[triI].region()]; - + Map<label> newPatchLabel; label counter(0); forAll(nTrianglesInPatch, patchI) @@ -84,7 +86,7 @@ triSurf* makePatchFromSubset if( nTrianglesInPatch[patchI] ) newPatchLabel.insert(patchI, counter++); } - + geometricSurfacePatchList copyPatches(counter); counter = 0; forAll(newPatches, patchI) @@ -95,39 +97,25 @@ triSurf* makePatchFromSubset newPatches[patchI].name(); } } - + newPatches = copyPatches; - + //- renumber the patches in the list of triangles forAll(newTriangles, triI) newTriangles[triI].region() = newPatchLabel[newTriangles[triI].region()]; - - //- copy subsets for the new surface - DynList<word> existingSubsets; - origSurf.existingFaceSubsets(existingSubsets); - - std::map<word, labelListPMG> newSubsets; - forAll(existingSubsets, sI) - newSubsets.insert - ( - std::pair<word, labelListPMG> - ( - existingSubsets[sI], - origSurf.facesInSubset(existingSubsets[sI]) - ) - ); - + //- delete subsets converted to patches forAll(subsetNames, subsetI) - newSubsets.erase(subsetNames[subsetI]); - - triSurf* newSurfPtr = - new triSurf(newTriangles, newPatches, origSurf.points(), newSubsets); - - return newSurfPtr; + { + const label subsetID = origSurf.facetSubsetIndex(subsetNames[subsetI]); + origSurf.removeFacetSubset(subsetID); + } + + //- update subsets + origSurf.updateFacetsSubsets(newPatchLabel); } - + int main(int argc, char *argv[]) { @@ -135,50 +123,46 @@ int main(int argc, char *argv[]) argList::validArgs.clear(); argList::validArgs.append("input surface file"); - argList::validArgs.append("subset file name"); argList::validArgs.append("subset"); argList args(argc, argv); fileName inFileName(args.args()[1]); - fileName subsetFileName(args.args()[2]); - word subsetName(args.args()[3]); - + word subsetName(args.args()[2]); + triSurf* origSurfPtr = new triSurf(inFileName); - origSurfPtr->readFaceSubsets(subsetFileName); - + DynList<word> subsetNames; - if( !origSurfPtr->doesFaceSubsetExist(subsetName) ) + const label subsetID = origSurfPtr->facetSubsetIndex(subsetName); + if( subsetID >= 0 ) { Warning << "Subset " << subsetName - << " checking subsets containing this string!" << endl; - DynList<word> existingSubsets; - origSurfPtr->existingFaceSubsets(existingSubsets); - + << " checking subsets containing this string!" << endl; + + DynList<label> existingSubsets; + origSurfPtr->facetSubsetIndices(existingSubsets); + forAll(existingSubsets, subsetI) { - if( - existingSubsets[subsetI].substr(0, subsetName.size()) == - subsetName - ) + const word sName = + origSurfPtr->facetSubsetName(existingSubsets[subsetI]); + + if( sName.substr(0, subsetName.size()) == subsetName ) { - subsetNames.append(existingSubsets[subsetI]); + subsetNames.append(sName); } } - + Info << "Converting " << subsetNames.size() << " subsets" << endl; } else { subsetNames.append(subsetName); } - - triSurf* newSurfPtr = makePatchFromSubset(*origSurfPtr, subsetNames); + + makePatchFromSubset(*origSurfPtr, subsetNames); + origSurfPtr->writeSurface(inFileName); deleteDemandDrivenData(origSurfPtr); - - newSurfPtr->write(inFileName, false); - newSurfPtr->writeFaceSubsets(subsetFileName); - deleteDemandDrivenData(newSurfPtr); - + Info << "End\n" << endl; return 0; } diff --git a/utilities/surfaceClosedness/Make/files b/utilities/surfaceClosedness/Make/files index 91321bb2135ca2ac233e9d28db09275ddc93200e..046ea4ed8938401286c70044da3ef89784a82827 100644 --- a/utilities/surfaceClosedness/Make/files +++ b/utilities/surfaceClosedness/Make/files @@ -1,3 +1,3 @@ surfaceClosedness.C -EXE = $(FOAM_USER_APPBIN)/surfaceClosedness +EXE = $(FOAM_APPBIN)/surfaceClosedness diff --git a/utilities/surfaceClosedness/Make/options b/utilities/surfaceClosedness/Make/options index 7e444b99456d6a132ae2888d264d385602d4ac3d..368004da9a4e64937894608e95209f3804ade11d 100644 --- a/utilities/surfaceClosedness/Make/options +++ b/utilities/surfaceClosedness/Make/options @@ -1,4 +1,4 @@ EXE_INC = -I$(FOAM_USER_LIB)/pMesh3D/pMeshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude + -I$(LIB_SRC)/triSurface/lnInclude -EXE_LIBS = -ltriSurface -lmeshTools -lMeshLibrary +EXE_LIBS = -ltriSurface -lmeshTools -lmeshLibrary diff --git a/utilities/surfaceClosedness/surfaceClosedness.C b/utilities/surfaceClosedness/surfaceClosedness.C index d6615d5ab86cf1e31431d5f16d8080f3094f7e55..5b74894e998276ceef98cd8f1ecd9764eb0c8e71 100644 --- a/utilities/surfaceClosedness/surfaceClosedness.C +++ b/utilities/surfaceClosedness/surfaceClosedness.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Checks if the surface is geometrically closed + Checks if the surface is geometrically closed \*---------------------------------------------------------------------------*/ diff --git a/utilities/surfaceFeatureEdges/Make/options b/utilities/surfaceFeatureEdges/Make/options index aca3590d63f3a0dc1fd230efa91fb75abb1cc2e9..ab3de10c7030c93790a4db67abb80f5bb77efb30 100644 --- a/utilities/surfaceFeatureEdges/Make/options +++ b/utilities/surfaceFeatureEdges/Make/options @@ -1,5 +1,10 @@ -EXE_INC = -I../../meshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude \ - -I$(LIB_SRC)/meshTools/lnInclude +EXE_INC = \ + -I../../meshLibrary/lnInclude \ + -I$(LIB_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude -EXE_LIBS = -ltriSurface -lMeshLibrary -lmeshTools +EXE_LIBS = \ + -ltriSurface \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/surfaceFeatureEdges/surfaceFeatureEdges.C b/utilities/surfaceFeatureEdges/surfaceFeatureEdges.C index c3dbcc0448e9e10b0df7e6e8ed0d81772b620f75..d05cd58741d37aeb30cf8c3b371aa7a95b9fc755 100644 --- a/utilities/surfaceFeatureEdges/surfaceFeatureEdges.C +++ b/utilities/surfaceFeatureEdges/surfaceFeatureEdges.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Finds feature edges and corners of a triangulated surface + Finds feature edges and corners of a triangulated surface \*---------------------------------------------------------------------------*/ @@ -33,10 +32,12 @@ Description #include "triSurf.H" #include "OFstream.H" #include "OSspecific.H" +#include "demandDrivenData.H" #include <cstdlib> #include <sstream> #include "triSurfaceDetectFeatureEdges.H" +#include "triSurfacePatchManipulator.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // Main program: @@ -48,8 +49,7 @@ int main(int argc, char *argv[]) argList::validArgs.clear(); argList::validArgs.append("input surface file"); argList::validArgs.append("output surface file"); - argList::validOptions.insert("subsets", "fileName"); - argList::validOptions.insert("angle", "scalar"); + argList::validOptions.insert("angle", "scalar"); argList args(argc, argv); fileName inFileName(args.args()[1]); @@ -74,33 +74,26 @@ int main(int argc, char *argv[]) Info << "Using 45 deg as default angle!" << endl; } - fileName setFile(""); - if( args.options().found("subsets") ) - { - setFile = args.options()["subsets"]; - } - triSurf originalSurface(inFileName); - if( setFile != "" ) - { - Info << "Reading subset file " << setFile << endl; - originalSurface.readFaceSubsets(setFile); - } triSurfaceDetectFeatureEdges edgeDetector(originalSurface, tol); + edgeDetector.detectFeatureEdges(); - const triSurf* newSurfPtr = edgeDetector.surfaceWithPatches(); - - Info << "Writing : " << outFileName << endl; - newSurfPtr->write(outFileName); - if( setFile != "" ) + if( outFileName.ext() == "fms" || outFileName.ext() == "FMS" ) { - fileName newSetFile = outFileName.lessExt()+'.'+setFile.ext(); - Info << "Writting renumbered sets into " << newSetFile << endl; - newSurfPtr->writeFaceSubsets(newSetFile); + Info << "Writing : " << outFileName << endl; + originalSurface.writeSurface(outFileName); } + else + { + triSurfacePatchManipulator manipulator(originalSurface); + const triSurf* newSurfPtr = manipulator.surfaceWithPatches(); - deleteDemandDrivenData(newSurfPtr); + Info << "Writing : " << outFileName << endl; + newSurfPtr->writeSurface(outFileName); + + deleteDemandDrivenData(newSurfPtr); + } Info << "End\n" << endl; diff --git a/utilities/surfaceGenerateBoundingBox/Make/files b/utilities/surfaceGenerateBoundingBox/Make/files index 0fe4e3c3b5cbd9b053c5e93fe1c9ed51a4e5e83f..cb7eb38d3f69ed9fac87d71f44a2b42a9da2d5cc 100644 --- a/utilities/surfaceGenerateBoundingBox/Make/files +++ b/utilities/surfaceGenerateBoundingBox/Make/files @@ -1,3 +1,3 @@ surfaceGenerateBoundingBox.C -EXE = $(FOAM_APPBIN)/surfaceGenerateBoundingBox +EXE = $(FOAM_USER_APPBIN)/surfaceGenerateBoundingBox diff --git a/utilities/surfaceGenerateBoundingBox/Make/options b/utilities/surfaceGenerateBoundingBox/Make/options index aca3590d63f3a0dc1fd230efa91fb75abb1cc2e9..ab3de10c7030c93790a4db67abb80f5bb77efb30 100644 --- a/utilities/surfaceGenerateBoundingBox/Make/options +++ b/utilities/surfaceGenerateBoundingBox/Make/options @@ -1,5 +1,10 @@ -EXE_INC = -I../../meshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude \ - -I$(LIB_SRC)/meshTools/lnInclude +EXE_INC = \ + -I../../meshLibrary/lnInclude \ + -I$(LIB_SRC)/triSurface/lnInclude \ + -I$(LIB_SRC)/meshTools/lnInclude -EXE_LIBS = -ltriSurface -lMeshLibrary -lmeshTools +EXE_LIBS = \ + -ltriSurface \ + -L$(FOAM_USER_LIBBIN) \ + -lmeshLibrary \ + -lmeshTools diff --git a/utilities/surfaceGenerateBoundingBox/surfaceGenerateBoundingBox.C b/utilities/surfaceGenerateBoundingBox/surfaceGenerateBoundingBox.C index 27a1a6683a9ce34d7cbd1c8603b1472922f12cb0..b381aadcd91b60008d3678baab977cd9bc1b43a0 100644 --- a/utilities/surfaceGenerateBoundingBox/surfaceGenerateBoundingBox.C +++ b/utilities/surfaceGenerateBoundingBox/surfaceGenerateBoundingBox.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Finds feature edges and corners of a triangulated surface + Finds feature edges and corners of a triangulated surface \*---------------------------------------------------------------------------*/ diff --git a/utilities/surfaceOutwardOrientation/Make/files b/utilities/surfaceOutwardOrientation/Make/files deleted file mode 100644 index a5a940c5f849628ddb4e8d273d22db15ef330d83..0000000000000000000000000000000000000000 --- a/utilities/surfaceOutwardOrientation/Make/files +++ /dev/null @@ -1,3 +0,0 @@ -surfaceOutwardOrientation.C - -EXE = $(FOAM_USER_APPBIN)/surfaceOutwardOrientation diff --git a/utilities/surfaceOutwardOrientation/Make/options b/utilities/surfaceOutwardOrientation/Make/options deleted file mode 100644 index 168df83ba662d84f8cb9075ef6da7e48181a7ea9..0000000000000000000000000000000000000000 --- a/utilities/surfaceOutwardOrientation/Make/options +++ /dev/null @@ -1,5 +0,0 @@ -EXE_INC = -I$(FOAM_USER_LIB)/pMesh3D/pMeshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude \ - -I$(LIB_SRC)/meshTools/lnInclude - -EXE_LIBS = -ltriSurface -lmeshTools $(FOAM_USER_LIBBIN)/libpMesh.so diff --git a/utilities/surfaceOutwardOrientation/surfaceOutwardOrientation.C b/utilities/surfaceOutwardOrientation/surfaceOutwardOrientation.C deleted file mode 100644 index f0383d8ad756c240d77924c4a789cb5453c837e7..0000000000000000000000000000000000000000 --- a/utilities/surfaceOutwardOrientation/surfaceOutwardOrientation.C +++ /dev/null @@ -1,121 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - Ensures outward orientation of the triangulated surface - -\*---------------------------------------------------------------------------*/ - -#include "argList.H" -#include "IFstream.H" -#include "fileName.H" -#include "triSurface.H" -#include "surfaceOctree.H" -#include "OFstream.H" -#include "OSspecific.H" - -#define DEBUGStitch - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -// Main program: -using namespace Foam; - -int main(int argc, char *argv[]) -{ - - argList::noParallel(); - argList::validArgs.clear(); - argList::validOptions.insert("noCleanup", ""); - argList::validOptions.insert("group", ""); - argList::validArgs.append("input surface file"); - argList::validArgs.append("output surface file"); - argList args(argc, argv); - - fileName inFileName(args.args()[1]); - fileName outFileName(args.args()[2]); - - triSurface* ts = new triSurface(inFileName); - - bool finished; - - do - { - Info << "New iteration " << endl; - finished = true; - - triSurface& os = *ts; - - surfaceOctree oc - ( - os, - 50, - 50 - ); - - const List<labelledTri>& faces = os.localFaces(); - - List<labelledTri> newTriangles(faces.size()); - - forAll(faces, faceI) - { - bool sure; - if( oc.normalOk(faceI, sure) ) - { - newTriangles[faceI] = faces[faceI]; - } - else - { - Info << "Reversing face " << faceI << endl; - labelledTri newT - ( - faces[faceI][0], - faces[faceI][2], - faces[faceI][1], - faces[faceI].region() - ); - - newTriangles[faceI] = newT; - } - - if( !sure ) finished = false; - } - - triSurface* newTs = - new triSurface(newTriangles, os.patches(), os.localPoints()); - - deleteDemandDrivenData(ts); - ts = newTs; - } while( !finished ); - - ts->write(outFileName, true); - - deleteDemandDrivenData(ts); - - Info << "End\n" << endl; - - return 0; -} - - -// ************************************************************************* // diff --git a/utilities/surfaceRefine/Make/files b/utilities/surfaceRefine/Make/files deleted file mode 100644 index f04cc0573b144a1aab471d83ab75910dcb9606bd..0000000000000000000000000000000000000000 --- a/utilities/surfaceRefine/Make/files +++ /dev/null @@ -1,3 +0,0 @@ -surfaceRefine.C - -EXE = $(FOAM_USER_APPBIN)/surfaceRefine diff --git a/utilities/surfaceRefine/Make/options b/utilities/surfaceRefine/Make/options deleted file mode 100644 index 7e444b99456d6a132ae2888d264d385602d4ac3d..0000000000000000000000000000000000000000 --- a/utilities/surfaceRefine/Make/options +++ /dev/null @@ -1,4 +0,0 @@ -EXE_INC = -I$(FOAM_USER_LIB)/pMesh3D/pMeshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude - -EXE_LIBS = -ltriSurface -lmeshTools -lMeshLibrary diff --git a/utilities/surfaceRefine/surfaceRefine.C b/utilities/surfaceRefine/surfaceRefine.C deleted file mode 100644 index cb6c46580276952d89b49d8c87e2512c91b98b39..0000000000000000000000000000000000000000 --- a/utilities/surfaceRefine/surfaceRefine.C +++ /dev/null @@ -1,197 +0,0 @@ -/*---------------------------------------------------------------------------*\ - ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox - \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | -------------------------------------------------------------------------------- -License - This file is part of OpenFOAM. - - OpenFOAM is free software; you can redistribute it and/or modify it - under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your - option) any later version. - - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT - ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - for more details. - - You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - -Description - Refinement of triangulated surface - -\*---------------------------------------------------------------------------*/ - -#include "argList.H" -#include "IFstream.H" -#include "fileName.H" -#include "triSurface.H" -#include "OFstream.H" -#include "OSspecific.H" - -#include "faceTessalation.H" -#include "delaunayPoint.H" - -#define DEBUGStitch - -// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // -// Main program: -using namespace Foam; - -int main(int argc, char *argv[]) -{ - - argList::noParallel(); - argList::validArgs.clear(); - argList::validOptions.insert("noCleanup", ""); - argList::validOptions.insert("group", ""); - argList::validArgs.append("input surface file"); - argList::validArgs.append("output surface file"); - argList args(argc, argv); - - fileName inFileName(args.args()[1]); - fileName outFileName(args.args()[2]); - - triSurface* ts = new triSurface(inFileName); - - //- refine the surface where needed - const pointField& points = ts->points(); - - SLList<delaunayPoint> dp; - - forAll(points, pI) - dp.append(delaunayPoint(points[pI],pI)); - - faceTessalation ft(dp); - - const IDLList<elementFace>& ef = ft.faces(); - - List<labelledTri> tessalationFaces(ft.faces().size()); - label faceI(0); - - for(IDLList<elementFace>::const_iterator fIter = ef.begin(); - fIter != ef.end(); - ++fIter - ) - { - bool store(true); - - for(direction i=0;i<3;i++) - if( fIter().pointI(i)->number() < 0 ) - store = false; - - if( store ) - { - labelledTri ltri - ( - fIter().pointI(0)->number(), - fIter().pointI(1)->number(), - fIter().pointI(2)->number(), - 0 - ); - - tessalationFaces[faceI++] = ltri; - } - } - - tessalationFaces.setSize(faceI); - - const List<labelledTri>& faces = ts->localFaces(); - boolList foundFace(faces.size(), false); - const labelListList& pointFaces = ts->pointFaces(); - - forAll(tessalationFaces, tfI) - { - const labelledTri& tf = tessalationFaces[tfI]; - const labelList& pf = pointFaces[tessalationFaces[tfI][0]]; - - forAll(pf, pfI) - { - const labelledTri& ltri = faces[pf[pfI]]; - - bool found(true); - - forAll(tf, pI) - { - bool foundVrt(false); - forAll(ltri, pJ) - if( tf[pI] == ltri[pJ] ) - { - foundVrt = true; - break; - } - - if( !foundVrt ) found = false; - } - - if( found ) - { - foundFace[pf[pfI]] = true; - break; - } - } - } - - Info << "FoundFace " << foundFace << endl; - - List<labelledTri> newTriangles(faceI); - faceI = 0; - pointField newPoints(points); - label pointI = points.size(); - - forAll(foundFace, fI) - if( foundFace[fI] ) - { - newTriangles[faceI++] = faces[fI]; - } - else - { - List<labelledTri> nf(3); - const edgeList edg = faces[fI].edges(); - - forAll(edg, eI) - { - const edge& e = edg[eI]; - nf[eI] = - labelledTri - ( - e.start(), - e.end(), - pointI, - faces[fI].region() - ); - } - - forAll(nf, nfI) - newTriangles[faceI++] = nf[nfI]; - - const point p = faces[fI].centre(points); - newPoints.newElmt(pointI++) = p; - } - - newPoints.setSize(pointI); - newTriangles.setSize(faceI); - - triSurface newSurf - ( - newTriangles, - ts->patches(), - newPoints - ); - - newSurf.write(outFileName, true); - - delete ts; - - Info << "End\n" << endl; - - return 0; -} - - -// ************************************************************************* // diff --git a/utilities/surfaceStitch/Make/files b/utilities/surfaceStitch/Make/files index 2717b1aa66e169553ee921c8aa766b4e5378476a..0aa083182089b26945a464c22a68d72bb3d2b54c 100644 --- a/utilities/surfaceStitch/Make/files +++ b/utilities/surfaceStitch/Make/files @@ -1,3 +1,3 @@ surfaceStitch.C -EXE = $(FOAM_USER_APPBIN)/surfaceStitch +EXE = $(FOAM_APPBIN)/surfaceStitch diff --git a/utilities/surfaceStitch/Make/options b/utilities/surfaceStitch/Make/options index 39f23d7a386e15b282f4f8d21765a269bc54b07a..5bb1fdcda2e365b5209c6c001bd94e7ee39080ea 100644 --- a/utilities/surfaceStitch/Make/options +++ b/utilities/surfaceStitch/Make/options @@ -1,4 +1,4 @@ EXE_INC = -I../../meshLibrary/lnInclude \ - -I$(LIB_SRC)/triSurface/lnInclude + -I$(LIB_SRC)/triSurface/lnInclude -EXE_LIBS = -ltriSurface -lmeshTools -lMeshLibrary +EXE_LIBS = -ltriSurface -lmeshTools -lmeshLibrary diff --git a/utilities/surfaceStitch/surfaceStitch.C b/utilities/surfaceStitch/surfaceStitch.C index b767885e3bbefeb1417097720e44b1ecdab9c27d..7ab6696f7c405f70bc404c7613dde5498189d658 100644 --- a/utilities/surfaceStitch/surfaceStitch.C +++ b/utilities/surfaceStitch/surfaceStitch.C @@ -1,29 +1,28 @@ /*---------------------------------------------------------------------------*\ ========= | - \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / F ield | cfMesh: A library for mesh generation \\ / O peration | - \\ / A nd | Copyright (C) 2005-2007 Franjo Juretic - \\/ M anipulation | + \\ / A nd | Author: Franjo Juretic (franjo.juretic@c-fields.com) + \\/ M anipulation | Copyright (C) Creative Fields, Ltd. ------------------------------------------------------------------------------- License - This file is part of OpenFOAM. + This file is part of cfMesh. - OpenFOAM is free software; you can redistribute it and/or modify it + cfMesh is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the - Free Software Foundation; either version 2 of the License, or (at your + Free Software Foundation; either version 3 of the License, or (at your option) any later version. - OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + cfMesh is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License - along with OpenFOAM; if not, write to the Free Software Foundation, - Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + along with cfMesh. If not, see <http://www.gnu.org/licenses/>. Description - Closing holes in the triangulated surface + Closing holes in the triangulated surface \*---------------------------------------------------------------------------*/ @@ -67,116 +66,116 @@ int main(int argc, char *argv[]) triSurface& surf = *ts; - const pointField& points = surf.localPoints(); + const pointField& points = surf.localPoints(); const labelListList& eFaces = surf.edgeFaces(); const edgeList& edges = surf.edges(); const labelListList& pEdges = surf.pointEdges(); - const labelListList& pFaces = surf.pointFaces(); + const labelListList& pFaces = surf.pointFaces(); - //- mark the open edges + //- mark the open edges boolList problemEdges(eFaces.size(), false); forAll(eFaces, eI) - { + { if( eFaces[eI].size() < 2 ) problemEdges[eI] = true; - } - - //- find the vertices which have exactly two open edges attached to them - //- create triangles which fit best into their surrounding - forAll(pEdges, pointI) - { - const labelList& pe = pEdges[pointI]; - - DynList<label> openEdges; - forAll(pe, peI) - { - if( problemEdges[pe[peI]] ) - openEdges.append(pe[peI]); - } - - //- skip vertices attached to more than two open edges - if( openEdges.size() != 2 ) - continue; - - //- skip vertices attached to only one triangle - if( pFaces[pointI].size() == 1 ) - continue; - - const edge& e0 = edges[openEdges[0]]; - const edge& e1 = edges[openEdges[1]]; - - const labelledTri& t0 = surf[eFaces[openEdges[0]][0]]; - const labelledTri& t1 = surf[eFaces[openEdges[1]][0]]; - - labelledTri t; - t[0] = pointI; - if( e0.start() == pointI ) - { - t[1] = e1.otherVertex(pointI); - t[2] = e0.otherVertex(pointI); - t.region() = t0.region(); - } - else if( e1.start() == pointI ) - { - t[1] = e0.otherVertex(pointI); - t[2] = e1.otherVertex(pointI); - t.region() = t1.region(); - } - else - { - continue; - FatalError << "Strange" << exit(FatalError); - } - - Info << "Creating triangle for point " << pointI << endl; - Info << "triangle is " << t << endl; - - //- check dot product between the normals - vector n0 = t0.normal(points); - n0 /= mag(n0) + VSMALL; - - vector n1 = t1.normal(points); - n1 /= mag(n1) + VSMALL; - - vector n = t.normal(points); - n /= mag(n) + VSMALL; - - //- find the maximum dot product between the normals of - //- of existing triangles and the newly generated one - scalar q = (n & n0); - q = Foam::max(q, (n & n1)); - - if( q > 0.9 ) - { - createdTriangles.append(t); - ++counter; - - forAll(openEdges, i) - problemEdges[openEdges[i]] = false; - } - } - - if( createdTriangles.size() ) - { - List<labelledTri> newTriangles = surf.localFaces(); - - label nTriangles(newTriangles.size()); - newTriangles.setSize(nTriangles+createdTriangles.size()); - forAll(createdTriangles, i) - newTriangles[nTriangles++] = createdTriangles[i]; - - triSurface* newts = - new triSurface - ( - newTriangles, - surf.patches(), - surf.points() - ); - - deleteDemandDrivenData(ts); - ts = newts; - } + } + + //- find the vertices which have exactly two open edges attached to them + //- create triangles which fit best into their surrounding + forAll(pEdges, pointI) + { + const labelList& pe = pEdges[pointI]; + + DynList<label> openEdges; + forAll(pe, peI) + { + if( problemEdges[pe[peI]] ) + openEdges.append(pe[peI]); + } + + //- skip vertices attached to more than two open edges + if( openEdges.size() != 2 ) + continue; + + //- skip vertices attached to only one triangle + if( pFaces[pointI].size() == 1 ) + continue; + + const edge& e0 = edges[openEdges[0]]; + const edge& e1 = edges[openEdges[1]]; + + const labelledTri& t0 = surf[eFaces[openEdges[0]][0]]; + const labelledTri& t1 = surf[eFaces[openEdges[1]][0]]; + + labelledTri t; + t[0] = pointI; + if( e0.start() == pointI ) + { + t[1] = e1.otherVertex(pointI); + t[2] = e0.otherVertex(pointI); + t.region() = t0.region(); + } + else if( e1.start() == pointI ) + { + t[1] = e0.otherVertex(pointI); + t[2] = e1.otherVertex(pointI); + t.region() = t1.region(); + } + else + { + continue; + FatalError << "Strange" << exit(FatalError); + } + + Info << "Creating triangle for point " << pointI << endl; + Info << "triangle is " << t << endl; + + //- check dot product between the normals + vector n0 = t0.normal(points); + n0 /= mag(n0) + VSMALL; + + vector n1 = t1.normal(points); + n1 /= mag(n1) + VSMALL; + + vector n = t.normal(points); + n /= mag(n) + VSMALL; + + //- find the maximum dot product between the normals of + //- of existing triangles and the newly generated one + scalar q = (n & n0); + q = Foam::max(q, (n & n1)); + + if( q > 0.9 ) + { + createdTriangles.append(t); + ++counter; + + forAll(openEdges, i) + problemEdges[openEdges[i]] = false; + } + } + + if( createdTriangles.size() ) + { + List<labelledTri> newTriangles = surf.localFaces(); + + label nTriangles(newTriangles.size()); + newTriangles.setSize(nTriangles+createdTriangles.size()); + forAll(createdTriangles, i) + newTriangles[nTriangles++] = createdTriangles[i]; + + triSurface* newts = + new triSurface + ( + newTriangles, + surf.patches(), + surf.points() + ); + + deleteDemandDrivenData(ts); + ts = newts; + } } while( createdTriangles.size() );