3 #include "gutilities.h"
11 using namespace gutilities;
25 log->debug(CONSTRUCTOR,
"G4DisplayView");
29 double thetaValue = getG4Number(jcamera.
theta);
30 double phiValue = getG4Number(jcamera.
phi);
32 vector<string> toggle_button_titles;
33 toggle_button_titles.emplace_back(
"Hidden\nLines");
34 toggle_button_titles.emplace_back(
"Anti\nAliasing");
35 toggle_button_titles.emplace_back(
"Auxiliary\nEdges");
36 toggle_button_titles.emplace_back(
"Field\nLines");
39 buttons_set1 =
new GQTToggleButtonWidget(80, 80, 20, toggle_button_titles,
false,
this);
40 connect(buttons_set1, &GQTToggleButtonWidget::buttonPressedIndexChanged,
this, &G4DisplayView::apply_buttons_set1);
43 cameraTheta =
new QSlider(Qt::Horizontal);
44 cameraTheta->setRange(0, 180);
45 cameraTheta->setSingleStep(1);
46 cameraTheta->setValue(thetaValue);
47 auto cameraThetaLabel =
new QLabel(tr(
"θ"));
49 auto cameraThetaLayout =
new QHBoxLayout;
50 cameraThetaLayout->addWidget(cameraThetaLabel);
51 cameraThetaLayout->addWidget(cameraTheta);
53 cameraPhi =
new QSlider(Qt::Horizontal);
54 cameraPhi->setRange(0, 360);
55 cameraPhi->setSingleStep(1);
56 cameraPhi->setValue(phiValue);
57 auto cameraPhiLabel =
new QLabel(tr(
"ɸ"));
59 auto cameraPhiLayout =
new QHBoxLayout;
60 cameraPhiLayout->addWidget(cameraPhiLabel);
61 cameraPhiLayout->addWidget(cameraPhi);
63 QVBoxLayout* cameraDirectionLayout =
new QVBoxLayout;
64 cameraDirectionLayout->addLayout(cameraThetaLayout);
65 cameraDirectionLayout->addSpacing(12);
66 cameraDirectionLayout->addLayout(cameraPhiLayout);
68 QGroupBox* cameraAnglesGroup =
new QGroupBox(tr(
"Camera Direction"));
69 cameraAnglesGroup->setLayout(cameraDirectionLayout);
71 connect(cameraTheta, &QSlider::valueChanged,
this, &G4DisplayView::changeCameraDirection);
72 connect(cameraPhi, &QSlider::valueChanged,
this, &G4DisplayView::changeCameraDirection);
75 lightTheta =
new QSlider(Qt::Horizontal);
76 lightTheta->setRange(0, 180);
77 lightTheta->setSingleStep(1);
78 lightTheta->setValue(thetaValue);
79 auto lightThetaLabel =
new QLabel(tr(
"θ"));
81 auto lightThetaLayout =
new QHBoxLayout;
82 lightThetaLayout->addWidget(lightThetaLabel);
83 lightThetaLayout->addWidget(lightTheta);
85 lightPhi =
new QSlider(Qt::Horizontal);
86 lightPhi->setRange(0, 360);
87 lightPhi->setSingleStep(1);
88 lightPhi->setValue(phiValue);
89 auto lightPhiLabel =
new QLabel(tr(
"ɸ"));
91 auto lightPhiLayout =
new QHBoxLayout;
92 lightPhiLayout->addWidget(lightPhiLabel);
93 lightPhiLayout->addWidget(lightPhi);
95 auto lightDirectionLayout =
new QVBoxLayout;
96 lightDirectionLayout->addLayout(lightThetaLayout);
97 lightDirectionLayout->addSpacing(12);
98 lightDirectionLayout->addLayout(lightPhiLayout);
100 QGroupBox* lightAnglesGroup =
new QGroupBox(tr(
"Light Direction"));
101 lightAnglesGroup->setLayout(lightDirectionLayout);
103 connect(lightTheta, &QSlider::valueChanged,
this, &G4DisplayView::changeLightDirection);
104 connect(lightPhi, &QSlider::valueChanged,
this, &G4DisplayView::changeLightDirection);
107 sliceXEdit =
new QLineEdit(tr(
"0"));
108 sliceXEdit->setMaximumWidth(100);
109 sliceXActi =
new QCheckBox(tr(
"&On"));
110 sliceXActi->setChecked(
false);
111 sliceXInve =
new QCheckBox(tr(
"&Flip"));
112 sliceXInve->setChecked(
false);
113 auto sliceXLayout =
new QHBoxLayout;
114 sliceXLayout->addWidget(
new QLabel(tr(
"X: ")));
115 sliceXLayout->addWidget(sliceXEdit);
116 sliceXLayout->addStretch(1);
117 sliceXLayout->addWidget(sliceXActi);
118 sliceXLayout->addWidget(sliceXInve);
119 sliceXLayout->addStretch(1);
123 sliceYEdit =
new QLineEdit(tr(
"0"));
124 sliceYEdit->setMaximumWidth(100);
125 sliceYActi =
new QCheckBox(tr(
"&On"));
126 sliceYActi->setChecked(
false);
127 sliceYInve =
new QCheckBox(tr(
"&Flip"));
128 sliceYInve->setChecked(
false);
129 auto sliceYLayout =
new QHBoxLayout;
130 sliceYLayout->addWidget(
new QLabel(tr(
"Y: ")));
131 sliceYLayout->addWidget(sliceYEdit);
132 sliceYLayout->addStretch(1);
133 sliceYLayout->addWidget(sliceYActi);
134 sliceYLayout->addWidget(sliceYInve);
135 sliceYLayout->addStretch(1);
138 sliceZEdit =
new QLineEdit(tr(
"0"));
139 sliceZEdit->setMaximumWidth(100);
140 sliceZActi =
new QCheckBox(tr(
"&On"));
141 sliceZActi->setChecked(
false);
142 sliceZInve =
new QCheckBox(tr(
"&Flip"));
143 sliceZInve->setChecked(
false);
144 auto sliceZLayout =
new QHBoxLayout;
145 sliceZLayout->addWidget(
new QLabel(tr(
"Z: ")));
146 sliceZLayout->addWidget(sliceZEdit);
147 sliceZLayout->addStretch(1);
148 sliceZLayout->addWidget(sliceZActi);
149 sliceZLayout->addWidget(sliceZInve);
150 sliceZLayout->addStretch(1);
153 QPushButton* clearSliceButton =
new QPushButton(tr(
"Clear Slices"));
154 clearSliceButton->setToolTip(
"Clear Slice Planes");
155 clearSliceButton->setIcon(QIcon::fromTheme(
"edit-clear"));
156 clearSliceButton->setIconSize(QSize(16, 16));
158 connect(clearSliceButton, &QPushButton::clicked,
this, &G4DisplayView::clearSlices);
161 QGroupBox* sliceChoiceBox =
new QGroupBox(tr(
"Slices Style"));
162 sliceSectn =
new QRadioButton(tr(
"&Intersection"), sliceChoiceBox);
163 sliceUnion =
new QRadioButton(tr(
"&Union"), sliceChoiceBox);
164 sliceSectn->setChecked(
true);
166 connect(sliceSectn, &QRadioButton::toggled,
this, &G4DisplayView::slice);
167 connect(sliceUnion, &QRadioButton::toggled,
this, &G4DisplayView::slice);
169 auto sliceChoiceLayout =
new QHBoxLayout;
170 sliceChoiceLayout->addWidget(sliceSectn);
171 sliceChoiceLayout->addWidget(sliceUnion);
172 sliceChoiceBox->setLayout(sliceChoiceLayout);
176 auto sliceLayout =
new QVBoxLayout;
177 sliceLayout->addLayout(sliceXLayout);
178 sliceLayout->addLayout(sliceYLayout);
179 sliceLayout->addLayout(sliceZLayout);
180 sliceLayout->addWidget(sliceChoiceBox);
181 sliceLayout->addWidget(clearSliceButton);
185 connect(sliceXEdit, &QLineEdit::returnPressed,
this, &G4DisplayView::slice);
186 connect(sliceYEdit, &QLineEdit::returnPressed,
this, &G4DisplayView::slice);
187 connect(sliceZEdit, &QLineEdit::returnPressed,
this, &G4DisplayView::slice);
190 #if QT_VERSION < QT_VERSION_CHECK(6, 7, 0)
191 connect(sliceXActi, &QCheckBox::stateChanged,
this, &G4DisplayView::slice);
192 connect(sliceYActi, &QCheckBox::stateChanged,
this, &G4DisplayView::slice);
193 connect(sliceZActi, &QCheckBox::stateChanged,
this, &G4DisplayView::slice);
194 connect(sliceXInve, &QCheckBox::stateChanged,
this, &G4DisplayView::slice);
195 connect(sliceYInve, &QCheckBox::stateChanged,
this, &G4DisplayView::slice);
196 connect(sliceZInve, &QCheckBox::stateChanged,
this, &G4DisplayView::slice);
198 connect(sliceXActi, &QCheckBox::checkStateChanged,
this, &G4DisplayView::slice);
199 connect(sliceYActi, &QCheckBox::checkStateChanged,
this, &G4DisplayView::slice);
200 connect(sliceZActi, &QCheckBox::checkStateChanged,
this, &G4DisplayView::slice);
201 connect(sliceXInve, &QCheckBox::checkStateChanged,
this, &G4DisplayView::slice);
202 connect(sliceYInve, &QCheckBox::checkStateChanged,
this, &G4DisplayView::slice);
203 connect(sliceZInve, &QCheckBox::checkStateChanged,
this, &G4DisplayView::slice);
207 QGroupBox* fieldPrecisionBox =
new QGroupBox(tr(
"Number of Field Points"));
208 field_npoints =
new QLineEdit(QString::number(field_NPOINTS),
this);
209 field_npoints->setMaximumWidth(40);
211 QFont font = field_npoints->font();
212 font.setPointSize(24);
213 field_npoints->setFont(font);
214 connect(field_npoints, &QLineEdit::returnPressed,
this, &G4DisplayView::field_precision_changed);
217 auto fieldPointsHBox =
new QHBoxLayout;
218 fieldPointsHBox->addWidget(field_npoints);
219 fieldPrecisionBox->setLayout(fieldPointsHBox);
221 auto buttons_field_HBox =
new QHBoxLayout;
222 buttons_field_HBox->addWidget(buttons_set1);
223 buttons_field_HBox->addWidget(fieldPrecisionBox);
224 fieldPrecisionBox->setMaximumHeight(3 * buttons_set1->height());
225 fieldPrecisionBox->setMaximumWidth(140);
229 auto mainLayout =
new QVBoxLayout;
230 mainLayout->addLayout(buttons_field_HBox);
231 mainLayout->addWidget(cameraAnglesGroup);
232 mainLayout->addWidget(lightAnglesGroup);
233 mainLayout->addLayout(sliceLayout);
234 setLayout(mainLayout);
243 void G4DisplayView::changeCameraDirection() {
245 string command =
"/vis/viewer/set/viewpointThetaPhi " +
246 to_string(cameraTheta->value()) +
" " +
247 to_string(cameraPhi->value());
249 G4UImanager::GetUIpointer()->ApplyCommand(command);
258 void G4DisplayView::changeLightDirection() {
259 string command =
"/vis/viewer/set/lightsThetaPhi " +
260 to_string(lightTheta->value()) +
" " +
261 to_string(lightPhi->value());
262 G4UImanager::GetUIpointer()->ApplyCommand(command);
273 void G4DisplayView::slice() {
274 G4UImanager* g4uim = G4UImanager::GetUIpointer();
275 if (g4uim ==
nullptr) {
return; }
283 g4uim->ApplyCommand(
"/vis/viewer/clearCutawayPlanes");
285 if (sliceSectn->isChecked()) { g4uim->ApplyCommand(
"/vis/viewer/set/cutawayMode intersection"); }
286 else if (sliceUnion->isChecked()) { g4uim->ApplyCommand(
"/vis/viewer/set/cutawayMode union"); }
288 g4uim->ApplyCommand(
"/vis/viewer/clearCutawayPlanes");
290 if (sliceXActi->isChecked()) {
291 string command =
"/vis/viewer/addCutawayPlane " + sliceXEdit->text().toStdString() +
" 0 0 mm " +
292 to_string(sliceXInve->isChecked() ? -1 : 1) +
" 0 0 ";
293 cout <<
"X " << command << endl;
294 g4uim->ApplyCommand(command);
297 if (sliceYActi->isChecked()) {
298 string command =
"/vis/viewer/addCutawayPlane 0 " + sliceYEdit->text().toStdString() +
" 0 mm 0 " +
299 to_string(sliceYInve->isChecked() ? -1 : 1) +
" 0 ";
300 cout <<
"Y " << command << endl;
301 g4uim->ApplyCommand(command);
304 if (sliceZActi->isChecked()) {
305 string command =
"/vis/viewer/addCutawayPlane 0 0 " + sliceZEdit->text().toStdString() +
" mm 0 0 " +
306 to_string(sliceZInve->isChecked() ? -1 : 1);
307 cout <<
"Z " << command << endl;
308 g4uim->ApplyCommand(command);
320 void G4DisplayView::clearSlices() {
321 G4UImanager::GetUIpointer()->ApplyCommand(
"/vis/viewer/clearCutawayPlanes");
322 sliceXActi->setChecked(
false);
334 void G4DisplayView::apply_buttons_set1(
int index) {
335 G4UImanager* g4uim = G4UImanager::GetUIpointer();
336 if (g4uim ==
nullptr) {
return; }
338 bool button_state = buttons_set1->lastButtonState();
341 string command = string(
"/vis/viewer/set/hiddenEdge") + (button_state ?
" 1" :
" 0");
342 g4uim->ApplyCommand(command);
343 g4uim->ApplyCommand(
"/vis/viewer/flush");
345 else if (index == 1) {
346 if (button_state == 0) {
347 glDisable(GL_LINE_SMOOTH);
348 glDisable(GL_POLYGON_SMOOTH);
351 glEnable(GL_LINE_SMOOTH);
352 glHint(GL_LINE_SMOOTH_HINT, GL_NICEST);
353 glEnable(GL_POLYGON_SMOOTH);
354 glHint(GL_POLYGON_SMOOTH_HINT, GL_NICEST);
357 else if (index == 2) {
358 string command = string(
"/vis/viewer/set/auxiliaryEdge") + (button_state ?
" 1" :
" 0");
359 g4uim->ApplyCommand(command);
360 command = string(
"/vis/viewer/set/hiddenEdge") + (button_state ?
" 1" :
" 0");
361 g4uim->ApplyCommand(command);
362 if (buttons_set1->buttonStatus(0) != button_state) { buttons_set1->toggleButton(0); }
364 else if (index == 3) {
365 if (button_state == 0) {
366 string command = string(
"vis/scene/activateModel Field 0");
367 g4uim->ApplyCommand(command);
368 g4uim->ApplyCommand(
"/vis/scene/removeModel Field");
371 string npoints = to_string(field_NPOINTS);
372 string command = string(
"/vis/scene/add/magneticField ") + npoints;
373 g4uim->ApplyCommand(command);
384 void G4DisplayView::field_precision_changed() {
385 G4UImanager* g4uim = G4UImanager::GetUIpointer();
386 if (g4uim ==
nullptr) {
return; }
387 field_NPOINTS = field_npoints->text().toInt();
388 if (buttons_set1->buttonStatus(3) == 1) {
389 string command = string(
"vis/scene/activateModel Field 0");
390 g4uim->ApplyCommand(command);
391 g4uim->ApplyCommand(
"/vis/scene/removeModel Field");
393 string npoints = to_string(field_NPOINTS);
394 command = string(
"/vis/scene/add/magneticField ") + npoints;
395 G4UImanager::GetUIpointer()->ApplyCommand(command);
G4DisplayView(GOptions *gopts, std::shared_ptr< GLogger > logger, QWidget *parent=nullptr)
Constructs the G4DisplayView widget.
G4Camera getG4Camera(GOptions *gopts)