OSDN Git Service

オブジェクト単位の面反転機能を実装
[qtgeoviewer/QtGeoViewer.git] / Src / QtGeoViewer / FormMain.cpp
1 #include "stdafx.h"
2 #include "FormMain.h"
3
4 #include <QFileInfo>
5 #include <fstream>
6 #include <sstream>
7
8 #include <cassert>
9 #include <QSettings>
10
11 #include "FormVertexBuilder.h"
12 #include "FullScreenPanel.h"
13
14 #include <Qt5Utility/QGui.h>
15
16 #include <QMessageBox>
17 #include <QFileDialog>
18 #include <QPrintDialog>
19 #include <QPrintPreviewDialog>
20
21 #include "BuildInfo.h"
22 #include "PathInfo.h"
23 #include "PostprocLibrary.h"
24 #include "SampleShapeBuilder.h"
25 #include "ShaderLibrary.h"
26 #include "QGVAboutDlg.h"
27
28 #include "FormCustomShader.h"
29 #include "FormPyScript.h"
30 #include "MatcapSelectDlg.h"
31 #include "EnvmapSelectDlg.h"
32 #include "FileDlgUtil.h"
33
34
35
36 QColor ToQColor(const lib_graph::color4f& c)
37 {
38         int r = lm::clamp(0, (int)(c.r() * 255.0f), 255);
39         int g = lm::clamp(0, (int)(c.g() * 255.0f), 255);
40         int b = lm::clamp(0, (int)(c.b() * 255.0f), 255);
41         int a = lm::clamp(0, (int)(c.a() * 255.0f), 255);
42
43         return QColor(r, g, b, a);
44 }
45
46
47
48 FormMain::FormMain(QWidget *parent)
49         : QMainWindow(parent)
50         , m_MatcapDlg(NULL)
51         , m_EnvmapDlg(NULL)
52         , m_CustomShaderDlg(NULL)
53         , m_PyScriptDlg(NULL)
54 {
55         ui.setupUi(this);
56
57         m_EnableAllFeatures = false;
58         m_LastFocusedDockDlg = NULL;
59
60         setAcceptDrops(true);
61
62         setWindowTitle("QtGeoViewer");
63
64         InitializeGLView();
65         InitializeStatusBar();
66         InitializeMenu();
67         InitializeCoordinateCombobox();
68         Initialize2DViewSrcCombobox();
69         InitializeEventFilter();
70         InitContextMenu();
71
72         InitDataBinding();
73
74         SyncViewSettingsFromGUI();
75         SyncUVViewSettingsFromGUI();
76         SyncSceneSettingsFromGUI();
77         ApplyGeomStateFromGUI();
78         SyncShaderSettingsToGUI();
79
80         ui.toolBar_View->setVisible( ui.actionWindow_ToolBarView->isChecked() );
81
82         UpdateViewTypeFromMenu();
83
84         CenteringSplitter();
85
86         RebuildObjectList();
87
88         InitializeSubDlg();
89
90         InitializeAnimation();
91
92         InitializeFromConfigFiles();
93
94         HideFeatures();
95
96         ResetHoleRange();
97
98         this->show();
99
100         m_InitRect = rect();
101         m_InitRect.translate(pos());
102
103         LoadLastWinPos();
104
105         ProcArguments();
106 }
107
108 FormMain::~FormMain()
109 {
110 }
111
112
113 void FormMain::LoadLastWinPos(void)
114 {
115         QString file = PathInfo::GetPosConfigFilePath();
116         QSettings conf(file, QSettings::IniFormat);
117
118         QVariant v;
119         v = conf.value("main/WindowPos");
120         if (v.isValid())
121         {
122                 QRect r = v.toRect();
123                 int dl = r.left();
124                 int dt = r.top();
125                 int dw = r.width();
126                 int dh = r.height();
127
128                 resize(dw, dh);
129
130                 move(QPoint(dl, dt));
131         }
132
133         v = conf.value("main/WinState");
134         if (v.isValid())
135         {
136                 if (v.toBool())
137                         setWindowState(Qt::WindowMaximized);
138         }
139 }
140
141 void FormMain::SaveWinPos(void)
142 {
143         QString file = PathInfo::GetPosConfigFilePath();
144         QSettings conf(file, QSettings::IniFormat);
145
146         conf.setValue("main/WinState", isMaximized());
147
148         if (isMaximized() || isMinimized())
149         {
150                 setWindowState(Qt::WindowNoState);
151                 QApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
152         }
153
154         QRect r = rect();
155         r.translate(pos());
156
157         conf.setValue("main/WindowPos", r);
158 }
159
160 void FormMain::HideFeatures(void)
161 {
162         bool b = m_EnableAllFeatures;
163
164         ui.actionVertexBuilder->setVisible(b);
165         ui.menuPrintRoot->menuAction()->setVisible(b);
166         ui.actionShadowmap->setVisible(b);
167         ui.actionEnvmap->setVisible(b);
168         ui.actionShaderCustom->setVisible(b);
169         ui.actionWindowCustomShader->setVisible(b);
170         ui.actionPyScript->setVisible(b);
171         ui.actionConsole->setVisible(b);
172         ui.actionReleaseShader->setVisible(b);
173 }
174
175 void FormMain::InitializeEventFilter(void)
176 {
177         ui.editEnvMap->installEventFilter(this);
178         ui.editMatcap->installEventFilter(this);
179
180         ui.editCurrentTexName->installEventFilter(this);
181         ui.editCurrentMatNormalMap->installEventFilter(this);
182         ui.editMatCapEachMaterial->installEventFilter(this);
183 }
184
185 void FormMain::InitDataBinding(void)
186 {
187         InitializeVisiblStateMenu();
188         InitializeUVStateMenu();
189         InitializeSceneStateMenu();
190         InitializeGeomStateMenu();
191         InitializeCursorMenu();
192 }
193
194 void FormMain::InitializeVisiblStateMenu(void)
195 {
196         DataBinderMap& dbmap = m_Binder_ViewConfig;
197
198         View3DConfig& cfg_3d = m_View3d.m_Config;
199
200         dbmap.AddBinder(new MenuBinder(ui.actionDrawBBox            , &cfg_3d.m_DrawBBox            ));
201         dbmap.AddBinder(new MenuBinder(ui.actionFaceVBO             , &cfg_3d.m_EnableFaceVBO       ));
202         dbmap.AddBinder(new MenuBinder(ui.actionVidTopMost          , &cfg_3d.m_ShowVidTopMost      ));
203         dbmap.AddBinder(new MenuBinder(ui.actionDrawBBoxRange       , &cfg_3d.m_DrawBBoxRange       ));
204         dbmap.AddBinder(new MenuBinder(ui.actionWireDispList        , &cfg_3d.m_EnableWireDispList  ));
205         dbmap.AddBinder(new MenuBinder(ui.actionMultisample         , &cfg_3d.m_EnableMultisample   ));
206         dbmap.AddBinder(new MenuBinder(ui.actionCoverageTransparent , &cfg_3d.m_EnableCoverageTrans ));
207         dbmap.AddBinder(new MenuBinder(ui.actionSeparateSpecular    , &cfg_3d.m_SeparateSpecular    ));
208         dbmap.AddBinder(new MenuBinder(ui.actionShowSelVertCoord    , &cfg_3d.m_ShowSelVertCoord    ));
209         dbmap.AddBinder(new MenuBinder(ui.actionHighlightSelected   , &cfg_3d.m_HighlightSelected   ));
210         dbmap.AddBinder(new MenuBinder(ui.actionFixMaterialSilver   , &cfg_3d.m_UseFixMaterial      ));
211         dbmap.AddBinder(new MenuBinder(ui.actionShadowmapBuffer     , &cfg_3d.m_DrawShadowmapBuf    ));
212         dbmap.AddBinder(new MenuBinder(ui.actionEnableTexture3D     , &cfg_3d.m_EnableTexture       ));
213         dbmap.AddBinder(new MenuBinder(ui.actionEnableLighting      , &cfg_3d.m_EnableLighting      ));
214         dbmap.AddBinder(new MenuBinder(ui.actionEnableCulling       , &cfg_3d.m_EnableCullFace      ));
215         dbmap.AddBinder(new MenuBinder(ui.actionDrawWire            , &cfg_3d.m_DrawWire            ));
216         dbmap.AddBinder(new MenuBinder(ui.actionDrawVid             , &cfg_3d.m_DrawVid             ));
217         dbmap.AddBinder(new MenuBinder(ui.actionDrawVertNormal      , &cfg_3d.m_DrawVertNormal      ));
218         dbmap.AddBinder(new MenuBinder(ui.actionDrawVert            , &cfg_3d.m_DrawVert            ));
219         dbmap.AddBinder(new MenuBinder(ui.actionWireVBO             , &cfg_3d.m_EnableWireVBO       ));
220         dbmap.AddBinder(new MenuBinder(ui.actionIndexColorMode      , &cfg_3d.m_IndexMaterial       ));
221         dbmap.AddBinder(new MenuBinder(ui.actionFBMaterial          , &cfg_3d.m_FBMaterial          ));
222         dbmap.AddBinder(new MenuBinder(ui.actionDrawMiniAxis        , &cfg_3d.m_DrawMiniAxis        ));
223         dbmap.AddBinder(new MenuBinder(ui.actionDrawLookPos         , &cfg_3d.m_DrawLookPos         ));
224         dbmap.AddBinder(new MenuBinder(ui.actionDrawLightPos        , &cfg_3d.m_DrawLightPosition   ));
225         dbmap.AddBinder(new MenuBinder(ui.actionDrawGround          , &cfg_3d.m_DrawGround          ));
226         dbmap.AddBinder(new MenuBinder(ui.actionDrawFid             , &cfg_3d.m_DrawFid             ));
227         dbmap.AddBinder(new MenuBinder(ui.actionDrawFace            , &cfg_3d.m_DrawFace            ));
228         dbmap.AddBinder(new MenuBinder(ui.actionCameraRecords       , &cfg_3d.m_DrawCameraRecord    ));
229         dbmap.AddBinder(new MenuBinder(ui.actionDrawAxis            , &cfg_3d.m_DrawAxis            ));
230         dbmap.AddBinder(new MenuBinder(ui.actionDoubleSideShading   , &cfg_3d.m_DoubleSideShading   ));
231         dbmap.AddBinder(new MenuBinder(ui.actionDirectionalLight    , &cfg_3d.m_LightIsDirectional  ));
232         dbmap.AddBinder(new MenuBinder(ui.actionCullFrontOrBack     , &cfg_3d.m_CullAngle_F         ));
233         dbmap.AddBinder(new MenuBinder(ui.actionHighlightMaterial   , &cfg_3d.m_HighlightMaterial   ));
234         dbmap.AddBinder(new MenuBinder(ui.actionCloseVert           , &cfg_3d.m_ShowCloseVertInfo   ));
235         dbmap.AddBinder(new MenuBinder(ui.actionCameraRange         , &cfg_3d.m_DrawRenderRange     ));
236         dbmap.AddBinder(new MenuBinder(ui.actionRenderTime          , &cfg_3d.m_ShowRenderTime      ));
237         dbmap.AddBinder(new MenuBinder(ui.actionUseFixTexture       , &cfg_3d.m_UseFixTexture       ));
238         dbmap.AddBinder(new MenuBinder(ui.actionShowSelVertIdx      , &cfg_3d.m_ShowSelVertIdx      ));
239         dbmap.AddBinder(new MenuBinder(ui.actionShowMeshBound       , &cfg_3d.m_ShowMeshBound       ));
240         dbmap.AddBinder(new MenuBinder(ui.actionPickTransparent     , &cfg_3d.m_PickTransparent     ));
241         dbmap.AddBinder(new MenuBinder(ui.actionFlatShading         , &cfg_3d.m_EnableFlatShade     ));
242         dbmap.AddBinder(new MenuBinder(ui.actionDrawPolylineLenWhl  , &cfg_3d.m_DrawPolylineLenWhl  ));
243         dbmap.AddBinder(new MenuBinder(ui.actionDrawPolylineLen     , &cfg_3d.m_DrawPolylineLen     ));
244         dbmap.AddBinder(new MenuBinder(ui.actionDrawPolylineIdx     , &cfg_3d.m_DrawPolylineIdx     ));
245         dbmap.AddBinder(new MenuBinder(ui.actionDrawPolyline        , &cfg_3d.m_DrawPolyline        ));
246         dbmap.AddBinder(new MenuBinder(ui.actionShowMeasure         , &cfg_3d.m_DrawCameraMeasure   ));
247         dbmap.AddBinder(new MenuBinder(ui.actionFlipMouseMR         , &cfg_3d.m_FlipMouseMR         ));
248         dbmap.AddBinder(new MenuBinder(ui.actionSyncLightToCamera   , &cfg_3d.m_SyncLightTocamera   ));
249
250         for (GuiBinder& binder : dbmap.m_BinderMap)
251         {
252                 MenuBinder* mb = dynamic_cast<MenuBinder*>(&binder);
253                 if (mb != NULL)
254                 {
255                         QAction* a = mb->GetMenu();
256                         connect(
257                                 a,
258                                 SIGNAL(triggered(bool)),
259                                 this,
260                                 SLOT(actionVisibleStates_Triggered(bool)));
261                 }
262         }
263 }
264
265 void FormMain::InitializeUVStateMenu(void)
266 {
267         DataBinderMap& dbmap = m_Binder_UVConfig;
268
269         dbmap.AddBinder(new MenuBinder(ui.actionUVRepeat         , &m_View2d.m_RepeatTexture             ));
270         dbmap.AddBinder(new MenuBinder(ui.actionUseFixTexture2D  , &m_View2d.m_UseFixTexute              ));
271         dbmap.AddBinder(new MenuBinder(ui.actionShowVertex2d     , &m_View2d.m_DrawVerts                 ));
272         dbmap.AddBinder(new MenuBinder(ui.actionShowImage2d      , &m_View2d.m_EnableTexture             ));
273         dbmap.AddBinder(new MenuBinder(ui.actionTextureMipmap    , &m_Scene.m_TexConfig.m_EnableMipmap   ));
274         dbmap.AddBinder(new MenuBinder(ui.actionTextureCompress  , &m_Scene.m_TexConfig.m_EnableCompress ));
275         dbmap.AddBinder(new MenuBinder(ui.actionUVFlipY          , &m_Scene.m_TextureTransform.m_FlipY   ));
276
277         for (GuiBinder& binder : dbmap.m_BinderMap)
278         {
279                 MenuBinder* mb = dynamic_cast<MenuBinder*>(&binder);
280                 if (mb != NULL)
281                 {
282                         QAction* a = mb->GetMenu();
283                         connect(
284                                 a,
285                                 SIGNAL(triggered(bool)),
286                                 this,
287                                 SLOT(actionVisibleStatesUV_Triggered(bool)));
288                 }
289         }
290 }
291
292 void FormMain::InitializeSceneStateMenu(void)
293 {
294         DataBinderMap& dbmap = m_Binder_Scene;
295
296         dbmap.AddBinder(new CheckboxBinder( ui.checkEnvMap         , &m_Scene.m_EnvImg.m_VisibleEnvSphere       ));
297         dbmap.AddBinder(new CheckboxBinder( ui.checkEnvReflection  , &m_Scene.m_EnvImg.m_IsEnableReflection     ));
298         dbmap.AddBinder(new CheckboxBinder( ui.checkShadowEnabled  , &m_Scene.m_ShadowConfig.m_EnableShadow     ));
299         dbmap.AddBinder(new CheckboxBinder( ui.checkSoftShadow     , &m_Scene.m_ShadowConfig.m_EnableSoftShadow ));
300
301         for (GuiBinder& binder : dbmap.m_BinderMap)
302         {
303                 CheckboxBinder* mb = dynamic_cast<CheckboxBinder*>(&binder);
304                 if (mb != NULL)
305                 {
306                         QCheckBox* c = mb->GetCheckBox();
307                         connect(
308                                 c,
309                                 SIGNAL(toggled(bool)),
310                                 this,
311                                 SLOT(actionSceneStates_Toggled(bool)));
312                 }
313         }
314 }
315
316 void FormMain::InitializeCursorMenu(void)
317 {
318         DataBinderMap& dbmap = m_Binder_Cursor;
319
320         Cursor3D& cursor = m_Scene.m_Cursor3d;
321         dbmap.AddBinder(new MenuBinder( ui.actionShowCursor     , &cursor.ShowCursor     ));
322         dbmap.AddBinder(new MenuBinder( ui.actionCursorToDepth  , &cursor.CursorDepth    ));
323         dbmap.AddBinder(new MenuBinder( ui.actionCursorCoord    , &cursor.ShowCoord      ));
324         dbmap.AddBinder(new MenuBinder( ui.actionCheckBaryCoord , &cursor.CheckBaryCoord ));
325         dbmap.AddBinder(new MenuBinder( ui.actionSelectCloseMat , &cursor.SelCloseVert   ));
326         dbmap.AddBinder(new MenuBinder( ui.actionCursorAxis     , &cursor.ShowAxis       ));
327         dbmap.AddBinder(new MenuBinder( ui.actionMeasure        , &cursor.ShowMeasure    ));
328         dbmap.AddBinder(new MenuBinder( ui.actionMeasureLen     , &cursor.ShowMeasureLen ));
329         dbmap.AddBinder(new MenuBinder( ui.actionMeasureXYZ     , &cursor.ShowMeasureXYZ ));
330
331         for (GuiBinder& binder : dbmap.m_BinderMap)
332         {
333                 MenuBinder* mb = dynamic_cast<MenuBinder*>(&binder);
334                 if (mb != NULL)
335                 {
336                         QAction* a = mb->GetMenu();
337                         connect(
338                                 a,
339                                 SIGNAL(triggered(bool)),
340                                 this,
341                                 SLOT(actionCursorMenuStates_Toggled(bool)));
342                 }
343         }
344 }
345
346
347 void FormMain::InitializeGeomStateMenu(void)
348 {
349         AddGeomStateAction( ui.actionCentering  );
350         AddGeomStateAction( ui.actionAutoResize );
351 }
352
353 void FormMain::AddGeomStateAction(const QAction* action)
354 {
355         connect(
356                 action,
357                 SIGNAL(triggered(bool)),
358                 this,
359                 SLOT(actionGeomStates_Triggered(bool)));
360 }
361
362
363 void FormMain::InitializeGLView(void)
364 {
365         ui.GLWidgetMain->setMouseTracking(true);
366         ui.GLWidgetUV->setMouseTracking(true);
367
368         ui.GLWidgetMain->SetViewer(&m_View3d);
369         m_View3d.m_Widgets = &m_Widgets;
370         m_View3d.RegisterScene(&m_Scene);
371         m_View3d.InitializeView(ui.GLWidgetMain);
372
373         ui.GLWidgetUV->SetViewer(&m_View2d);
374         m_View2d.m_Widgets = &m_Widgets;
375         m_View2d.RegisterScene(&m_Scene);
376         m_View2d.InitializeView(ui.GLWidgetUV);
377
378         m_Widgets.AddWidget(ui.GLWidgetMain);
379         m_Widgets.AddWidget(ui.GLWidgetUV);
380
381         // OpenGL\82Ì\83\8a\83X\83g\82Ì\8b¤\97L\89»
382         SetContextShare();
383
384         m_ContextShare.BeginDrawTop();
385
386         m_Scene.Initialize();
387
388         m_ContextShare.EndDrawTop();
389
390         connect(
391                 &m_View3d,
392                 SIGNAL(SelectedObjectChanged(int, int)),
393                 SLOT(View3D_SelectedObjectChanged(int, int)));
394         connect(
395                 &m_View3d,
396                 SIGNAL(SelectedMatChanged(int)),
397                 SLOT(View3D_SelectedMatChanged(int)));
398         connect(
399                 &m_View3d,
400                 SIGNAL(CameraMoved(void)),
401                 SLOT(View3D_CameraMoved(void)));
402         connect(
403                 &m_View3d,
404                 SIGNAL(StatusTipChanged(QString)),
405                 SLOT(View3D_StatusTipChanged(QString)));
406 }
407
408 // OpenGL\82Ì\83\8a\83X\83g\82Ì\8b¤\97L\89»
409 void FormMain::SetContextShare(void)
410 {
411         ui.GLWidgetUV->makeCurrent();
412         m_ContextShare.AddContext( GetDC((HWND)ui.GLWidgetUV->winId()) , wglGetCurrentContext() );
413         ui.GLWidgetUV->doneCurrent();
414
415         ui.GLWidgetMain->makeCurrent();
416         m_ContextShare.AddContext( GetDC((HWND)ui.GLWidgetUV->winId()) , wglGetCurrentContext() );
417         ui.GLWidgetMain->doneCurrent();
418
419         m_ContextShare.MakeShare();
420 }
421
422 void FormMain::InitializeCoordinateCombobox(void)
423 {
424         ui.comboCoordinate->blockSignals(true);
425         ui.comboCoordinate->addItem("Yup RH"); // RUF
426         ui.comboCoordinate->addItem("Zup RH"); // FRU
427         ui.comboCoordinate->addItem("Xup RH"); // UFR
428         ui.comboCoordinate->addItem("Yup LH"); // RUB
429         ui.comboCoordinate->addItem("Zup LH"); // BRU
430         ui.comboCoordinate->addItem("Xup LH"); // UBR
431         ui.comboCoordinate->blockSignals(false);
432 }
433
434 void FormMain::Initialize2DViewSrcCombobox(void)
435 {
436         ui.combo2DViewSrcType->blockSignals(true);
437         ui.combo2DViewSrcType->addItem("Color");
438         ui.combo2DViewSrcType->addItem("Normal");
439         ui.combo2DViewSrcType->blockSignals(false);
440 }
441
442 void FormMain::InitializeStatusBar(void)
443 {
444         m_StatusBar0 = new QLabel(this);
445         m_StatusBar1 = new QLabel(this);
446         ui.statusBar->addWidget(m_StatusBar0, 1);
447         ui.statusBar->addWidget(m_StatusBar1, 0);
448
449         m_StatusBar0->setText("");
450
451         m_StatusBar1->setMinimumWidth(290);
452         m_StatusBar1->setText("");
453 }
454
455 void FormMain::InitializeFromConfigFiles(void)
456 {
457         if (!InitializeConfig(PathInfo::GetGuiConfigFilePath()))
458         {
459                 InitializeConfig(PathInfo::GetDefaultGuiConfigFilePath());
460         }
461
462         OpenCameraFile(PathInfo::GetCameraLogFilePath());
463
464         LoadWindowLayout(PathInfo::GetWindowLayoutConfigFilePath());
465
466         if (!QGui::LoadGUIState(this, PathInfo::GetLayoutConfigFilePath()))
467         {
468                 QGui::LoadGUIState(this, PathInfo::GetDefaultLayoutConfigFilePath());
469         }
470 }
471
472 void FormMain::LoadDefaultConfig(void)
473 {
474         InitializeConfig(PathInfo::GetDefaultGuiConfigFilePath());
475         QGui::LoadGUIState(this, PathInfo::GetDefaultLayoutConfigFilePath());
476 }
477
478 void FormMain::SaveConfig(void)
479 {
480         PathInfo::CreateConfiDirIfNotExist();
481
482         SaveConfigFile(PathInfo::GetGuiConfigFilePath());
483
484         m_View3d.m_CameraRecord.SaveCamera(PathInfo::GetCameraLogFilePath().toLocal8Bit().data());
485
486         QGui::SaveGUIState(this, PathInfo::GetLayoutConfigFilePath());
487
488         SaveWindowLayout(PathInfo::GetWindowLayoutConfigFilePath());
489 }
490
491 bool FormMain::InitializeConfig(QString path)
492 {
493         View3DConfig& config_3d = m_View3d.m_Config;
494
495         GuiConfig cfg;
496         cfg.m_Config3D = &config_3d;
497         cfg.m_Scene    = &m_Scene;
498
499         if (!cfg.LoadConfigT(path.toLocal8Bit().data()))
500                 return false;
501
502         ui.actionUVAutoFit->setChecked(cfg.m_AutFitUVView);
503
504         ui.comboCoordinate->setCurrentIndex(cfg.m_CoordType);
505
506         CreateRecentFilesMenu(cfg.m_RecentFiles);
507
508         m_Binder_ViewConfig.UpdateAllGUI(true);
509         m_Binder_UVConfig.UpdateAllGUI(true);
510         m_Binder_Scene.UpdateAllGUI(true);
511         m_Binder_Cursor.UpdateAllGUI(true);
512
513         ApplyGeomStateDataoToGUI();
514
515         SyncViewSettingsFromGUI();
516         SyncUVViewSettingsFromGUI();
517         SyncShaderSettingsToGUI();
518
519         m_EnableAllFeatures = cfg.m_EnableAllFeatures;
520
521         return true;
522 }
523
524 void FormMain::SaveConfigFile(QString path)
525 {
526         GuiConfig cfg;
527         cfg.m_Config3D = &m_View3d.m_Config;
528         cfg.m_Scene    = &m_Scene;
529
530         cfg.m_EnableAllFeatures = m_EnableAllFeatures;
531
532         cfg.m_AutFitUVView = ui.actionUVAutoFit ->isChecked();
533
534         cfg.m_CoordType = ui.comboCoordinate->currentIndex();
535
536         CreateRecentFilesFromMenu(cfg.m_RecentFiles);
537
538         cfg.SaveConfigT(path.toLocal8Bit().data());
539 }
540
541
542 void FormMain::InitializeSubDlg(void)
543 {
544         connect(
545                 &m_WireColorSelDlg,
546                 SIGNAL(currentColorChanged(const QColor &)),
547                 this,
548                 SLOT(WireOverlayColorChanged(const QColor &)));
549         connect(
550                 &m_DiffuseColorSelDlg,
551                 SIGNAL(currentColorChanged(const QColor &)),
552                 this,
553                 SLOT(FaceDiffuseColorChanged(const QColor &)));
554         connect(
555                 &m_BGColorSelDlg,
556                 SIGNAL(currentColorChanged(const QColor &)),
557                 this,
558                 SLOT(BGColorChanged(const QColor &)));
559         connect(
560                 &m_SelMatColorSelDlg,
561                 SIGNAL(currentColorChanged(const QColor &)),
562                 this,
563                 SLOT(SelMatColorChanged(const QColor &)));
564
565         m_SelMatColorWidget = NULL;
566
567         m_ViewConfigDlg.InitializeConfigDlg(&m_View3d.m_Config);
568         connect(
569                 &m_ViewConfigDlg,
570                 SIGNAL(ConfigChanged()),
571                 this,
572                 SLOT(ConfigChangedDlg_ConfigChanged()));
573
574         m_CrossSectionDlg.InitializeConfigDlg(&m_View3d);
575         connect(
576                 &m_CrossSectionDlg,
577                 SIGNAL(ConfigChanged()),
578                 this,
579                 SLOT(CrossSectionDlg_ConfigChanged()));
580 }
581
582 void FormMain::InitializeAnimation(void)
583 {
584         connect(
585                 &m_RotationTimer,
586                 SIGNAL(timeout()),
587                 this,
588                 SLOT(OnRotateTimerUpdated()));
589         m_RotationTimer.setInterval(20);
590 }
591
592 void FormMain::InitializeMenu(void)
593 {
594         m_AGroup_Window = new QActionGroup(this);
595         m_AGroup_Window->setExclusive(true);
596         m_AGroup_Window->addAction( ui.actionWindow_3DView    );
597         m_AGroup_Window->addAction( ui.actionWindow_UVView    );
598         m_AGroup_Window->addAction( ui.actionWindows_DualView );
599
600         m_AGroup_Shader = new QActionGroup(this);
601         m_AGroup_Shader->setExclusive(true);
602         m_AGroup_Shader->addAction( ui.actionShaderDefault   );
603         m_AGroup_Shader->addAction( ui.actionShaderPhong     );
604         m_AGroup_Shader->addAction( ui.actionShaderCustom    );
605         m_AGroup_Shader->addAction( ui.actionNormalColor     );
606         m_AGroup_Shader->addAction( ui.actionDepthColor      );
607         m_AGroup_Shader->addAction( ui.actionShadowmap       );
608         m_AGroup_Shader->addAction( ui.actionEnvmap          );
609         m_AGroup_Shader->addAction( ui.actionIntegrateShader );
610         m_AGroup_Shader->addAction( ui.actionMatcapShader    );
611
612         m_AGroup_PProc = new QActionGroup(this);
613         m_AGroup_PProc->addAction( ui.actionPostProcNone            );
614         m_AGroup_PProc->addAction( ui.actionPostProcAntialias       );
615         m_AGroup_PProc->addAction( ui.actionPostProcBorder          );
616         m_AGroup_PProc->addAction( ui.actionPostProcDepthLayerColor );
617         m_AGroup_PProc->addAction( ui.actionPostProcDepthColor      );
618         m_AGroup_PProc->addAction( ui.actionPostProcDepthOfField    );
619 }
620
621 void FormMain::InitContextMenu(void)
622 {
623         QList<QAction*> actions;
624         actions
625                 << ui.actionSelObjectVisible
626                 << ui.actionSelObjectVertexOnlyMode
627                 << ui.actionSelObjectDelete
628                 << ui.actionSelObjectReload
629                 << ui.actionSelObjectFlipFace
630                 << ui.actionSelObjectOpenDir
631                 << ui.actionActionSelObjectShowOnlyOnce
632                 << ui.actionSelObjectTriangulate;
633
634         QTreeWidget* obj_tree = ui.treeObjects;
635
636         obj_tree->setContextMenuPolicy(Qt::ActionsContextMenu);
637         obj_tree->addActions(actions);
638 }
639
640 void FormMain::ProcArguments(void)
641 {
642         QStringList args = QApplication::arguments();
643         for (int i = 1; i < args.size(); ++i)
644         {
645                 QString s = args[i];
646                 OpenGeomFile(s);
647         }
648 }
649
650 void FormMain::closeEvent(QCloseEvent *e)
651 {
652         SaveWinPos();
653
654         SaveConfig();
655
656         e->accept();
657
658         m_ViewConfigDlg.close();
659         m_CrossSectionDlg.close();
660         m_FullscreenPanel.close();
661
662         if (m_CustomShaderDlg != NULL)
663                 m_CustomShaderDlg->close();
664         if (m_PyScriptDlg != NULL)
665                 m_PyScriptDlg->close();
666
667         if (m_MatcapDlg != NULL)
668                 m_MatcapDlg->close();
669         if (m_EnvmapDlg != NULL)
670                 m_EnvmapDlg->close();
671
672         m_ContextShare.BeginDrawTop();
673         m_Scene.FinalizeScene();
674         m_ContextShare.EndDrawTop();
675 }
676
677
678 bool FormMain::eventFilter(QObject * filterobj, QEvent * filterevt)
679 {
680         if (filterobj == ui.editEnvMap)
681         {
682                 if (filterevt->type() == QEvent::DragEnter)
683                         return AcceptDropFilterIfUrl(filterevt);
684
685                 if (filterevt->type() == QEvent::Drop)
686                         return OnDropFile_editEnvMap(filterevt);
687         }
688         else if (filterobj == ui.editMatcap)
689         {
690                 if (filterevt->type() == QEvent::DragEnter)
691                         return AcceptDropFilterIfUrl(filterevt);
692
693                 if (filterevt->type() == QEvent::Drop)
694                         return OnDropFile_editMatcap(filterevt);
695         }
696         else if (filterobj == ui.editMatCapEachMaterial)
697         {
698                 if (filterevt->type() == QEvent::DragEnter)
699                         return AcceptDropFilterIfUrl(filterevt);
700
701                 if (filterevt->type() == QEvent::Drop)
702                         return OnDropFile_editMatcapEachMat(filterevt);
703         }
704         else if (filterobj == ui.editCurrentTexName)
705         {
706                 if (filterevt->type() == QEvent::DragEnter)
707                         return AcceptDropFilterIfUrl(filterevt);
708
709                 if (filterevt->type() == QEvent::Drop)
710                         return OnDropFile_editCurrentTexName(filterevt);
711         }
712         else if (filterobj == ui.editCurrentMatNormalMap)
713         {
714                 if (filterevt->type() == QEvent::DragEnter)
715                         return AcceptDropFilterIfUrl(filterevt);
716
717                 if (filterevt->type() == QEvent::Drop)
718                         return OnDropFile_editCurrentMatNormalMap(filterevt);
719         }
720
721         return QMainWindow::eventFilter(filterobj, filterevt);
722 }
723
724 bool FormMain::OnDropFile_editEnvMap(QEvent * filterevt)
725 {
726         QString path = GetFirstLoadableImagePathFromDragEvent(filterevt);
727         if (!path.isEmpty())
728                 LoadEnvMap(path);
729
730         return true;
731 }
732
733 bool FormMain::OnDropFile_editMatcap(QEvent * filterevt)
734 {
735         QString path = GetFirstLoadableImagePathFromDragEvent(filterevt);
736         if (!path.isEmpty())
737                 LoadMatcapImage(path);
738
739         return true;
740 }
741
742 bool FormMain::OnDropFile_editMatcapEachMat(QEvent * filterevt)
743 {
744         QString path = GetFirstLoadableImagePathFromDragEvent(filterevt);
745         if (!path.isEmpty())
746                 LoadMatcapImageForCurrentMat(path);
747
748         return true;
749 }
750
751 bool FormMain::OnDropFile_editCurrentTexName(QEvent * filterevt)
752 {
753         QString path = GetFirstLoadableImagePathFromDragEvent(filterevt);
754         if (!path.isEmpty())
755                 LoadCurSelMatTexture(TextureType::Color, path);
756
757         return true;
758 }
759
760 bool FormMain::OnDropFile_editCurrentMatNormalMap(QEvent * filterevt)
761 {
762         QString path = GetFirstLoadableImagePathFromDragEvent(filterevt);
763         if (!path.isEmpty())
764                 LoadCurSelMatTexture(TextureType::Normal, path);
765
766         return true;
767 }
768
769 bool FormMain::AcceptDropFilterIfUrl(QEvent * filterevt)
770 {
771         QDragEnterEvent* e = dynamic_cast<QDragEnterEvent*>(filterevt);
772         if (e == NULL)
773                 return false;
774
775         if (e->mimeData()->hasUrls())
776                 e->acceptProposedAction();
777
778         return true;
779 }
780
781 QString FormMain::GetFirstLoadableImagePathFromDragEvent(QEvent* filterevt)
782 {
783         QDropEvent* e = dynamic_cast<QDropEvent*>(filterevt);
784         if (e == NULL)
785                 return false;
786
787         if (!e->mimeData()->hasUrls())
788                 return false;
789
790         QList<QUrl> urls = e->mimeData()->urls();
791         for (int i = 0; i < urls.size(); ++i)
792         {
793                 QString path = urls[i].toLocalFile();
794                 if (IsSupportedTextureExt(path))
795                         return path;
796         }
797
798         return QString();
799 }
800
801
802 void FormMain::CenteringSplitter(void)
803 {
804         int w = ui.splitter->width();
805         QList<int> s;
806         s.append(w / 2);
807         s.append(w / 2);
808         ui.splitter->setSizes(s);
809 }
810
811 void FormMain::updateView_All(void)
812 {
813         updateView_3D();
814         updateView_2D();
815 }
816
817 void FormMain::updateView_2D(void)
818 {
819         ui.GLWidgetUV->update();
820 }
821
822 void FormMain::updateView_3D(void)
823 {
824         ui.GLWidgetMain->update();
825 }
826
827 void FormMain::on_actionOpen_triggered()
828 {
829         FileDlgFilterList exts;
830         exts.Add( "Wavefront"   , "obj" );
831         exts.Add( "STL"         , "stl" );
832         exts.Add( "PLY"         , "ply" );
833         exts.Add( "Metasequoia" , "mqo" );
834         exts.Add( "Pmd"         , "pmd" );
835         exts.Add( "Collada"     , "dae" );
836         exts.Add( "DirectX"     , "x"   );
837
838         QString filter = FileDlgUtil::ExtListToDlgFilter("Geometry", exts);
839         QString title = "Open file";
840         QString fileName = GetFilePathFromOpenDlg(title, filter);
841
842         if (fileName.isEmpty())
843                 return;
844
845         if (IsResetSceneOnBeforeLoadFile())
846                 ClearAllObjects();
847
848         if (OpenGeomFile(fileName))
849                 return;
850 }
851
852 void FormMain::on_actionExit_triggered()
853 {
854         close();
855 }
856
857 void FormMain::actionVisibleStates_Triggered(bool checked)
858 {
859         QAction* a = dynamic_cast<QAction*>(QObject::sender());
860         if (checked)
861         {
862                 if (a == ui.actionIndexColorMode)
863                 {
864                         ui.actionFixMaterialSilver->setChecked(false);
865                         ui.actionFBMaterial->setChecked(false);
866                 }
867                 else if (a == ui.actionFixMaterialSilver)
868                 {
869                         ui.actionIndexColorMode->setChecked(false);
870                         ui.actionFBMaterial->setChecked(false);
871                 }
872                 else if (a == ui.actionFBMaterial)
873                 {
874                         ui.actionFixMaterialSilver->setChecked(false);
875                         ui.actionIndexColorMode->setChecked(false);
876                 }
877         }
878
879         SyncViewSettingsFromGUI();
880         updateView_All();
881 }
882
883 void FormMain::SyncViewSettingsFromGUI(void)
884 {
885         m_Binder_ViewConfig.UpdateAllData();
886
887         QAction* menu = GetMenuFromShader(m_View3d.m_Config.m_ShaderMode);
888         if (menu != NULL)
889                 menu->setChecked(true);
890 }
891
892 QAction* FormMain::GetMenuFromShader(ShaderType type)
893 {
894         switch(m_View3d.m_Config.m_ShaderMode)
895         {
896         case ShaderType::Phong      : return ui.actionShaderPhong;
897         case ShaderType::Custom     : return ui.actionShaderCustom;
898         case ShaderType::NormalColor: return ui.actionNormalColor;
899         case ShaderType::DepthColor : return ui.actionDepthColor;
900         case ShaderType::Shadowmap  : return ui.actionShadowmap;
901         case ShaderType::Envmap     : return ui.actionEnvmap;
902         case ShaderType::Integrate  : return ui.actionIntegrateShader;
903         case ShaderType::Matcap     : return ui.actionMatcapShader;
904         case ShaderType::Default    : return ui.actionShaderDefault;
905
906         default:
907                 assert(false);
908                 return NULL;
909         };
910 }
911
912 bool FormMain::SaveWindowLayout(const QString& filepath)
913 {
914         WindowConfig config;
915
916         config.m_MainWinLeft   = geometry().x();
917         config.m_MainWinTop    = geometry().y();
918         config.m_MainWinWidth  = geometry().width();
919         config.m_MainWinHeight = geometry().height();
920         config.m_IsMaximized   = isMaximized();
921
922         return config.SaveConfig(filepath.toLocal8Bit().data());
923 }
924
925 bool FormMain::LoadWindowLayout(const QString& filepath)
926 {
927         WindowConfig config;
928         if (!config.LoadConfig(filepath.toLocal8Bit().data()))
929                 return false;
930
931         if (config.m_IsMaximized)
932                 showMaximized();
933
934         int l = config.m_MainWinLeft;
935         int t = config.m_MainWinTop;
936         int w = config.m_MainWinWidth;
937         int h = config.m_MainWinHeight;
938         setGeometry(l, t, w, h);
939
940         return true;
941 }
942
943 void FormMain::actionVisibleStatesUV_Triggered(bool)
944 {
945         SyncUVViewSettingsFromGUI();
946 }
947
948 void FormMain::SyncUVViewSettingsFromGUI(void)
949 {
950         m_Binder_UVConfig.UpdateAllData();
951         updateView_All();
952 }
953
954 void FormMain::actionSceneStates_Toggled(bool)
955 {
956         SyncSceneSettingsFromGUI();
957 }
958
959 void FormMain::SyncSceneSettingsFromGUI(void)
960 {
961         m_Binder_Scene.UpdateAllData();
962         updateView_All();
963 }
964
965 void FormMain::on_actionWindow_ToolBarView_triggered(bool checked)
966 {
967         ui.toolBar_View->setVisible( ui.actionWindow_ToolBarView->isChecked() );
968 }
969
970 void FormMain::on_actionToolBar_Options_toggled(bool checked)
971 {
972         ui.toolBar_Option->setVisible(checked);
973 }
974
975 void FormMain::on_actionToolBar_Operation_toggled(bool checked)
976 {
977         ui.toolBar_Operation->setVisible(checked);
978 }
979
980 void FormMain::on_actionCameraDist_triggered()
981 {
982         m_View3d.AdjustCameraDistAuto();
983 }
984
985 void FormMain::on_actionCameraFront_triggered()
986 {
987         m_View3d.MoveCaemraTo(ViewPoint::Front);
988 }
989
990 void FormMain::on_actionCameraBack_triggered()
991 {
992         m_View3d.MoveCaemraTo(ViewPoint::Back);
993 }
994
995 void FormMain::on_actionCameraLeft_triggered()
996 {
997         m_View3d.MoveCaemraTo(ViewPoint::Left);
998 }
999
1000 void FormMain::on_actionCameraRight_triggered()
1001 {
1002         m_View3d.MoveCaemraTo(ViewPoint::Right);
1003 }
1004
1005 void FormMain::on_actionCameraTop_triggered()
1006 {
1007         m_View3d.MoveCaemraTo(ViewPoint::Top);
1008 }
1009
1010 void FormMain::on_actionCameraBottom_triggered()
1011 {
1012         m_View3d.MoveCaemraTo(ViewPoint::Bottom);
1013 }
1014
1015 void FormMain::on_actionCameraPers_triggered()
1016 {
1017         m_View3d.MoveCaemraTo(ViewPoint::Perse);
1018 }
1019
1020 void FormMain::on_actionCameraLookOrigin_triggered()
1021 {
1022         m_View3d.MoveLookPosToOrigin();
1023 }
1024
1025 void FormMain::on_actionCameraLookCenter_triggered()
1026 {
1027         m_View3d.MoveLookPosToCenter();
1028 }
1029
1030 void FormMain::on_actionWindow_3DView_triggered(bool checked)
1031 {
1032         UpdateViewTypeFromMenu();
1033 }
1034
1035 void FormMain::on_actionWindows_DualView_triggered(bool checked)
1036 {
1037         UpdateViewTypeFromMenu();
1038 }
1039
1040 void FormMain::on_actionWindow_UVView_triggered(bool checked)
1041 {
1042         UpdateViewTypeFromMenu();
1043 }
1044
1045 void FormMain::UpdateViewTypeFromMenu(void)
1046 {
1047         if (ui.actionWindows_DualView->isChecked())
1048         {
1049                 ui.frameView3D->setVisible(true);
1050                 ui.frameView2D->setVisible(true);
1051
1052                 // TODO: \89¼. \8bN\93®\8e\9e\82É\83r\83\85\81[\82ð1:1\82É\90Ý\92è\82Å\82«\82È\82¢\96â\91è\82Ì\89¼\91Î\89\9e.
1053                 static bool firsttime = true;
1054                 if (firsttime)
1055                 {
1056                         firsttime = false;
1057                         CenteringSplitter();
1058                 }
1059         }
1060         if (ui.actionWindow_3DView->isChecked())
1061         {
1062                 ui.frameView3D->setVisible(true);
1063                 ui.frameView2D->setVisible(false);
1064         }
1065         if (ui.actionWindow_UVView->isChecked())
1066         {
1067                 ui.frameView3D->setVisible(false);
1068                 ui.frameView2D->setVisible(true);
1069         }
1070 }
1071
1072 void FormMain::on_actionWindowMaterialList_triggered()
1073 {
1074         ShowAndActivateAndRaise(ui.dockMaterial);
1075         ui.listMaterial->setFocus();
1076 }
1077
1078 void FormMain::on_actionWindowObjectList_triggered()
1079 {
1080         ShowAndActivateAndRaise(ui.dockObject);
1081         ui.treeObjects->setFocus();
1082 }
1083
1084 void FormMain::on_actionWindowCameraList_triggered()
1085 {
1086         ShowAndActivateAndRaise(ui.dockCamera);
1087         ui.listCamera->setFocus();
1088 }
1089
1090 void FormMain::on_actionWindowScenePanel_triggered()
1091 {
1092         ShowAndActivateAndRaise(ui.dockScene);
1093 }
1094
1095 void FormMain::on_listMaterial_currentItemChanged(QListWidgetItem *current, QListWidgetItem *previous)
1096 {
1097         m_Scene.m_Sels.SetSelMat(ui.listMaterial->currentRow());
1098         OnChangedSelectedMaterial();
1099         updateView_All();
1100 }
1101
1102 void FormMain::ShowAndActivateAndRaise(QDockWidget* widget)
1103 {
1104         widget->setVisible(true);
1105         widget->activateWindow();
1106         widget->raise();
1107 }
1108
1109 void FormMain::on_treeObjects_currentItemChanged(QTreeWidgetItem * current, QTreeWidgetItem * previous)
1110 {
1111         RefreshObjectSelectState();
1112 }
1113
1114 void FormMain::RefreshObjectSelectState(void)
1115 {
1116         SetPrimayrSelectObjectToScene();
1117
1118         QListWidget* list_mat = ui.listMaterial;
1119         list_mat->clear();
1120
1121         const MeshBuf* mbuf = m_Scene.GetPrimaryMeshbuf();
1122         if (mbuf != NULL)
1123         {
1124                 const lib_geo::BaseMesh& mesh = mbuf->m_Mesh;
1125                 for (const lib_geo::BaseMaterial& mat : mesh.m_Materials)
1126                 {
1127                         const std::string& name = mat.m_Name;
1128
1129                         if (name.empty())
1130                                 list_mat->addItem("--");
1131                         else
1132                                 list_mat->addItem(QString::fromLocal8Bit(name.c_str()));
1133                 }
1134         }
1135
1136         const GeomObject* obj = m_Scene.GetPrimaryObject();
1137         if (mbuf != NULL)
1138         {
1139                 ui.actionSelObjectVisible->setChecked(mbuf->IsVisible());
1140         }
1141         else if (obj != NULL)
1142         {
1143                 ui.actionSelObjectVisible->setChecked(obj->m_Visible);
1144         }
1145         
1146         if (obj != NULL)
1147                 ui.actionSelObjectVertexOnlyMode->setChecked(obj->m_VertexOnlyMode);
1148
1149         if (list_mat->count() > 0 && list_mat->currentRow() < 0)
1150         {
1151                 list_mat->setCurrentRow(0);
1152                 m_Scene.m_Sels.SetSelMat(0);
1153                 OnChangedSelectedMaterial();
1154         }
1155
1156         updateView_All();
1157 }
1158
1159 void FormMain::OnChangedSelectedMaterial(void)
1160 {
1161         if (IsAutUVFit())
1162         {
1163                 m_View2d.FitView();
1164         }
1165
1166         ui.editCurrentTexName->clear();
1167
1168         GeomTextureSet* ts = m_Scene.GetSelectedTexture();
1169         if (ts == NULL)
1170         {
1171                 ui.editCurrentTexName->setText("");
1172                 ui.editMatCapEachMaterial->setText("");
1173         }
1174         else
1175         {
1176                 QString name_c, name_n;
1177
1178                 gl::GlTexture* tex_c = ts->GetTexColor();
1179                 if (tex_c != NULL)
1180                         name_c = QString::fromLocal8Bit(tex_c->GetName().c_str());
1181
1182                 gl::GlTexture* tex_n = ts->GetTexNormal();
1183                 if (tex_n != NULL)
1184                         name_n = QString::fromLocal8Bit(tex_n->GetName().c_str());
1185
1186                 ui.editCurrentTexName->setText(name_c);
1187                 ui.editCurrentMatNormalMap->setText(name_n);
1188
1189                 MatcapImage& matcap = ts->TexMatcap;
1190                 ui.editMatCapEachMaterial->setText(matcap.GetName());
1191         }
1192
1193         lib_geo::BaseMaterial* mat = m_Scene.GetSelectedMaterial();
1194         if (mat != NULL)
1195         {
1196                 SetWidgetColor(ui.colorAmbient  , ToQColor(mat->m_Ambient));
1197                 SetWidgetColor(ui.colorEmission , ToQColor(mat->m_Emission));
1198                 SetWidgetColor(ui.colorDiffuse  , ToQColor(mat->m_Diffuse));
1199                 SetWidgetColor(ui.colorSpecular , ToQColor(mat->m_Specular));
1200
1201                 int val_max = ui.sliderShininess->maximum();
1202                 int slider_pos = (int)(mat->m_Shininess * (float)val_max / 200.0f);
1203                 slider_pos = (lm::min)(val_max, slider_pos);
1204                 ui.sliderShininess->blockSignals(true);
1205                 ui.sliderShininess->setValue(slider_pos);
1206                 ui.sliderShininess->blockSignals(false);
1207                 ui.labelShininessVal->setText(QString::number(mat->m_Shininess, 'f', 2));
1208         }
1209
1210         updateView_All();
1211 }
1212
1213 void FormMain::keyPressEvent(QKeyEvent *e)
1214 {
1215         Modifier m(e);
1216         if (m.Flag_C() && e->key() == Qt::Key_Tab)
1217         {
1218                 FocusNextSubDlg();
1219         }
1220 }
1221
1222 void FormMain::FocusNextSubDlg(void)
1223 {
1224         std::vector<QDockWidget*> widgets;
1225
1226         if (ui.dockObject   ->isVisible()) widgets.push_back( ui.dockObject   );
1227         if (ui.dockCamera   ->isVisible()) widgets.push_back( ui.dockCamera   );
1228         if (ui.dockScene    ->isVisible()) widgets.push_back( ui.dockScene    );
1229         if (ui.dockMaterial ->isVisible()) widgets.push_back( ui.dockMaterial );
1230
1231         if (widgets.empty())
1232                 return;
1233
1234         QDockWidget* next_widget = NULL;
1235
1236         for (size_t i = 0; i < widgets.size(); ++i)
1237         {
1238                 if (widgets[i] == m_LastFocusedDockDlg)
1239                 {
1240                         next_widget = widgets[(i + 1) % widgets.size()];
1241                         break;
1242                 }
1243         }
1244
1245         if (next_widget == NULL)
1246                 next_widget = widgets.front();
1247
1248         m_LastFocusedDockDlg = next_widget;
1249
1250         next_widget->activateWindow();
1251         next_widget->raise();
1252         next_widget->setFocus();
1253 }
1254
1255 void FormMain::dragEnterEvent(QDragEnterEvent* e)
1256 {
1257         if (e->mimeData()->hasUrls())
1258                 e->acceptProposedAction();
1259 }
1260
1261 void FormMain::dropEvent(QDropEvent* e)
1262 {
1263         if (e->mimeData()->hasUrls())
1264         {
1265                 QList<QUrl> urls = e->mimeData()->urls();
1266
1267                 std::vector<QString> geom_files;
1268
1269                 for (int i = 0; i < urls.size(); ++i)
1270                 {
1271                         QString path = urls[i].toLocalFile();
1272                         if (FormatType::IsGeomFileExt(path))
1273                                 geom_files.push_back(path);
1274                 }
1275
1276                 if (!geom_files.empty())
1277                 {
1278                         if (IsResetSceneOnBeforeLoadFile())
1279                                 ClearAllObjects();
1280
1281                         for (size_t i = 0; i < geom_files.size(); ++i)
1282                         {
1283                                 if (OpenGeomFile(geom_files[i]))
1284                                         continue;
1285                         }
1286                 }
1287
1288                 for (int i = 0; i < urls.size(); ++i)
1289                 {
1290                         QString path = urls[i].toLocalFile();
1291
1292                         if (IsSupportedTextureExt(path))
1293                         {
1294                                 OpenFixTextureFile(path);
1295                                 continue;
1296                         }
1297
1298                         if (IsCameraFile(path))
1299                         {
1300                                 OpenCameraFile(path);
1301                                 continue;
1302                         }
1303                 }
1304         }
1305 }
1306
1307 bool FormMain::IsResetSceneOnBeforeLoadFile(void) const
1308 {
1309         if (QApplication::keyboardModifiers() & Qt::ShiftModifier)
1310                 return true;
1311
1312         return false;
1313 }
1314
1315 //! \83I\83u\83W\83F\83N\83g\82Ì\83}\83e\83\8a\83A\83\8b\82É\90Ý\92è\82³\82ê\82½\82à\82Ì\82Æ\82Í\95Ê\82Ì\83e\83N\83X\83`\83\83\82ð\8ew\92è\82·\82é.
1316 void FormMain::OpenFixTextureFile(const QString& path)
1317 {
1318         std::string fname = path.toLocal8Bit().data();
1319
1320         m_ContextShare.BeginDrawTop();
1321         m_Scene.LoadDefaultMatTexture(fname);
1322         m_ContextShare.EndDrawTop();
1323
1324         updateView_All();
1325 }
1326
1327 bool FormMain::OpenGeomFile(const QString& path)
1328 {
1329         m_Scene.m_ObjSplit = ui.checkSplitOBJ->isChecked();
1330
1331         m_ContextShare.BeginDrawTop();
1332
1333         bool suc = true;
1334         try
1335         {
1336                 m_Scene.ImportFileAutoFmt(path);
1337         }
1338         catch(const FileLoadErrorException& ex)
1339         {
1340                 QString msg;
1341                 msg += "Failed Load ";
1342                 msg += path + "\n\n";
1343                 msg += QString::fromLocal8Bit(ex.what());
1344
1345                 QMessageBox::warning(this, "", msg);
1346                 suc = false;
1347         }
1348
1349         m_ContextShare.EndDrawTop();
1350
1351         RebuildObjectList();
1352
1353         updateView_All();
1354
1355         if (!suc)
1356                 return false;
1357
1358         AddRecentFile(path);
1359
1360         return true;
1361 }
1362
1363 void FormMain::ClearAllObjects(void)
1364 {
1365         m_ContextShare.BeginDrawTop();
1366
1367         m_Scene.ClearObjects();
1368
1369         m_ContextShare.EndDrawTop();
1370
1371         m_View3d.ClearRenderMap();
1372
1373         RebuildObjectList();
1374         RefreshObjectSelectState();
1375
1376         updateView_All();
1377 }
1378
1379 void FormMain::RebuildObjectList(void)
1380 {
1381         QTreeWidget* obj_tree = ui.treeObjects;
1382
1383         obj_tree->setCurrentItem(NULL);
1384         obj_tree->blockSignals(true);
1385
1386         obj_tree->clear();
1387
1388         obj_tree->setSelectionBehavior(QAbstractItemView::SelectRows);
1389         obj_tree->setSelectionMode(QAbstractItemView::SingleSelection);
1390         obj_tree->setEditTriggers(QAbstractItemView::NoEditTriggers);
1391
1392         obj_tree->setColumnCount(4);
1393
1394         InitObjectListHeader();
1395
1396         for (const geom::GeomObject& obj : m_Scene.m_Objects)
1397         {
1398                 QTreeWidgetItem* n = CreateObjectTreeNode(obj);
1399                 PushbackTreeNode(ui.treeObjects, n);
1400                 n->setExpanded(true);
1401         }
1402
1403         SetPrimayrSelectObjectFromScene();
1404
1405         obj_tree->blockSignals(false);
1406
1407         if (obj_tree->currentItem() == NULL)
1408         {
1409                 if (!m_Scene.m_Objects.empty())
1410                 {
1411                         QTreeWidgetItem* ti = obj_tree->topLevelItem(0);
1412                         obj_tree->setCurrentItem(ti);
1413
1414                         if (IsAutUVFit())
1415                                 m_View2d.FitView();
1416                 }
1417         }
1418
1419         ResizeTreeColumns(obj_tree, 4);
1420 }
1421
1422
1423 bool FormMain::IsCameraFile(const QString& path) const
1424 {
1425         QFileInfo fInfo( path );
1426         QString ext = fInfo.suffix().toLower();
1427         return (ext == "camera");
1428 }
1429
1430 bool FormMain::OpenCameraFile(const QString& path)
1431 {
1432         std::string fname = path.toLocal8Bit().data();
1433
1434         if(!m_View3d.m_CameraRecord.LoadCamera(fname.c_str()))
1435                 return false;
1436
1437         ui.listCamera->blockSignals(true);
1438         ui.listCamera->clear();
1439         for (size_t i = 0; i < m_View3d.m_CameraRecord.m_Records.size(); ++i)
1440         {
1441                 ui.listCamera->addItem( QString::number(i) );
1442         }
1443         ui.listCamera->blockSignals(false);
1444
1445         return true;
1446 }
1447
1448
1449 void FormMain::actionGeomStates_Triggered(bool)
1450 {
1451         ApplyGeomStateFromGUI();
1452
1453         m_Scene.UpdateTransform();
1454
1455         updateView_All();
1456 }
1457
1458 void FormMain::ApplyGeomStateFromGUI(void)
1459 {
1460         m_Scene.m_Config.m_EnableAutoCentering = ui.actionCentering->isChecked();
1461         m_Scene.m_Config.m_EnableAutoReisze    = ui.actionAutoResize->isChecked();
1462 }
1463
1464 void FormMain::ApplyGeomStateDataoToGUI(void)
1465 {
1466         ui.actionAutoResize ->setChecked( m_Scene.m_Config.m_EnableAutoReisze    );
1467         ui.actionCentering  ->setChecked( m_Scene.m_Config.m_EnableAutoCentering );
1468
1469         ui.checkShowOnlySelect->setChecked(m_View3d.m_Config.m_ShowOnlySelect);
1470 }
1471
1472 void FormMain::on_actionGeomClear_triggered()
1473 {
1474         ClearAllObjects();
1475 }
1476
1477
1478 void FormMain::on_actionUVFitView_triggered()
1479 {
1480         m_View2d.FitView();
1481         updateView_All();
1482 }
1483
1484 void FormMain::on_actionSelObjectDelete_triggered()
1485 {
1486         DeleteSelectedObject();
1487 }
1488
1489 void FormMain::on_actionSelObjectReload_triggered()
1490 {
1491         GeomObject* obj = m_Scene.GetPrimaryObject();
1492         if (obj == NULL)
1493                 return;
1494
1495         if (!obj->IsFileObject())
1496         {
1497                 QMessageBox::information(this, "", "IsNotFileObject");
1498                 return;
1499         }
1500
1501         m_Scene.ReloadObject(obj);
1502
1503         RebuildObjectList();
1504
1505         updateView_All();
1506 }
1507
1508 void FormMain::on_actionSelObjectVisible_triggered()
1509 {
1510         FlipVisibleSelectedObject();
1511 }
1512
1513 void FormMain::on_actionSelObjectVertexOnlyMode_triggered()
1514 {
1515         GeomObject* obj = m_Scene.GetPrimaryObject();
1516         if (obj == NULL)
1517                 return;
1518
1519         obj->m_VertexOnlyMode = !obj->m_VertexOnlyMode;
1520
1521         ui.actionSelObjectVertexOnlyMode->setChecked(obj->m_VertexOnlyMode);
1522
1523         updateView_All();
1524 }
1525
1526 void FormMain::on_actionSelObjectFlipFace_triggered()
1527 {
1528         GeomObject* geo = m_Scene.GetPrimaryObject();
1529         MeshBuf* mbuf = m_Scene.GetPrimaryMeshbuf();
1530         if (mbuf == NULL && geo == NULL)
1531                 return;
1532
1533         if (mbuf != NULL)
1534         {
1535                 mbuf->FlipFace();
1536         }
1537         else
1538         {
1539                 for (MeshBuf& m : geo->m_MeshAry)
1540                 {
1541                         m.FlipFace();
1542                 }
1543         }
1544
1545         ui.GLWidgetMain->makeCurrent();
1546         m_View3d.ReleaseRenderbuffer(mbuf);
1547         ui.GLWidgetMain->doneCurrent();
1548
1549         updateView_All();
1550 }
1551
1552 void FormMain::on_actionSelObjectOpenDir_triggered()
1553 {
1554         GeomObject* obj = m_Scene.GetPrimaryObject();
1555         if (obj == NULL)
1556                 return;
1557
1558         if (!obj->IsFileObject())
1559                 return;
1560
1561         QString path = QString::fromLocal8Bit(obj->m_FilePath.c_str());
1562         QString p2 = QDir::toNativeSeparators(path);
1563         QGui::ShowExplorerFileSel(p2);
1564 }
1565
1566 void FormMain::on_actionShowOnlySelected_triggered()
1567 {
1568         ShowObjectOnlySelected();
1569 }
1570
1571 void FormMain::on_actionSelObjectTriangulate_triggered()
1572 {
1573         MeshBuf* mbuf = m_Scene.GetPrimaryMeshbuf();
1574         if (mbuf == NULL)
1575                 return;
1576
1577         mbuf->Triangulate();
1578
1579         m_View3d.ReleaseAllRenderBuffer();
1580
1581         RebuildObjectList();
1582         updateView_All();
1583 }
1584
1585
1586 void FormMain::on_actionAddSample_triggered()
1587 {
1588         SampleShapeBuilder::CreateSphere(m_Scene);
1589         OnDoneAddGeom();
1590 }
1591
1592 void FormMain::on_actionAddGroundPlane_triggered()
1593 {
1594         SampleShapeBuilder::CreateGroundPlane(m_Scene);
1595         OnDoneAddGeom();
1596 }
1597
1598 void FormMain::OnDoneAddGeom(void)
1599 {
1600         QTreeWidget* obj_tree = ui.treeObjects;
1601
1602         const GeomObject& obj = m_Scene.m_Objects.back();
1603
1604         obj_tree->setCurrentItem(NULL);
1605         obj_tree->blockSignals(true);
1606
1607         QTreeWidgetItem* n = CreateObjectTreeNode(obj);
1608         PushbackTreeNode(obj_tree, n);
1609         n->setExpanded(true);
1610
1611         SetPrimayrSelectObjectFromScene();
1612
1613         obj_tree->blockSignals(false);
1614
1615         if (obj_tree->currentItem() == NULL)
1616         {
1617                 if (!m_Scene.m_Objects.empty())
1618                 {
1619                         QTreeWidgetItem * j = obj_tree->topLevelItem(0);
1620                         obj_tree->setCurrentItem(j);
1621
1622                         if (IsAutUVFit())
1623                                 m_View2d.FitView();
1624                 }
1625         }
1626
1627         ResizeTreeColumns(obj_tree, 4);
1628
1629         updateView_All();
1630 }
1631
1632
1633 void FormMain::on_actionShaderDefault_triggered(bool checked)
1634 {
1635         ChangeShaderMenuMain(ShaderType::Default);
1636 }
1637
1638 void FormMain::on_actionShaderPhong_triggered(bool checked)
1639 {
1640         ChangeShaderMenuMain(ShaderType::Phong);
1641 }
1642
1643 void FormMain::on_actionShaderCustom_triggered(bool checked)
1644 {
1645         ChangeShaderMenuMain(ShaderType::Custom);
1646 }
1647
1648 void FormMain::on_actionNormalColor_triggered(bool checked)
1649 {
1650         ChangeShaderMenuMain(ShaderType::NormalColor);
1651 }
1652
1653 void FormMain::on_actionDepthColor_triggered(bool checked)
1654 {
1655         ChangeShaderMenuMain(ShaderType::DepthColor);
1656 }
1657
1658 void FormMain::on_actionShadowmap_triggered(bool checked)
1659 {
1660         ChangeShaderMenuMain(ShaderType::Shadowmap);
1661 }
1662
1663 void FormMain::on_actionEnvmap_triggered(bool checked)
1664 {
1665         ChangeShaderMenuMain(ShaderType::Envmap);
1666 }
1667
1668 void FormMain::on_actionIntegrateShader_triggered(bool checked)
1669 {
1670         ChangeShaderMenuMain(ShaderType::Integrate);
1671 }
1672
1673 void FormMain::on_actionMatcapShader_triggered(bool checked)
1674 {
1675         ChangeShaderMenuMain(ShaderType::Matcap);
1676 }
1677
1678 void FormMain::SyncShaderSettingsToGUI(void)
1679 {
1680         ChangeShaderMenuMain(m_View3d.m_Config.m_ShaderMode);
1681 }
1682
1683 void FormMain::ChangeShaderMenuMain(ShaderType type)
1684 {
1685         m_View3d.m_Config.m_ShaderMode = type;
1686         updateView_All();
1687 }
1688
1689
1690 void FormMain::on_actionCreate_Check_triggered()
1691 {
1692         CreateSampleTextureMain(SampleTextureBuilder::TEX_CHECKER);
1693 }
1694
1695 void FormMain::on_actionCreate_Stripe_V_triggered()
1696 {
1697         CreateSampleTextureMain(SampleTextureBuilder::TEX_STRIPE_V);
1698 }
1699
1700 void FormMain::on_actionCreate_Stripe_H_triggered()
1701 {
1702         CreateSampleTextureMain(SampleTextureBuilder::TEX_STRIPE_H);
1703 }
1704
1705 void FormMain::CreateSampleTextureMain(SampleTextureBuilder::TextureType tex_type)
1706 {
1707         m_ContextShare.BeginDrawTop();
1708         m_Scene.CreateSampleTexture(tex_type);
1709         m_ContextShare.EndDrawTop();
1710
1711         updateView_All();
1712 }
1713
1714 bool FormMain::IsAutUVFit(void) const
1715 {
1716         return ui.actionUVAutoFit->isChecked();
1717 }
1718
1719
1720 void FormMain::on_pushDeleteSelectedObject_clicked()
1721 {
1722         DeleteSelectedObject();
1723 }
1724
1725 void FormMain::on_treeObjects_itemChanged(QTreeWidgetItem * item, int column)
1726 {
1727         QTreeWidget* obj_tree = ui.treeObjects;
1728
1729         if (column == 1)
1730         {
1731                 QTreeWidgetItem* t = item->parent();
1732                 bool checked = (item->checkState(1) == Qt::Checked);
1733                 if (t == NULL)
1734                 {
1735                         int sel_idx = obj_tree->indexOfTopLevelItem(item);
1736                         GeomObject& obj = m_Scene.m_Objects[sel_idx];
1737                         obj.m_Visible = checked;
1738                 }
1739                 else
1740                 {
1741                         int sel_idx = obj_tree->indexOfTopLevelItem(t);
1742                         int midx = t->indexOfChild(item);
1743
1744                         GeomObject& obj = m_Scene.m_Objects[sel_idx];
1745                         MeshBuf& mb = obj.m_MeshAry[midx];
1746                         mb.m_Visible = checked;
1747                 }
1748
1749                 updateView_All();
1750         }
1751 }
1752
1753
1754 void FormMain::DeleteSelectedObject()
1755 {
1756         QTreeWidget* obj_tree = ui.treeObjects;
1757         QTreeWidgetItem* ti = obj_tree->currentItem();
1758         if (ti == NULL)
1759                 return;
1760
1761         QTreeWidgetItem* pn = ti->parent();
1762
1763         int sel_idx;
1764         if (pn == NULL)
1765                 sel_idx = obj_tree->indexOfTopLevelItem(ti);
1766         else
1767                 sel_idx = obj_tree->indexOfTopLevelItem(pn);
1768
1769         if (sel_idx < 0)
1770                 return;
1771
1772         m_ContextShare.BeginDrawTop();
1773
1774         m_Scene.RemoveItem(sel_idx);
1775
1776         m_ContextShare.EndDrawTop();
1777
1778         m_View3d.ClearRenderMap();
1779
1780         obj_tree->setCurrentItem(NULL);
1781         obj_tree->takeTopLevelItem(sel_idx);
1782
1783         ResizeTreeColumns(obj_tree, 4);
1784
1785         ti = obj_tree->currentItem();
1786         sel_idx = obj_tree->indexOfTopLevelItem(ti);
1787         m_Scene.m_Sels.SelectObject(sel_idx);
1788
1789         m_Scene.UpdateTransform();
1790
1791         RefreshObjectSelectState();
1792
1793         updateView_All();
1794 }
1795
1796 void FormMain::FlipVisibleSelectedObject()
1797 {
1798         QTreeWidget* obj_tree = ui.treeObjects;
1799         QTreeWidgetItem * item = obj_tree->currentItem();
1800         if (item == NULL)
1801                 return;
1802
1803         item->setCheckState(1, FilpState(item->checkState(1)));
1804 }
1805
1806 Qt::CheckState FormMain::FilpState(Qt::CheckState state) const
1807 {
1808         if(state == Qt::Checked)
1809                 return Qt::Unchecked;
1810         else
1811                 return Qt::Checked;
1812 }
1813
1814 void FormMain::ShowObjectOnlySelected(void)
1815 {
1816         GeomObject* sel_obj = m_Scene.GetPrimaryObject();
1817         if (sel_obj == NULL)
1818                 return;
1819
1820         for (GeomObject& o : m_Scene.m_Objects)
1821         {
1822                 o.m_Visible = (sel_obj == &o);
1823         }
1824
1825         RebuildObjectList();
1826         updateView_All();
1827 }
1828
1829 void FormMain::ShowAllObject(void)
1830 {
1831         m_Scene.ShowAllObject();
1832
1833         RebuildObjectList();
1834         updateView_All();
1835 }
1836
1837 void FormMain::HideAllObject(void)
1838 {
1839         m_Scene.HideAllObject();
1840
1841         RebuildObjectList();
1842         updateView_All();
1843 }
1844
1845 void FormMain::on_actionUVResetView_triggered()
1846 {
1847         m_View2d.ResetView();
1848
1849         updateView_All();
1850 }
1851
1852
1853 //! \83\8f\83C\83\84\81[\83I\81[\83o\81[\83\8c\83C\95\\8e¦\8e\9e\82Ì\90F\90Ý\92è
1854 void FormMain::on_actionWireColor_triggered()
1855 {
1856         m_WireColorSelDlg.exec();
1857 }
1858
1859 //! \83f\83t\83H\83\8b\83g\83}\83e\83\8a\83A\83\8b\82Ì\90F\90Ý\92è
1860 void FormMain::on_actionFaceColor_triggered()
1861 {
1862         const lib_graph::color4f& c = m_Scene.m_DefaultMaterial.m_Diffuse;
1863
1864         m_DiffuseColorSelDlg.setOption(QColorDialog::ShowAlphaChannel);
1865         m_DiffuseColorSelDlg.setCurrentColor(ToQColor(c));
1866         m_DiffuseColorSelDlg.exec();
1867 }
1868
1869 //! \94w\8ci\90F\82Ì\90Ý\92è
1870 void FormMain::on_actionBackGroundColor_triggered()
1871 {
1872         const lib_graph::color4f& c = m_View3d.m_BGColor;
1873
1874         m_BGColorSelDlg.setCurrentColor(ToQColor(c));
1875         m_BGColorSelDlg.exec();
1876 }
1877
1878 void FormMain::WireOverlayColorChanged(const QColor & color)
1879 {
1880         lib_graph::color3b& c = m_View3d.m_Config.m_WireColor;
1881         c.set(color.red(), color.green(), color.blue());
1882
1883         m_View3d.ReleaseAllRenderBuffer();
1884
1885         updateView_All();
1886 }
1887
1888 void FormMain::CopyRGB(lib_graph::color4f& c, const QColor & color)
1889 {
1890         c.r() = (float)color.red()   / 255.0f;
1891         c.g() = (float)color.green() / 255.0f;
1892         c.b() = (float)color.blue()  / 255.0f;
1893 }
1894
1895 void FormMain::CopyRGBA(lib_graph::color4f& c, const QColor & color)
1896 {
1897         c.r() = (float)color.red()   / 255.0f;
1898         c.g() = (float)color.green() / 255.0f;
1899         c.b() = (float)color.blue()  / 255.0f;
1900         c.a() = (float)color.alpha() / 255.0f;
1901 }
1902
1903 void FormMain::FaceDiffuseColorChanged(const QColor & color)
1904 {
1905         lib_graph::color4f& c = m_Scene.m_DefaultMaterial.m_Diffuse;
1906         CopyRGB(c, color);
1907
1908         m_View3d.ReleaseAllRenderBuffer();
1909         updateView_All();
1910 }
1911
1912 void FormMain::BGColorChanged(const QColor & color)
1913 {
1914         lib_graph::color4f& c = m_View3d.m_BGColor;
1915         CopyRGB(c, color);
1916
1917         updateView_All();
1918 }
1919
1920 void FormMain::SetSelectedMaterialColor(QColor col)
1921 {
1922         lib_geo::BaseMaterial* mat = m_Scene.GetSelectedMaterial();
1923         if (mat == NULL)
1924                 return;
1925
1926         if (m_SelMatColorWidget == ui.colorAmbient  ) CopyRGBA(mat->m_Ambient  , col);
1927         if (m_SelMatColorWidget == ui.colorEmission ) CopyRGBA(mat->m_Emission , col);
1928         if (m_SelMatColorWidget == ui.colorDiffuse  ) CopyRGBA(mat->m_Diffuse  , col);
1929         if (m_SelMatColorWidget == ui.colorSpecular ) CopyRGBA(mat->m_Specular , col);
1930
1931         SetWidgetColor(m_SelMatColorWidget, col);
1932 }
1933
1934 void FormMain::SelMatColorChanged(const QColor & color)
1935 {
1936         SetSelectedMaterialColor(color);
1937         m_View3d.ResetPrimaryObjectLists();
1938         updateView_All();
1939 }
1940
1941
1942 void FormMain::on_actionWindowOptions_triggered()
1943 {
1944         m_ViewConfigDlg.showNormal();
1945         m_ViewConfigDlg.show();
1946         m_ViewConfigDlg.activateWindow();
1947 }
1948
1949 void FormMain::on_actionWindowCustomShader_triggered()
1950 {
1951         if (m_CustomShaderDlg == NULL)
1952         {
1953                 m_CustomShaderDlg = new FormCustomShader(this);
1954                 m_CustomShaderDlg->SetShaderLibrary(&m_View3d.m_ShaderLib);
1955                 m_CustomShaderDlg->SetParentWidget(ui.GLWidgetMain);
1956                 m_CustomShaderDlg->LoadOrSetDefaultCode();
1957                 connect(
1958                         m_CustomShaderDlg,
1959                         SIGNAL(ShaderBuild()),
1960                         this,
1961                         SLOT(CustomShaderDlg_ShaderBuild()));
1962         }
1963
1964         m_CustomShaderDlg->showNormal();
1965         m_CustomShaderDlg->show();
1966         m_CustomShaderDlg->activateWindow();
1967 }
1968
1969
1970 void FormMain::ConfigChangedDlg_ConfigChanged()
1971 {
1972         m_View3d.ReleaseAllRenderBuffer();
1973         updateView_All();
1974 }
1975
1976 void FormMain::CrossSectionDlg_ConfigChanged()
1977 {
1978         updateView_All();
1979 }
1980
1981
1982 void FormMain::OnPaintImage(QPrinter *printer)
1983 {
1984         QPainter painter(printer);
1985
1986         QRect rect = painter.viewport();
1987         QSize size = this->size();
1988         size.scale(rect.size(), Qt::KeepAspectRatio);//\8fc\89¡\94ä\88Û\8e\9d
1989
1990         painter.setViewport(rect.x(), rect.y(), size.width(), size.height());
1991         painter.setWindow(this->rect());
1992
1993         this->render(&painter);
1994 }
1995
1996 void FormMain::on_actionPrint_triggered()
1997 {
1998         PrintImage(false);
1999 }
2000
2001 void FormMain::on_actionPrintPreview_triggered()
2002 {
2003         PrintImage(true);
2004 }
2005
2006 void FormMain::PrintImage(bool WithPreview)
2007 {
2008         //QPrinter printer(QPrinter::ScreenResolution);
2009         QPrinter printer(QPrinter::ScreenResolution);
2010
2011         if(WithPreview)
2012         {
2013                 QPrintPreviewDialog preview(&printer, this);
2014                 preview.setWindowFlags( Qt::Window );
2015                 connect(
2016                         &preview,
2017                         SIGNAL(paintRequested(QPrinter *)),
2018                         SLOT(OnPaintImage(QPrinter *)));
2019
2020                 preview.showMaximized();
2021                 preview.exec();
2022         }
2023         else
2024         {
2025                 QPrintDialog printDialog(&printer, this);
2026                 if(printDialog.exec() == QDialog::Accepted)
2027                         OnPaintImage(&printer);
2028         }
2029 }
2030
2031
2032 void FormMain::on_pushButtonAddCameraRecord_clicked()
2033 {
2034         m_View3d.RecordCamera();
2035
2036         ui.listCamera->addItem( QString::number(ui.listCamera->count()) );
2037
2038         updateView_3D();
2039 }
2040
2041 void FormMain::on_pushButtonDeleteCameraRecord_clicked()
2042 {
2043         int idx = ui.listCamera->currentRow();
2044         if(idx < 0)
2045                 return;
2046
2047         m_View3d.RemoveRecordedCamera(idx);
2048
2049         for (int i = idx+1; i < ui.listCamera->count(); ++i)
2050         {
2051                 ui.listCamera->item(i)->setText(QString::number(i - 1));
2052         }
2053
2054         ui.listCamera->takeItem(idx);
2055
2056         updateView_3D();
2057 }
2058
2059 void FormMain::on_pushCameraRecordClear_clicked()
2060 {
2061         m_View3d.ClearRecordedCamera();
2062
2063         ui.listCamera->clear();
2064
2065         updateView_3D();
2066 }
2067
2068 void FormMain::on_listCamera_itemDoubleClicked(QListWidgetItem *item)
2069 {
2070         int idx = ui.listCamera->currentRow();
2071         if (idx < 0)
2072                 return;
2073
2074         m_View3d.MoveToRecordedCamera(idx, ui.checkCameraAnimation->isChecked());
2075 }
2076
2077 void FormMain::on_actionSaveCamera_triggered()
2078 {
2079         QString title = "camera";
2080         QString filter = "Camera File(*.camera)";
2081         QString fileName = GetFilePathFromSaveDlg(title, filter);
2082         if (fileName.isEmpty())
2083                 return;
2084
2085         m_View3d.m_CameraRecord.SaveCamera(fileName.toLocal8Bit().data());
2086 }
2087
2088 void FormMain::on_actionProjectionOrtho_triggered()
2089 {
2090         ui.actionProjectionOrtho->setChecked(true);
2091         ui.actionProjectionPers->setChecked(false);
2092
2093         m_View3d.m_Camera.m_ProjMode = gl::Camera::PROJ_ORTHO;
2094
2095         updateView_All();
2096 }
2097
2098 void FormMain::on_actionProjectionPers_triggered()
2099 {
2100         ui.actionProjectionPers->setChecked(true);
2101         ui.actionProjectionOrtho->setChecked(false);
2102
2103         m_View3d.m_Camera.m_ProjMode = gl::Camera::PROJ_PERS;
2104
2105         updateView_All();
2106 }
2107
2108
2109 void FormMain::CustomShaderDlg_ShaderBuild()
2110 {
2111         updateView_All();
2112 }
2113
2114 void FormMain::OnRotateTimerUpdated()
2115 {
2116         static const float rot_speed = 0.005f;
2117
2118         if (ui.actionRotateCamera->isChecked())
2119         {
2120                 m_View3d.m_Camera.m_Manip.Tumble(rot_speed, 0.0f);
2121                 UpdateCameraStatus();
2122         }
2123
2124         if (ui.actionRotateLight->isChecked())
2125                 m_View3d.m_ControlLight.m_Position.rotate_y(rot_speed);
2126
2127         updateView_3D();
2128 }
2129
2130 void FormMain::on_actionRotateCamera_toggled(bool checked)
2131 {
2132         ToggleLightCamera();
2133 }
2134
2135 void FormMain::on_actionRotateLight_toggled(bool checked)
2136 {
2137         ToggleLightCamera();
2138 }
2139
2140 void FormMain::ToggleLightCamera(void)
2141 {
2142         bool camera_rotate = ui.actionRotateCamera->isChecked();
2143         bool light_rotate  = ui.actionRotateLight->isChecked();
2144
2145         if (camera_rotate || light_rotate)
2146                 m_RotationTimer.start();
2147         else
2148                 m_RotationTimer.stop();
2149 }
2150
2151 void FormMain::on_actionCrossSectionDlg_triggered()
2152 {
2153         m_CrossSectionDlg.showNormal();
2154         m_CrossSectionDlg.show();
2155         m_CrossSectionDlg.activateWindow();
2156 }
2157
2158 void FormMain::on_actionSelectNext_triggered()
2159 {
2160         AddSelectObjectIdx(1);
2161 }
2162
2163 void FormMain::on_actionSelectPrev_triggered()
2164 {
2165         AddSelectObjectIdx(-1);
2166 }
2167
2168 void FormMain::AddSelectObjectIdx(int step)
2169 {
2170         QTreeWidget* obj_tree = ui.treeObjects;
2171
2172         int num_obj = obj_tree->topLevelItemCount();
2173         if (num_obj == 0)
2174                 return;
2175
2176         QTreeWidgetItem * i = obj_tree->currentItem();
2177         int idx = obj_tree->indexOfTopLevelItem(i);
2178         idx += step;
2179
2180         if (0 > idx)
2181                 idx = num_obj - 1;
2182         else if (idx >= num_obj)
2183                 idx = 0;
2184
2185         QTreeWidgetItem * j = obj_tree->topLevelItem(idx);
2186         obj_tree->setCurrentItem(j);
2187 }
2188
2189 void FormMain::on_actionSwitchVisible_triggered()
2190 {
2191         FlipVisibleSelectedObject();
2192 }
2193
2194 void FormMain::on_actionActionSelObjectShowOnlyOnce_triggered()
2195 {
2196         ShowObjectOnlySelected();
2197 }
2198
2199 void FormMain::on_actionHideAll_triggered()
2200 {
2201         HideAllObject();
2202 }
2203
2204 void FormMain::on_actionShowAll_triggered()
2205 {
2206         ShowAllObject();
2207 }
2208
2209 void FormMain::on_actionVertexBuilder_triggered()
2210 {
2211         FormVertexBuilder builder;
2212         builder.CreateVertex(m_Scene);
2213
2214         RebuildObjectList();
2215         updateView_All();
2216 }
2217
2218 void FormMain::on_actionFullScreen_triggered()
2219 {
2220         m_FullscreenPanel.ShowWidgetAsFullscreen(ui.splitter, ui.gridLayout_4);
2221 }
2222
2223 void FormMain::on_actionResetConfig_triggered()
2224 {
2225         QString msg = QString::fromLocal8Bit("\90Ý\92è\82ð\83\8a\83Z\83b\83g\82µ\82Ü\82·");
2226         if (QMessageBox::question(this, "", msg, QMessageBox::Ok|QMessageBox::Cancel) != QMessageBox::Ok)
2227                 return;
2228
2229         setGeometry(m_InitRect);
2230
2231         LoadDefaultConfig();
2232
2233         SyncViewSettingsFromGUI();
2234         SyncUVViewSettingsFromGUI();
2235         ApplyGeomStateFromGUI();
2236         SyncShaderSettingsToGUI();
2237 }
2238
2239 QString FormMain::GetFilePathFromOpenDlg(const QString& title, const QString& filter)
2240 {
2241         QString default_path = GetNextDefaultPathForFileDlg();
2242         QString s = QFileDialog::getOpenFileName(this, title, default_path, filter);
2243
2244         if (!s.isEmpty())
2245                 m_LastFileDialogDir = QFileInfo(s).absolutePath();
2246
2247         return s;
2248 }
2249
2250 QString FormMain::GetFilePathFromSaveDlg(const QString& title, const QString& filter)
2251 {
2252         QString default_path = GetNextDefaultPathForFileDlg();
2253         QString s = QFileDialog::getSaveFileName(this, title, default_path, filter);
2254
2255         if (!s.isEmpty())
2256                 m_LastFileDialogDir = QFileInfo(s).absolutePath();
2257
2258         return s;
2259 }
2260
2261 bool FormMain::IsSupportedTextureExt(const QString& path) const
2262 {
2263         QString ext = QFileInfo(path).suffix().toLower();
2264
2265         std::map<QString, bool> types;
2266         types[ "png"  ] = true;
2267         types[ "jpg"  ] = true;
2268         types[ "jepg" ] = true;
2269         types[ "bmp"  ] = true;
2270         types[ "tif"  ] = true;
2271         types[ "tiff" ] = true;
2272
2273         return types[ext];
2274 }
2275
2276 QString FormMain::GetSupportedImageFilePathFromDlg(const QString& title)
2277 {
2278         FileDlgFilterList exts;
2279         exts.Add( "Png" , "png"  );
2280         exts.Add( "Jpg" , "jpg"  );
2281         exts.Add( "Jpg" , "jpeg" );
2282         exts.Add( "Bmp" , "bmp"  );
2283         exts.Add( "Tif" , "tif"  );
2284         exts.Add( "Tif" , "tiff" );
2285
2286         QString filter = FileDlgUtil::ExtListToDlgFilter("Image", exts);
2287         return GetFilePathFromOpenDlg(title, filter);
2288 }
2289
2290
2291 QString FormMain::GetNextDefaultPathForFileDlg(void)
2292 {
2293         if (m_LastFileDialogDir.isEmpty())
2294                 return PathInfo::GetMyDocDirPath();
2295
2296         return m_LastFileDialogDir;
2297 }
2298
2299
2300 void FormMain::on_toolLoadEnvMap_clicked()
2301 {
2302         QString fileName = GetSupportedImageFilePathFromDlg("Open envmap");
2303         if (fileName.isEmpty())
2304                 return;
2305
2306         LoadEnvMap(fileName);
2307 }
2308
2309 void FormMain::LoadEnvMap(QString& path)
2310 {
2311         m_ContextShare.BeginDrawTop();
2312         m_Scene.m_EnvImg.LoadTexture(path.toLocal8Bit().data());
2313         m_ContextShare.EndDrawTop();
2314
2315         QString title = QFileInfo(path).fileName();
2316         ui.editEnvMap->setText(title);
2317
2318         updateView_All();
2319 }
2320
2321 void FormMain::on_buttonReleaseEnvImg_clicked()
2322 {
2323         m_ContextShare.BeginDrawTop();
2324         m_Scene.m_EnvImg.ClearEnv();
2325         m_ContextShare.EndDrawTop();
2326
2327         ui.editEnvMap->clear();
2328
2329         updateView_All();
2330 }
2331
2332 void FormMain::on_buttonPresetEnvMap_clicked()
2333 {
2334         if (m_EnvmapDlg == NULL)
2335         {
2336                 m_EnvmapDlg = new EnvmapSelectDlg(this);
2337                 connect(
2338                         m_EnvmapDlg,
2339                         SIGNAL(ListSelectChanged()),
2340                         this,
2341                         SLOT(EnvmapDlg_ListSelectChanged()));
2342         }
2343
2344         m_EnvmapDlg->show();
2345 }
2346
2347 void FormMain::EnvmapDlg_ListSelectChanged()
2348 {
2349         QString p = m_EnvmapDlg->GetSelectedItemPath();
2350         if (p.isEmpty())
2351                 return;
2352
2353         LoadEnvMap(p);
2354 }
2355
2356 void FormMain::on_toolLoadMatcap_clicked()
2357 {
2358         QString fileName = GetSupportedImageFilePathFromDlg("Open matcap");
2359         if (fileName.isEmpty())
2360                 return;
2361
2362         LoadMatcapImage(fileName);
2363 }
2364
2365 void FormMain::on_buttonReleaseMatcap_clicked()
2366 {
2367         m_ContextShare.BeginDrawTop();
2368         m_Scene.m_MatcapImg.ClearEnv();
2369         m_ContextShare.EndDrawTop();
2370
2371         ui.editMatcap->clear();
2372
2373         updateView_All();
2374 }
2375
2376 void FormMain::on_buttonLoadMatcapPreset_clicked()
2377 {
2378         if (m_MatcapDlg == NULL)
2379         {
2380                 m_MatcapDlg = new MatcapSelectDlg(this);
2381                 connect(
2382                         m_MatcapDlg,
2383                         SIGNAL(ListSelectChanged()),
2384                         this,
2385                         SLOT(MatcapDlg_ListSelectChanged()));
2386         }
2387
2388         m_MatcapDlg->show();
2389 }
2390
2391 void FormMain::MatcapDlg_ListSelectChanged()
2392 {
2393         QString p = m_MatcapDlg->GetSelectedItemPath();
2394         if (p.isEmpty())
2395                 return;
2396
2397         LoadMatcapImage(p);
2398 }
2399
2400 void FormMain::on_sliderEnvReflection_valueChanged(int value)
2401 {
2402         float r = GetSliderNormalizedPos(ui.sliderEnvReflection);
2403         m_Scene.m_EnvImg.m_EnvReflection = r;
2404
2405         updateView_All();
2406 }
2407
2408
2409 void FormMain::on_comboCoordinate_currentIndexChanged(int index)
2410 {
2411         SceneTransform& transform = m_Scene.m_WorldTransform;
2412
2413         int idx = ui.comboCoordinate->currentIndex();
2414         switch (idx)
2415         {
2416         case 0: transform.SetCoordType(geom::SceneTransform::COORD_RUF); break;
2417         case 1: transform.SetCoordType(geom::SceneTransform::COORD_FRU); break;
2418         case 2: transform.SetCoordType(geom::SceneTransform::COORD_UFR); break;
2419         case 3: transform.SetCoordType(geom::SceneTransform::COORD_RUB); break;
2420         case 4: transform.SetCoordType(geom::SceneTransform::COORD_BRU); break;
2421         case 5: transform.SetCoordType(geom::SceneTransform::COORD_UBR); break;
2422         default:
2423                 break;
2424         }
2425
2426         updateView_All();
2427 }
2428
2429 void FormMain::on_sliderShadowDarkness_valueChanged(int value)
2430 {
2431         int b = ui.sliderShadowDarkness->minimum();
2432         int t = ui.sliderShadowDarkness->maximum();
2433
2434         float r = (float)(value - b) / (float)(t - b);
2435         m_Scene.m_ShadowConfig.m_ShadowDarkness = r;
2436
2437         updateView_All();
2438 }
2439
2440 void FormMain::on_buttonClearAllGeoms_clicked()
2441 {
2442         ClearAllObjects();
2443 }
2444
2445 //! \83J\83\81\83\89\88Ê\92u\95\9c\8c³\8b@\94\\8eg\97p\8e\9e\82Ì\83A\83j\83\81\81[\83V\83\87\83\93\97L\96³
2446 void FormMain::on_checkCameraAnimation_toggled(bool checked)
2447 {
2448 }
2449
2450
2451 void FormMain::on_actionOpenAppdir_triggered()
2452 {
2453         PathInfo::OpenAppDir();
2454 }
2455
2456 void FormMain::on_actionOpenConfigDir_triggered()
2457 {
2458         PathInfo::OpenConfigDir();
2459 }
2460
2461 void FormMain::on_buttonDecGridAxis_clicked()
2462 {
2463         m_View3d.m_GridAxisScale /= 10.0f;
2464         updateView_3D();
2465 }
2466
2467 void FormMain::on_buttonIncGridAxis_clicked()
2468 {
2469         m_View3d.m_GridAxisScale *= 10.0f;
2470         updateView_3D();
2471 }
2472
2473 void FormMain::on_buttonResetGridAxis_clicked()
2474 {
2475         m_View3d.m_GridAxisScale = 1.0f;
2476         updateView_3D();
2477 }
2478
2479
2480 void FormMain::View3D_SelectedObjectChanged(int sel_obj, int sel_mesh)
2481 {
2482         QTreeWidgetItem* on = ui.treeObjects->topLevelItem(sel_obj);
2483
2484         if (sel_mesh == -1)
2485         {
2486                 ui.treeObjects->setCurrentItem(on);
2487         }
2488         else
2489         {
2490                 QTreeWidgetItem* mn = on->child(sel_mesh);
2491                 ui.treeObjects->setCurrentItem(mn);
2492         }
2493 }
2494
2495 void FormMain::View3D_SelectedMatChanged(int sel_idx)
2496 {
2497         ui.listMaterial->setCurrentRow(sel_idx);
2498 }
2499
2500 void FormMain::View3D_CameraMoved(void)
2501 {
2502         UpdateCameraStatus();
2503 }
2504
2505 void FormMain::View3D_StatusTipChanged(QString msg)
2506 {
2507         //ui.statusBar->showMessage(msg, 1500);
2508 }
2509
2510 void FormMain::UpdateCameraStatus(void)
2511 {
2512         const Camera& camera = m_View3d.m_Camera;
2513         const lib_gl::CameraManipulator& manip = camera.m_Manip;
2514         const lm::vec3f& vp = manip.m_ViewPos;
2515
2516         float a, b;
2517         manip.GetViewAngles(a, b);
2518         a = a * 180.0f / M_PI;
2519         b = b * 180.0f / M_PI;
2520
2521         QString msg;
2522         msg += "(";
2523         msg += QString::number(vp.x, 'f', 2) + " ";
2524         msg += QString::number(vp.y, 'f', 2) + " ";
2525         msg += QString::number(vp.z, 'f', 2);
2526         msg += ")";
2527
2528         msg += "(";
2529         msg += QString::number(a, 'f', 2) + " ";
2530         msg += QString::number(b, 'f', 2);
2531         msg += ")";
2532
2533         msg += "(";
2534         msg += QString::number(camera.m_Projection.m_Near, 'f', 2) + " ";
2535         msg += QString::number(camera.m_Projection.m_Far, 'f', 2);
2536         msg += ")";
2537
2538         m_StatusBar1->setText(msg);
2539 }
2540
2541 void FormMain::on_actionCameraFPSMode_toggled(bool arg1)
2542 {
2543         m_View3d.m_FpsMode = arg1;
2544 }
2545
2546
2547 void FormMain::actionCursorMenuStates_Toggled(bool)
2548 {
2549         m_Binder_Cursor.UpdateAllData();
2550         updateView_3D();
2551 }
2552
2553 void FormMain::on_actionResetCursor_triggered()
2554 {
2555         m_Scene.m_Cursor3d.ResetCursorPos();
2556         m_Scene.m_Cursor3d.UpdateNormal(m_View3d.m_Camera.m_Manip.GetFront());
2557         updateView_3D();
2558 }
2559
2560 void FormMain::on_actionResetMeasure_triggered()
2561 {
2562         m_View3d.ResetCursorMeasure();
2563         updateView_3D();
2564 }
2565
2566
2567 void FormMain::on_actionPyScript_triggered()
2568 {
2569         if (m_PyScriptDlg == NULL)
2570         {
2571                 m_PyScriptDlg = new FormPyScript(this);
2572                 m_PyScriptDlg->m_Scene = &m_Scene;
2573                 m_PyScriptDlg->m_View3d = &m_View3d;
2574                 m_PyScriptDlg->m_View2d = &m_View2d;
2575         }
2576
2577         m_PyScriptDlg->showNormal();
2578         m_PyScriptDlg->show();
2579         m_PyScriptDlg->activateWindow();
2580 }
2581
2582 void FormMain::on_actionConsole_triggered()
2583 {
2584         ::AllocConsole();
2585         freopen( "CON", "r", stdin  );
2586         freopen( "CON", "w", stdout );
2587 }
2588
2589
2590 void FormMain::on_actionClearVertSelect_triggered()
2591 {
2592         m_Scene.ClearAllVertSelect();
2593         updateView_All();
2594 }
2595
2596
2597 void FormMain::on_action_About_triggered()
2598 {
2599         QGVAboutDlg dlg;
2600         dlg.exec();
2601 }
2602
2603 void FormMain::on_action_Association_triggered()
2604 {
2605         m_AssociationDlg.exec();
2606 }
2607
2608 void FormMain::on_actionLookDepth_triggered()
2609 {
2610         m_View3d.LookDepth();
2611 }
2612
2613 void FormMain::on_actionLook3DCursor_triggered()
2614 {
2615         m_View3d.Look3DCursor();
2616 }
2617
2618 void FormMain::on_sliderLightPower_valueChanged(int value)
2619 {
2620         float val = (float)ui.sliderLightPower->value();
2621         float val_max = (float)ui.sliderLightPower->maximum();
2622         float n = 2.0f * val / val_max;
2623         
2624         m_View3d.SetLightStrengthByStdRatio(n);
2625
2626         ui.labelLightPower->setText(QString("LightPower ") + QString::number(n, 'f', 2));
2627
2628         updateView_All();
2629 }
2630
2631 void FormMain::on_buttonResetLightPower_clicked()
2632 {
2633         ui.sliderLightPower->setValue(1000);
2634 }
2635
2636 void FormMain::on_checkHoleAroundCursor_clicked(bool checked)
2637 {
2638         if (checked)
2639                 ui.checkShowOnlyAroundCursor->setChecked(false);
2640
2641         if (checked)
2642                 m_Scene.m_Cursor3d.CircleClip = Cursor3DCircleClip::Hole;
2643         else
2644                 m_Scene.m_Cursor3d.CircleClip = Cursor3DCircleClip::None;
2645
2646         updateView_All();
2647 }
2648
2649 void FormMain::on_checkShowOnlyAroundCursor_toggled(bool checked)
2650 {
2651         if (checked)
2652                 ui.checkHoleAroundCursor->setChecked(false);
2653
2654         if (checked)
2655                 m_Scene.m_Cursor3d.CircleClip = Cursor3DCircleClip::ShowAround;
2656         else
2657                 m_Scene.m_Cursor3d.CircleClip = Cursor3DCircleClip::None;
2658
2659         updateView_All();
2660 }
2661
2662 void FormMain::on_sliderCursorHoleRange_valueChanged(int value)
2663 {
2664         float val = (float)ui.sliderCursorHoleRange->value();
2665         float maxval = (float)ui.sliderCursorHoleRange->maximum();
2666         float n = val / maxval;
2667
2668         m_Scene.m_Cursor3d.HoleRangeRatio = n;
2669         updateView_All();
2670 }
2671
2672 void FormMain::on_buttonResetCursorHoleRange_clicked()
2673 {
2674         ResetHoleRange();
2675 }
2676
2677 void FormMain::ResetHoleRange(void)
2678 {
2679         ui.sliderCursorHoleRange->setValue(500);
2680 }
2681
2682 void FormMain::on_actionSaveImageToMydoc_triggered()
2683 {
2684         QString path = PathInfo::GetMyDocDirPath();
2685         QString basename = path + "/" + "qgv_snap_";
2686
2687         QDateTime dt = QDateTime::currentDateTime();
2688
2689         QString dst;
2690         for(;;)
2691         {
2692                 QString tp = dt.toString("yyyyMMdd_hhmmss_zzz");
2693                 dst = basename + tp + ".png";
2694                 if (!QFile(dst).exists())
2695                         break;
2696         }
2697
2698         ui.GLWidgetMain->grabFrameBuffer().save(dst);
2699 }
2700
2701 void FormMain::on_actionPostProcNone_triggered()
2702 {
2703         ChangePostprocMode(PostProcType::None);
2704 }
2705
2706 void FormMain::on_actionPostProcAntialias_triggered()
2707 {
2708         ChangePostprocMode(PostProcType::Antialias);
2709 }
2710
2711 void FormMain::on_actionPostProcBorder_triggered()
2712 {
2713         ChangePostprocMode(PostProcType::Border);
2714 }
2715
2716 void FormMain::on_actionPostProcDepthLayerColor_triggered()
2717 {
2718         ChangePostprocMode(PostProcType::DepthLayerColor);
2719 }
2720
2721 void FormMain::on_actionPostProcDepthColor_triggered()
2722 {
2723         ChangePostprocMode(PostProcType::DepthColor);
2724 }
2725
2726 void FormMain::on_actionPostProcDepthOfField_triggered()
2727 {
2728         ChangePostprocMode(PostProcType::DepthOfField);
2729 }
2730
2731 void FormMain::ChangePostprocMode(PostProcType type)
2732 {
2733         m_View3d.m_Config.m_PPMode = type;
2734         updateView_3D();
2735 }
2736
2737 void FormMain::on_sliderDOFPint_valueChanged(int value)
2738 {
2739         float n = GetSliderNormalizedPos(ui.sliderDOFPint);
2740         m_View3d.m_PPContext.m_DOFPintPos = n;
2741
2742         updateView_3D();
2743 }
2744
2745 void FormMain::on_sliderDOFRange_valueChanged(int value)
2746 {
2747         float n = GetSliderNormalizedPos(ui.sliderDOFRange);
2748         m_View3d.m_PPContext.m_DOFRange = 10.0f * n;
2749
2750         updateView_3D();
2751 }
2752
2753 float FormMain::GetSliderNormalizedPos(const QSlider* slider) const
2754 {
2755         float t = (float)slider->maximum();
2756         float b = (float)slider->minimum();
2757         float v = (float)slider->value();
2758
2759         return (v - b) / (t - b);
2760 }
2761
2762 void FormMain::on_buttonResetDOFPint_clicked()
2763 {
2764         ui.sliderDOFPint->setValue(1000);
2765 }
2766
2767 void FormMain::on_buttonResetDOFRange_clicked()
2768 {
2769         ui.sliderDOFRange->setValue(1000);
2770 }
2771
2772 void FormMain::on_actionAddCrossSectionRecord_triggered()
2773 {
2774         m_Scene.AddCrossSectionRecord();
2775         updateView_All();
2776 }
2777
2778 void FormMain::on_actionClearCrossSectionRecord_triggered()
2779 {
2780         m_Scene.ClearCrossSectionRecord();
2781         updateView_All();
2782 }
2783
2784 void FormMain::LoadCurSelMatTexture(TextureType type)
2785 {
2786         QString path = GetSupportedImageFilePathFromDlg("Load Texture");
2787         if (path.isEmpty())
2788                 return;
2789
2790         LoadCurSelMatTexture(type, path);
2791 }
2792
2793 void FormMain::LoadCurSelMatTexture(TextureType type, QString filepath)
2794 {
2795         GeomTextureSet* ts = m_Scene.GetSelectedTexture();
2796         if (ts == NULL)
2797                 return;
2798
2799         MeshBuf* mbuf = ts->GetParent();
2800         std::string fp = filepath.toLocal8Bit().data();
2801
2802         QString name_qs = QFileInfo(filepath).fileName();
2803         std::string name = name_qs.toLocal8Bit().data();
2804
2805         m_ContextShare.BeginDrawTop();
2806
2807         mbuf->ReleaseTextureUnit(ts, type);
2808         gl::GlTexture* tex = mbuf->GetInitTexture(fp, name, m_Scene.m_TexConfig);
2809         ts->SetTextureUnit(type, tex);
2810
2811         if (type == TextureType::Normal)
2812                 m_View3d.ReleaseAllRenderBuffer();
2813
2814         m_ContextShare.EndDrawTop();
2815
2816         OnChangedSelectedMaterial();
2817         updateView_All();
2818 }
2819
2820 void FormMain::ReleaseCurSelTexture(TextureType type)
2821 {
2822         MeshBuf* mbuf = m_Scene.GetPrimaryMeshbuf();
2823         if (mbuf == NULL)
2824                 return;
2825
2826         int mat_idx = m_Scene.m_Sels.GetSelMat();
2827
2828         m_ContextShare.BeginDrawTop();
2829         mbuf->ReleaseTextureUnit(mat_idx, type);
2830         m_ContextShare.EndDrawTop();
2831
2832         OnChangedSelectedMaterial();
2833         updateView_All();
2834 }
2835
2836 void FormMain::LoadMatcapImageForCurrentMat(QString& path)
2837 {
2838         GeomTextureSet* ts = m_Scene.GetSelectedTexture();
2839
2840         QString title = QFileInfo(path).fileName();
2841
2842         m_ContextShare.BeginDrawTop();
2843         ts->TexMatcap.LoadTexture(path.toLocal8Bit().data());
2844         ts->TexMatcap.SetName(title);
2845         m_ContextShare.EndDrawTop();
2846
2847         OnChangedSelectedMaterial();
2848         updateView_All();
2849 }
2850
2851 void FormMain::LoadMatcapImage(QString& path)
2852 {
2853         MatcapImage& mc = m_Scene.m_MatcapImg;
2854
2855         QString title = QFileInfo(path).fileName();
2856
2857         ui.editMatcap->setText(mc.GetName());
2858
2859         m_ContextShare.BeginDrawTop();
2860         mc.LoadTexture(path.toLocal8Bit().data());
2861         mc.SetName(title);
2862         m_ContextShare.EndDrawTop();
2863
2864         updateView_All();
2865 }
2866
2867 void FormMain::on_buttonOpenMatCapEachMaterial_clicked()
2868 {
2869         QString path = GetSupportedImageFilePathFromDlg("Load Texture");
2870         if (path.isEmpty())
2871                 return;
2872
2873         LoadMatcapImage(path);
2874 }
2875
2876 void FormMain::on_buttonClearMatCapEachMaterial_clicked()
2877 {
2878         geom::GeomTextureSet* tex = m_Scene.GetSelectedTexture();
2879         if (tex == NULL)
2880                 return;
2881
2882         m_ContextShare.BeginDrawTop();
2883         tex->TexMatcap.ClearEnv();
2884         m_ContextShare.EndDrawTop();
2885
2886         ui.editMatCapEachMaterial->clear();
2887
2888         updateView_All();
2889 }
2890
2891 void FormMain::on_buttonOpenCurrentMatColorMap_clicked()
2892 {
2893         LoadCurSelMatTexture(TextureType::Color);
2894 }
2895
2896 void FormMain::on_buttonClearCurrentMatColorMap_clicked()
2897 {
2898         ReleaseCurSelTexture(TextureType::Color);
2899 }
2900
2901 void FormMain::on_buttonOpenCurrentMatNormalMap_clicked()
2902 {
2903         LoadCurSelMatTexture(TextureType::Normal);
2904 }
2905
2906 void FormMain::on_buttonClearCurrentMatNormalMap_clicked()
2907 {
2908         ReleaseCurSelTexture(TextureType::Normal);
2909 }
2910
2911 void FormMain::ChangeMatlemColor(QWidget* col_widget)
2912 {
2913         lib_geo::BaseMaterial* mat = m_Scene.GetSelectedMaterial();
2914         if (mat == NULL)
2915                 return;
2916
2917         lib_graph::color4f* col;
2918
2919         if (col_widget == ui.colorAmbient  ) col = &mat->m_Ambient  ;
2920         if (col_widget == ui.colorEmission ) col = &mat->m_Emission ;
2921         if (col_widget == ui.colorDiffuse  ) col = &mat->m_Diffuse  ;
2922         if (col_widget == ui.colorSpecular ) col = &mat->m_Specular ;
2923
2924         lib_graph::color4f src = *col;
2925
2926         QColor dc = ToQColor(*col);
2927
2928         m_SelMatColorWidget = col_widget;
2929
2930         m_SelMatColorSelDlg.setOption(QColorDialog::ShowAlphaChannel);
2931         m_SelMatColorSelDlg.setCurrentColor(dc);
2932         if (m_SelMatColorSelDlg.exec() == QDialog::Rejected)
2933         {
2934                 *col = src;
2935                 SetWidgetColor(col_widget, dc);
2936         }
2937 }
2938
2939 void FormMain::on_buttonDiffuse_clicked()
2940 {
2941         ChangeMatlemColor(ui.colorDiffuse);
2942 }
2943
2944 void FormMain::on_buttonAmbient_clicked()
2945 {
2946         ChangeMatlemColor(ui.colorAmbient);
2947 }
2948
2949 void FormMain::on_buttonEmission_clicked()
2950 {
2951         ChangeMatlemColor(ui.colorEmission);
2952 }
2953
2954 void FormMain::on_buttonSpecular_clicked()
2955 {
2956         ChangeMatlemColor(ui.colorSpecular);
2957 }
2958
2959 void FormMain::SetWidgetColor(QWidget* w, QColor col)
2960 {
2961         QString ss = QString("background-color: %1").arg(col.name());
2962         w->setStyleSheet(ss);
2963 }
2964
2965 void FormMain::on_sliderShininess_valueChanged(int value)
2966 {
2967         lib_geo::BaseMaterial* mat = m_Scene.GetSelectedMaterial();
2968         if (mat == NULL)
2969                 return;
2970
2971         float val = (float)ui.sliderShininess->value();
2972         float val_max = (float)ui.sliderShininess->maximum();
2973
2974         float real_val = 200.0f * val / val_max;
2975
2976         mat->m_Shininess = real_val;
2977
2978         ui.labelShininessVal->setText(QString::number(real_val, 'f', 2));
2979
2980         updateView_All();
2981 }
2982
2983 void FormMain::CreateRecentFilesMenu(const std::vector<QString>& path)
2984 {
2985         QMenu* recents = ui.menuOpenRecent;
2986         recents->actions().clear();
2987
2988         for (size_t i = 0; i < path.size(); ++i)
2989         {
2990                 AddRecentFile(path[path.size() - i - 1]);
2991         }
2992 }
2993
2994 void FormMain::CreateRecentFilesFromMenu(std::vector<QString>& path)
2995 {
2996         QMenu* recents = ui.menuOpenRecent;
2997         for (int i = 0; i < recents->actions().size(); ++i)
2998         {
2999                 QAction* a = recents->actions().at(i);
3000                 path.push_back(a->text());
3001         }
3002 }
3003
3004 void FormMain::AddRecentFile(const QString& path)
3005 {
3006         QString path_local = QDir::toNativeSeparators(path);
3007
3008         static const int max_files = 10;
3009
3010         QMenu* recents = ui.menuOpenRecent;
3011
3012         for (int i = 0; i < recents->actions().size(); ++i)
3013         {
3014                 QAction* a = recents->actions().at(i);
3015                 if (a->text() == path_local)
3016                 {
3017                         recents->removeAction(a);
3018                         break;
3019                 }
3020         }
3021
3022         QAction* new_path = new QAction(path_local, this);
3023         connect(
3024                 new_path,
3025                 SIGNAL(triggered()),
3026                 this,
3027                 SLOT(OnOpenRecent()));
3028
3029         if (recents->actions().empty())
3030                 recents->addAction(new_path);
3031         else
3032                 recents->insertAction(recents->actions().front(), new_path);
3033
3034         if (recents->actions().size() > max_files)
3035         {
3036                 QAction* a = recents->actions().back();
3037                 recents->removeAction(a);
3038         }
3039 }
3040
3041 void FormMain::OnOpenRecent()
3042 {
3043         QAction* a = dynamic_cast<QAction*>(QObject::sender());
3044         assert(a != NULL);
3045         if (a == NULL)
3046                 return;
3047
3048         QString path = a->text();
3049
3050         if (IsResetSceneOnBeforeLoadFile())
3051                 ClearAllObjects();
3052
3053         if (OpenGeomFile(path))
3054                 return;
3055 }
3056
3057 void FormMain::on_checkShowOnlySelect_toggled(bool checked)
3058 {
3059         m_View3d.m_Config.m_ShowOnlySelect = checked;
3060         updateView_All();
3061 }
3062
3063 void FormMain::ResizeTreeColumns(QTreeWidget* t, int num_col)
3064 {
3065         t->setVisible(false);
3066         t->resizeColumnToContents(0);
3067         t->resizeColumnToContents(1);
3068         t->resizeColumnToContents(2);
3069         t->resizeColumnToContents(3);
3070         t->setVisible(true);
3071 }
3072
3073 void FormMain::PushbackTreeNode(QTreeWidget* tree, QTreeWidgetItem *node)
3074 {
3075         int next_idx = tree->topLevelItemCount();
3076         tree->insertTopLevelItem(next_idx, node);
3077 }
3078
3079 QTreeWidgetItem* FormMain::CreateObjectTreeNode(const geom::GeomObject& obj) const
3080 {
3081         QTreeWidgetItem* n = new QTreeWidgetItem;
3082
3083         n->setText(0, QString::fromLocal8Bit(obj.m_Name.c_str()));
3084         n->setCheckState(1, obj.m_Visible ? Qt::Checked : Qt::Unchecked);
3085         n->setText(2, QString::number(obj.GetNumTotalVerts()));
3086         n->setText(3, QString::number(obj.GetNumTotalFaces()));
3087
3088         int idx = 0;
3089         for (const MeshBuf& mbuf : obj.m_MeshAry)
3090         {
3091                 n->addChild(CreateMeshBufNode(obj, mbuf, idx++));
3092         }
3093
3094         n->setExpanded(true);
3095
3096         return n;
3097 }
3098
3099 QTreeWidgetItem* FormMain::CreateMeshBufNode(const geom::GeomObject& obj, const MeshBuf& mbuf, int idx) const
3100 {
3101         QTreeWidgetItem* n = new QTreeWidgetItem;
3102
3103         QString name;
3104         if (mbuf.m_Name.empty())
3105                 name = QString::fromLocal8Bit(obj.m_Name.c_str()) + QString::number(idx);
3106         else
3107                 name = QString::fromLocal8Bit(mbuf.m_Name.c_str());
3108
3109         n->setText(0, name);
3110         n->setCheckState(1, mbuf.m_Visible ? Qt::Checked : Qt::Unchecked);
3111         n->setText(2, QString::number(mbuf.GetNumVerts()));
3112         n->setText(3, QString::number(mbuf.GetNumFaces()));
3113
3114         return n;
3115 }
3116
3117 void FormMain::InitObjectListHeader(void)
3118 {
3119         QStringList qs;
3120         qs << "Name" << "Visible" << "Verts" << "Faces";
3121         ui.treeObjects->setHeaderLabels(qs);
3122 }
3123
3124 void FormMain::SetPrimayrSelectObjectFromScene(void)
3125 {
3126         QTreeWidget* obj_tree = ui.treeObjects;
3127
3128         Selection3D& sels = m_Scene.m_Sels;
3129         if (!sels.IsObjectSelected())
3130                 return;
3131
3132         int sel_idx = sels.GetSelObjectIdx();
3133
3134         QTreeWidgetItem* on = obj_tree->topLevelItem(sel_idx);
3135         if (on == NULL)
3136                 return;
3137
3138         if (sels.IsMBufSelected())
3139         {
3140                 QTreeWidgetItem* mn = on->child(sels.GetMBufIdx());
3141                 obj_tree->setCurrentItem(mn);
3142         }
3143         else
3144         {
3145                 obj_tree->setCurrentItem(on);
3146         }
3147 }
3148
3149 void FormMain::SetPrimayrSelectObjectToScene(void)
3150 {
3151         Selection3D& sels = m_Scene.m_Sels;
3152
3153         QTreeWidget* tree = ui.treeObjects;
3154
3155         QTreeWidgetItem* sel_node = tree->currentItem();
3156         if (sel_node == NULL)
3157                 return;
3158
3159         QTreeWidgetItem* on = sel_node->parent();
3160         if (on == NULL)
3161         {
3162                 int obj_idx = tree->indexOfTopLevelItem(sel_node);
3163                 sels.SelectObject(obj_idx);
3164         }
3165         else
3166         {
3167                 int obj_idx = tree->indexOfTopLevelItem(on);
3168                 int mb_idx = on->indexOfChild(sel_node);
3169                 sels.SelectMBuf(obj_idx, mb_idx);
3170         }
3171 }
3172
3173 void FormMain::on_actionReleaseShader_triggered()
3174 {
3175         m_ContextShare.BeginDrawTop();
3176
3177         m_View3d.m_ShaderLib.ReleaseAllShaders();
3178
3179         m_ContextShare.EndDrawTop();
3180 }
3181
3182 void FormMain::on_combo2DViewSrcType_currentIndexChanged(int index)
3183 {
3184         switch (index)
3185         {
3186         case 0 : return m_View2d.ChangeTextureSource(View2DTexSrc::Color);
3187         case 1 : return m_View2d.ChangeTextureSource(View2DTexSrc::Normal);
3188         default:
3189                 assert(false);
3190                 break;
3191         }
3192 }