cfMesh VS snappyHexMesh, 回転メッシュで比較

背景

先の記事で、OpenFOAM 標準チュートリアルのmixerVesselを対象に、cfMeshを使ったメッシュ作成法を紹介した。

   

 

その結果を見る限りにおいて、メッシュ数や計算時間は、ほぼ同等の結果になっていた。 一方、cfMeshでは境界層レイヤーがきちんと作成出来ているし、メッシュ作成に要する計算時間も短く済むので、この種の回転体問題でも、マルチリージョンメッシュを作成する(個別に作成して合体させる)手間が必要ではあるが、cfMeshの利用を推奨してきた。 しかし、最近取り組んだ現実の設計問題で、cfMeshではsnappyHexMesh(以下SHMと記す)に比べて、どうしてもメッシュ数が多くなりすぎてしまうという問題が生じた。 この現実の設計問題と、mixerVesselの問題との違いは何であったのか?・・・どうも回転体と静止部分間のクリアランスに違いがあるようであった。  

 
 

問題の略式化

そこで、この違いをもう少し明確にすべく、もっとシンプルな形状でクリアランスの違いがメッシュ数にどう効いてくるのか。以下のようなモデルを使って、cfMeshとSHMで比較してみました。 範囲を選択_999(232) 2つの円柱の入れ子構造で、2つの円柱で囲まれた領域(上右図中、水色の領域)でメッシュ作成するというもの。回転体問題のメッシュ作成に際して、どちらかが回転境界面(cyclicAMI)になり、もう一方が、物体(回転体、もしくは固定境界)になることを想定しています。 物体と回転境界面の隙間が小さいと、きれいな回転境界面が出来なくなってしまい、計算が不能ということになります。したがって隙間の大きさに対して、メッシュの最少分割サイズをどこまで大きく出来るか?というアプローチで取り組んでみました。 メッシュの分割方案としては、内部の円柱(inner)を最小セルサイズ(min cellSize)になるようにして、ベースセルサイズ(Base cellSize)は、その8倍となるよう設定しました。参考に、DEXCS2015 for OpenFOAM(R)を使った場合のパラメタ設定画面(min cellSize=1の場合)を以下に添付しておきます。 範囲を選択_999(236)下図は、min cellSize に対して、出来上がったメッシュのサイズをプロットしたものです。 範囲を選択_999(237) なお、snappyHexMeshでは、内部円柱の内部をcellZone定義するという方法でメッシュ作成しており、この図に記したメッシュ数(No. of cells)は、cfMeshで作成したメッシュと対比すべく、この内部を除いた領域( splitMeshRegions -cellZones を実施してメッシュ分割したもの)におけるメッシュ数です。 min cellSizeが小さい(=0.2)場合、cfMeshとSHMで、ほとんど違いはありませんが、 範囲を選択_999(246) 大きくなるにつれ、cfMeshのほうがメッシュ数が大きくなります(下図は、minCellSize=0.5)。 範囲を選択_999(245) また、隙間の大きさ(=5)に対し、SHMでは約70%のminCellSizeでメッシュ生成できるのに対して、cfMeshでは、20%を超えたところで、以下のようなメッシュとなって、回転境界面として不適切な物になってしまいました(下図は、minCellSize=1.5で、上のプロット図中では赤の✕印に相当するケース)。   範囲を選択_999(244)  

keepCellsIntersectingPatches

但し、cfMeshには、keepCellsIntersectingPatches というオプションパラメタがあって、これを使うと、上記のような狭い隙間でも、patch の形状を再現してくれるようになります。その代わりにメッシュ数は下図(緑がオプション無し、赤がオプション有り)で示したようにもう少し増えてしまいます。

 

範囲を選択_999(247)

下図は、minCellSize=2 におけるメッシュを比較したものです。

範囲を選択_999(250)

最終的には、minCellSize=2.25(隙間に対して45%)まで大きくすることは出来ましたが、いずれにせよ、SHM(隙間に対して70%)に比べると、そんなに大きくできないので、最少メッシュサイズが隙間サイズで規定されるようなケースでは、cfMeshの方がメッシュ数は増えてしまうことになります。

 

現実の設計問題と、mixerVessel問題との違いを改めて考察

mixerVessel問題の寸法を改めてチェックし直したところ、最少メッシュサイズが隙間サイズに対して約20%の大きさになっていました。このサイズであれば、cfMeshとSHMはほぼ同等なので、上述のケースには該当しない。

一方、現実の設計問題で取り扱った例では、最少メッシュサイズが隙間サイズで規定され、cfMeshではSHMよりも最少メッシュサイズを小さくせざるを得なくなり、大幅なメッシュ増加になったということでした。

 

結論

回転体問題では、メッシュ生成に際して、隙間(回転面と回転体、または回転面と静止境界間)のサイズが重要なファクターで、このサイズに対して最少メッシュサイズを、

  • cfMeshの場合、45%以下
  • SHMの場合、70%以下

にする必要がある。

この基準でメッシュ作成した場合、cfMeshのメッシュ数はSHMに比べ、最大で8倍程度増加する。

FreeCADとcfMesh用マクロの使い方

先の記事に書いた通り、ただいまDEXCS2015 for OpenFOAM(R) の動画チュートリアルを作成中ですが、その一部は単独でそのまま表題の説明用途にも使えるわなぁ・・・と改めて気付いたので、本記事にて紹介しておきます。

FreeCADの基本的な使い方

範囲を選択_987

DEXCSでは、複雑な形状作成はユーザーが使い慣れた3D-CAD(もちろん頑張ればDEXCSに搭載のFreeCADやBlenderでも可能です!)で作成してもらうとして、これをstepまたはstl形式でFreeCADにインポートして使ってもらう事を想定しています。

その際に、FreeCADに標準搭載のプリミティブ要素(直方体や円柱など)を使って、領域を追加で定義したり、解析用の境界面を定義するのに、面の分割や再結合の操作が必要になりますが、これらの操作方法を具体例で確認することが出来ます。

⇒ チュートリアルを見る

 

cfMesh用マクロの使い方と機能の概要説明

範囲を選択_988

上述の方法で、FreeCADのソリッドモデルで解析空間を定義できるようになれば、DEXCSに搭載のFreeCAD用マクロ(makeCfMeshSetting.py)を使って、cfMesh用に境界面の定義や分割方法を指定する為の設定ファイル(meshDict)を自動作成できます。

このチュートリアルでは、マクロで起動される表形式のGUIの使い方と、実際に作成したmeshDictを対比させながらmeshDictファイルのパラメタの意味を解説するとともに、GUIでは指定しなかった、または指定出来ないパラメタを手修正で追加する方法についても解説しています。

⇒ チュートリアルを見る

STL品質(3Dプリンター VS cfMesh)

先の記事で、「STLファイルに不可視な欠損がある・・・」と云われてしまった拙作の3Dデータですが、これはiphoneケースのベースデータをダウンロード提供してくれているサイトから入手したstpファイルと、拙作のLogoデータを、FreeCAD上でソリッド演算にて作成したものです(下図参照)。範囲を選択_011これらのデータから、3Dプリンタ用のSTLファイルを作成するに際して、FreeCADの使用法という面で、備忘録として残しておきたい情報もいくつかあったので、以下記しておきます。

ブーリアン演算範囲を選択_012

ソリッド演算は、単純にocse2Logo とDocument003の2つのパーツで差をとればいいだろう、と思ってブーリアン演算にかけると・・・範囲を選択_015となってしまって、ここで、

  • iphoneケースデータの本体部分(Document003)が実はシェルデータだったということ
  • FreeCADでは、ソリッドデータしかブーリアン演算できない、

ということが判った。

ソリッドとシェルで、オブジェクトのアイコンを変えてくれれば分り易いんだろうにね。

 

形状構築ツール範囲を選択_017

Partワークベンチにある形状構築ツールを使うと、シェルデータをソリッドデータに変換したり、その逆変換も可能になる、

範囲を選択_032

これで出来上がったSolidを対象にブーリアン演算範囲を選択_012すると、

範囲を選択_023

 

最後に、出来上がったもの(Cut)と、それ以外のもの(Document,Document001,Document002)を全てまとめて、結合範囲を選択_024すれば、

範囲を選択_022

となるので、出来上がった(Block)をSTLファイルに書き出してやればよい。DEXCS2014の最新版(5/30に開催するオープンCAE講習会でお披露目予定のもの)であれば、マクロの実行ボタン範囲を選択_030から、

範囲を選択_033

上段のマクロ(exportStl.py)を実行してやれば、任意の名前でSTLファイル出力が可能になる。

ちなみに、下段のマクロ(makeCfMeshSetting.py)を実行すれば、cfMesh用の設定ファイル作成用GUIが起動し、範囲を選択_029

 

上記設定(Maxメッシュサイズ=0.5)にてExportボタンを押して、cfMesh(cartesianMesh)を実行して、以下のようなメッシュが作成できることは確認済です。

範囲を選択_034

問題は、このSTLファイルを使って3Dプリンタ用のスライスデータを作成しようとしたら、形状が再現できなかったという事です。

2015-05-21_1829スライスデータに変換するソフトがヴァージョンアップしたら出来なくなったので、てっきり変換ソフトに問題があると思ったのですが・・・

サポートの回答は、

STLファイルに不可視な欠損がある場合、スライス後に欠損が可視化し
スライス後の形状が変わる場合がございます。

弊社で使用しておりますデータ補正用のフリーソフトがございますので
お試しいただければと存じます。

http://www.3ds.co.jp/netfabb/

お手数をお掛けしますが、よろしくお願い申し上げます。

以上、どうぞよろしくお願い申し上げます。

というものでした。

そこで、紹介されたソフト(netfabbの無償版)を使って表示させると、

2015-05-22_1538確かに、ビックリマークが表示されて、STLに欠陥がある事を指摘されています。ここで嬉しいのは、この欠陥を自動修復してくれる機能があったことでした。

2015-05-22_1552_001

「その他」⇒「パーツの修復」 を選択すると、

2015-05-22_1540右下の「自動修復」のボタンを押すと、

2015-05-22_1540_001

「実行ボタン」を押せば、

2015-05-22_1541欠陥が修復されるという、いとも簡単でした。あとは、「パーツをエクスポート」。

2015-05-22_1552

このSTLファイルを使えば、スライスデータへの変換は何の問題も無し、という事でした。

 

中間まとめ

  1. STLの品質に対し、cfMeshはロバスト性大(多少の欠陥があってもメッシュ生成可能)であるが、3Dプリンターはそうでない。
  2. STLの欠陥を自動修復するソフトとして、netfabbは無償版も有り、簡単に使えて有効であった。但し、より複雑、大規模なモデルに対する検証は未実施。
  3. 本例で、STLに欠陥が生じた原因はFreeCADの機能不足?

ということで、ここで終わってしまうと、FreeCADは使えないのか?になってしまうので、ここはあくまで「中間まとめ」ということで、次回は、今回のSTL欠陥の本質原因を探りたいと思います。

 

おまけ・・・Netgen

File ⇒ LoadGeometry にて、元のSTLデータを読み込んだ後、

Geometry ⇒ STL Info で調べてみると、確かにERRORが表示されていました。

NETGEN - -home-et-Desktop-3D-caseA.stl_036

 

これに対し、netfabbにて修復したSTLデータだと、ERRORはなしで、GenerateMeshボタンで自動メッシュ作成も可能でした。NETGEN - -home-et-Desktop-3D-caseAm.stl_037

但し、メッシュ品質は、ちょっとどうかな? ですね。STLは修復はされたものの、品質の悪い三角形が多くあり、メッシュ生成はその影響を受けてしまっているということでしょうね。

このNetgenとの比較においても、cfMeshのロバスト性は立派です。

 

 

makeCfMeshSetting.py(改)

来る5/30のオープンCAE講習会にて講習用に使用する計算環境(DEXCS2014 for OpenFOAM®の特別版)を製作するにあたり、表題のFreeCAD用マクロを改良しました。⇒少々シンプルになって使い易くなったと思います。

マクロ画面の説明(旧版)

範囲を選択_999(583)

マクロ画面の説明(新版)

範囲を選択_999(585)

  • Refinement(細分化)方法の指定が不要になったことと、Loadボタンが追加されています。

 

 

マクロの実行手順(旧版)

範囲を選択_999(586)

マクロの実行手順(新版)

範囲を選択_999(587)

  • 中間の確認ダイヤログを廃止しました。

追加機能(Loadボタン)

一番下の左端にあるLoadボタンを押すと・・・

範囲を選択_999(588)既存のmeshDictファイルを読み込んで、設定済のパラメタを反映することが出来るようになりました。これで、やり直しの際の作業効率が格段に向上すると思います。

範囲を選択_999(589)

範囲を選択_999(590)

但し・・・

  1. マウスカーソルで表中をクリックしないと、パラメタが再表示されない。(自動で画面リフレッシュされない)
  2. region以外の表面Type指定(patch/wall/…)は反映されない。(meshDictで指定していないので)

という問題はありますが、致命的ではないと思うので、まずはこのレベルでリリースすることと致しました。

 

謝辞

本マクロを作成するに際しては、旧版の作成記事の中で、「自分は本職のプログラマでないので・・・協力者求む!」的な願望を記したところ、MさんとIさんという強力助っ人が手を挙げてくれて、旧版のソースコードをリファクタリングしてもらえました。GUIの見た目はほとんど変わっていませんが、ソースコード(近日中には公開予定)は一変して見易くなっており、開発環境としてpythonの素の(FreeCADマクロから起動しなくてもよい)環境でデバッグ出来るようにもなり、おかげで今回の改造も大幅に効率upで講習会に間に合わせることが出来ました。

こういう活動の成果も出せるようになったという事は、ようやくオープンCAEの活動らしくなってきたと、ここに改めてお礼申し上げます。

motoBikeチュートリアルをcfMeshで実施する方法

先日の勉強会にて発表した表題の資料は、それなりに反響があったようで、アップロード先のslideshareさんからは、初めて下のような「Hot on Facebook」のお知らせを頂きました(こんなものがあるということも初めて知りました)。

範囲を選択_999(194)

 

ここでは、当日およびその後に頂いたコメントに対して検証計算した結果について報告しておきます。

検証内容は、大きく以下の2点です。

ひとつは、当日にakiyamaさんからいただいた、重複面があるモデルであっても、fmsファイルでなく、stlファイルをそのまま使えば出来るんではないか?

そこで…

  • stlファイルを使ってみた(その1)
  • stlファイルを使ってみた(その2)

もう一つは、Twitter上でいただいた下記のコメントです。

範囲を選択_999(195)

但し、このコメントの前半(格子が歪む原因)については、開発者に聞いて下さいとしか答えようがありません。また最後のmeshQuarity制限も何処をいじるのか、あまり思いつくものもないので、ここでは「分割レベル」についての検証で、

  • snappyの細分化レベルを変えてみた
  • cfMeshの細分化方案を変えてみた

結果について、以下記しておきます。

 

 

stlファイルを使ってみた(その1)

FreeCADでエクスポートしたstlをそのまま使う事は、以下の図に示した手順で簡単にできます。

範囲を選択_999(226)

ただこの方法ではFeatureEdges(輪郭線)情報を使わないので、上図、左側のfmsファイルを使った場合と比べると、輪郭線が鈍ってしまいます。

 

stlファイルを使ってみた(その2)

その1の検証で、輪郭線が鈍る件は、akiyamaさんもとっくにご存知で、輪郭線を使うのではなく、patchが分割されていればpatch境界として認識されるはずだというご指摘でした。

そこで、OpenFOAMのチュートリアルに付属のデータ($FOAM_TUTORIALS/resources/geometry/motorBike.obj.gz)を、以下の図に示す手順で検証してみました。

範囲を選択_999(227)

これで、motorBikeの面が分割されたstlファイルが作れた事になるのですが、問題は、system/meshDict です。分割されたそれぞれの面に対し、レイヤーや細分化指定してやる必要があります(下図赤枠部分)。

範囲を選択_999(229)

solidブロック(patch)が全部で67箇所もあり、ここは面倒な作業になりそうでスクリプトを作ることも考えましたが、とりあえず適当に作ったメッシュのboundaryファイルから、patchリストが簡単に取得できたので、単純なコピペ作業で出来ました。

で、苦労した後の結果ですが…

範囲を選択_999(196)

範囲を選択_999(197)

残念ながら、何度やっても途中で終わってしまいます。やはり、厚みのほとんどない部分で困っているんだろうと推察されます。

 

snappyの細分化レベルを変えてみた

snappyHexMeshでは、patchの平坦部とそうでない部分に対して、細分化のレベルを 変えることが出来ますが、cfMeshは出来ません。そこで比較の土俵を合わせるのに、snappyHexMeshでも一律同じ細分化レベルにしてやってみました(下図参照)。

範囲を選択_999(230)

 

メッシュを以下に比較します。

範囲を選択_999(231)

頭部ヘルメットのあたりで、分割方案による差異が見られますが、メッシュ数の増加はほんのわずかでした。

以下、checkMesh、計算進行状況、y+の結果もほとんど差異は見られませんでした。

範囲を選択_999(232)

 

範囲を選択_999(233)

 

範囲を選択_999(234)

cfMeshの細分化方案を変えてみた

一方、cfMeshでPatchを指定して局所的な細分化指定を出来ないと記しましたが、minCellSizeパラメタを使って、結果的に局所的な細分化が出来る場合(たとえばDEXCSフォントの例⇒資料の111ページ参照)があります。ここではその方法を使ってみました。

範囲を選択_999(237)

この設定によれば、下図に示すように、MotorBikeGroupの表面で、平坦部とそうでない部分の差異を実現することが出来ます。もっとも、運転者頭部ヘルメットのあたりでは差異が無かったんですが…

範囲を選択_999(238)

それよりも、checkMeshや全体メッシュで大きな構造変化が生じてしまいました。

範囲を選択_999(239)

範囲を選択_999(240)

 

領域全体の隅部で、minCellSizeまで細分化されています。実はかようなケースが、cfMeshに付属の標準サンプルの中にもいくつかあります。先に例示したDEXCSフォントの例では、このような結果にならないのですがね。

cfMeshのオプションパラメタに関する記事の中で述べているminCellSizeについてよく判らない点の一つでもあります。

ま、いずれにせよ、こうなってしまうと、流れ場計算そのものも、すんなりとはいかなくなります。一例を以下に示します。

範囲を選択_999(241)

 

もう少し頑張れば、収束解が得られそうな気もしますが、それを見つけたからといって、意味のない仕事になりそうなので、これ以上は調べておりません。

 

まとめと結論

cfMesh作成に際し、fms形式でなく、stl形式の領域定義ファイルを使用してみたが、板厚が極端に薄い領域を持った(重複面と見做されそうな)データについて境界面を区分するメッシュ作成は出来なかった。⇒やはり重複面と見做されそうな面は単面化の処理が必要。

cfMeshとsnappyHexMeshで、分割レベルの土俵を近づけるべく、それぞれの分割方案を変えたメッシュ作成を実施してみたが、先の結論(cfMeshはsnappyHexMeshと比較して、メッシュ生成時間・checkMesh品質は劣ったが、境界レイヤーは格段に優れていた。)を覆す結果には到らなかった。