Exercise-2
この演習では、ジオメトリ実装の基本を練習します。 基本的な、placement(移動、回転)を通して、どのようにvolumeを配置するのか学びます。
ここでは、箱の中に円筒形を寝かして配置したものを、Z軸の回りに45度間隔で配置していきます。

教材のダウンロード
ここから、演習コードをダウンロードし、作業ディレクトリに展開します。
$ cd ~/g4work/ $ tar zxvf (somewhere)/exercise-2.tar.gz $ cd exercise-2 $ ls GNUmakefile ex02.cc gun.mac include/ src/ vis.mac vrml.mac
Step1: コンパイルと実行
まずは、プログラムをコンパイルして、実行してみます。
初期状態では、箱が1個、world volume中に配置されているだけです。円筒も寝ていません。
$ make ... $ ./bin/Linux-g++/ex02 ... ex02(Idle)[/]:/control/execute vis.mac

Step2: 円筒を寝かせる
では、最初のステップとして、円筒を寝かせてみます。
ジオメトリの実装は、DetectorConstructionのクラスで記述します。
円筒のplacementの部分を以下のように変更します。
placementは、子ボリュームを親ボリュームに対して中心を合わせて回転させた後、
移動を行います。今の場合は、Y軸回りに90度回転させます。
ここで、注意しておきたいのは、この形式のplacementでの回転行列は、
座標軸回転(passive)の形式で与えることです。物体を回転させる方法で記述する場合は、
G4RotationMatrix* rotM= new G4RotationMatrix; rotM-> rotateY(-90.*deg); new G4PVPlacement(rotM, G4ThreeVector(), tubeLV, "tube", boxLV, false, 0);

Step3: Z軸回りに配置する
次に、箱をZ軸回りに45度づつ回転させながら配置していきます。
各ボリュームには、コピー番号がユニークにふられていることに注意してください。
これで、各phyical volumeを識別することができます。
今回は、
const G4double dphi= 45.*deg; for(G4int i=0; i<6; i++) { // check rotation directioon!! G4ThreeVector armVec= G4ThreeVector(30.*cm, 0., 0.); G4RotationMatrix armRot= G4RotationMatrix(); armVec.rotateZ(dphi*i); armRot.rotateZ(dphi*i); new G4PVPlacement(G4Transform3D(armRot, armVec), boxLV, "box", worldLV, false, i); // copy# should be unique. }

$ ./bin/Linux-g++/ex02 ... ex02(Idle)[/]:/control/execute gun.mac ex02(Idle)[/]:/control/execute vis.mac ex02(Idle)[/]:/run/beamOn

おまけ: Collision Detectionをためす。
Geant4では、オーバーラップしてボリュームを配置することはできません。
new G4PVPlacement(rotM, G4ThreeVector(5.*cm, 0., 0.), tubeLV, "tube", boxLV, false, 0, true);
実際に実行してみると、G4Exceptionが発行されています。
$ make ... $ ./bin/Linux-g++/ex02 ... *** G4Exception : InvalidSetup issued by : G4PVPlacement::CheckOverlaps() Overlap with mother volume ! *** This is just a warning message.
