Hugintrunk  0.1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
PanoOutputDialog.cpp
Go to the documentation of this file.
1 // -*- c-basic-offset: 4 -*-
2 
11 /* This is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU General Public
13  * License as published by the Free Software Foundation; either
14  * version 2 of the License, or (at your option) any later version.
15  *
16  * This software is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19  * Lesser General Public License for more details.
20  *
21  * You should have received a copy of the GNU General Public
22  * License along with this software. If not, see
23  * <http://www.gnu.org/licenses/>.
24  *
25  */
26 
27 #include "hugin/PanoOutputDialog.h"
28 #include "base_wx/wxPlatform.h"
29 #include "panoinc.h"
30 
31 #include "hugin/huginApp.h"
32 #include "base_wx/platform.h"
33 #include "hugin/config_defaults.h"
36 
37 BEGIN_EVENT_TABLE(PanoOutputDialog,wxDialog)
38  EVT_BUTTON(wxID_OK, PanoOutputDialog::OnOk)
39  EVT_CHECKBOX(XRCID("output_normal"), PanoOutputDialog::OnOutputChanged)
40  EVT_CHECKBOX(XRCID("output_fused_blended"), PanoOutputDialog::OnOutputChanged)
41  EVT_CHECKBOX(XRCID("output_blended_fused"), PanoOutputDialog::OnOutputChanged)
42  EVT_CHECKBOX(XRCID("output_hdr"), PanoOutputDialog::OnOutputChanged)
43  EVT_CHOICE(XRCID("output_ldr_format"), PanoOutputDialog::OnLDRFormatChanged)
44  EVT_CHOICE(XRCID("output_hdr_format"), PanoOutputDialog::OnHDRFormatChanged)
45  EVT_SPINCTRL(XRCID("output_width"), PanoOutputDialog::OnWidthChanged)
46  EVT_SPINCTRL(XRCID("output_height"), PanoOutputDialog::OnHeightChanged)
48 
49 PanoOutputDialog::PanoOutputDialog(wxWindow *parent, HuginBase::Panorama& pano, GuiLevel guiLevel) : m_pano(pano), m_aspect(0)
50 {
51  // load our children. some children might need special
52  // initialization. this will be done later.
53  wxXmlResource::Get()->LoadDialog(this, parent, wxT("pano_output_dialog"));
54 
55 #ifdef __WXMSW__
56  wxIconBundle myIcons(huginApp::Get()->GetXRCPath() + wxT("data/hugin.ico"),wxBITMAP_TYPE_ICO);
57  SetIcons(myIcons);
58 #else
59  wxIcon myIcon(huginApp::Get()->GetXRCPath() + wxT("data/hugin.png"),wxBITMAP_TYPE_PNG);
60  SetIcon(myIcon);
61 #endif
62 
63  //set parameters
64  wxConfigBase * cfg = wxConfigBase::Get();
65  //position
66  int x = cfg->Read(wxT("/PanoOutputDialog/positionX"),-1l);
67  int y = cfg->Read(wxT("/PanoOutputDialog/positionY"),-1l);
68  if ( y >= 0 && x >= 0)
69  {
70  this->Move(x, y);
71  }
72  else
73  {
74  this->Move(0, 44);
75  };
76  // get number of stacks and exposure layers
77  m_guiLevel=guiLevel;
78  HuginBase::UIntSet images=getImagesinROI(m_pano, m_pano.getActiveImages());
79  m_stacks=getHDRStacks(m_pano, images, m_pano.getOptions());
80  m_exposureLayers=getExposureLayers(m_pano, images, m_pano.getOptions());
81  // set initial width
82  m_newOpt = m_pano.getOptions();
83  wxConfigBase* config = wxConfigBase::Get();
84  if (m_newOpt.fovCalcSupported(m_newOpt.getProjection()))
85  {
86  // calc optimal size of pano, only of projection is supported
87  // otherwise use current width as start point
88  long opt_width = hugin_utils::roundi(HuginBase::CalculateOptimalScale::calcOptimalScale(m_pano) * m_newOpt.getWidth());
89  double sizeFactor = HUGIN_ASS_PANO_DOWNSIZE_FACTOR;
90  config->Read(wxT("/Assistant/panoDownsizeFactor"), &sizeFactor, HUGIN_ASS_PANO_DOWNSIZE_FACTOR);
91  m_newOpt.setWidth(hugin_utils::floori(sizeFactor*opt_width), true);
92  };
93  m_initalWidth=m_newOpt.getWidth();
94  m_initalROIWidth=m_newOpt.getROI().width();
95  m_aspect=(double)m_newOpt.getROI().height()/m_newOpt.getROI().width();
96  m_edit_width=XRCCTRL(*this, "output_width", wxSpinCtrl);
97  m_edit_height=XRCCTRL(*this, "output_height", wxSpinCtrl);
98  m_edit_width->SetValue(m_newOpt.getROI().width());
99  m_edit_height->SetValue(m_newOpt.getROI().height());
100 
101  //LDR output format, as in preferences set
102  int i = config->Read(wxT("/output/jpeg_quality"),HUGIN_JPEG_QUALITY);
103  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->SetValue(i);
104  i=config->Read(wxT("/output/tiff_compression"), HUGIN_TIFF_COMPRESSION);
105  XRCCTRL(*this, "output_tiff_compression", wxChoice)->SetSelection(i);
106  i=config->Read(wxT("/output/ldr_format"), HUGIN_LDR_OUTPUT_FORMAT);
107  XRCCTRL(*this, "output_ldr_format", wxChoice)->SetSelection(i);
108  //HDR output format, as in project given
109  if (m_newOpt.outputImageTypeHDR == "exr")
110  {
111  XRCCTRL(*this, "output_hdr_format", wxChoice)->SetSelection(0);
112  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(2);
113  }
114  else
115  {
116  XRCCTRL(*this, "output_hdr_format", wxChoice)->SetSelection(1);
117  if (m_newOpt.outputImageTypeHDRCompression == "PACKBITS")
118  {
119  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(1);
120  }
121  else
122  {
123  if (m_newOpt.outputImageTypeHDRCompression == "LZW")
124  {
125  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(2);
126  }
127  else
128  {
129  if (m_newOpt.outputImageTypeHDRCompression == "DEFLATE")
130  {
131  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(3);
132  }
133  else
134  {
135  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(0);
136  };
137  };
138  };
139  };
140  EnableOutputOptions();
141  wxCommandEvent dummy;
142  OnOutputChanged(dummy);
143  OnLDRFormatChanged(dummy);
144  OnHDRFormatChanged(dummy);
145 };
146 
148 {
149  wxConfigBase * cfg = wxConfigBase::Get();
150  wxPoint ps = this->GetPosition();
151  cfg->Write(wxT("/PanoOutputDialog/positionX"), ps.x);
152  cfg->Write(wxT("/PanoOutputDialog/positionY"), ps.y);
153  cfg->Flush();
154 };
155 
157 {
158  // check, if hdr images
159  wxFileName file1(wxString(m_pano.getImage(0).getFilename().c_str(), HUGIN_CONV_FILENAME));
160  wxString ext1=file1.GetExt().Lower();
161  if(ext1 == wxT(".hdr") || ext1 == wxT(".exr") || ext1==wxT("hdr") || ext1==wxT("exr"))
162  {
163  XRCCTRL(*this, "output_normal", wxCheckBox)->SetValue(true);
164  XRCCTRL(*this, "output_normal", wxCheckBox)->Enable(true);
165  XRCCTRL(*this, "output_normal_bitmap", wxStaticBitmap)->Enable(true);
166  return;
167  }
168  //hide hdr controls for simple interface
170  {
171  XRCCTRL(*this, "output_hdr", wxCheckBox)->Hide();
172  XRCCTRL(*this, "output_hdr_bitmap", wxStaticBitmap)->Hide();
173  XRCCTRL(*this, "output_hdr_format_label", wxStaticText)->Hide();
174  XRCCTRL(*this, "output_hdr_format", wxChoice)->Hide();
175  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Hide();
176  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Hide();
177  Layout();
178  GetSizer()->Fit(this);
179  };
180  //single image or normal panorama, enable only normal output
181  if(m_pano.getNrOfImages()==1 || m_stacks.size() >= 0.7 * m_pano.getNrOfImages())
182  {
183  XRCCTRL(*this, "output_normal", wxCheckBox)->SetValue(true);
184  XRCCTRL(*this, "output_normal", wxCheckBox)->Enable(true);
185  XRCCTRL(*this, "output_normal_bitmap", wxStaticBitmap)->Enable(true);
186  if(m_pano.getNrOfImages()==1 || m_stacks.size()==m_pano.getNrOfImages())
187  {
188  return;
189  };
190  };
191  XRCCTRL(*this, "output_fused_blended", wxCheckBox)->Enable(true);
192  XRCCTRL(*this, "output_fused_blended_bitmap", wxStaticBitmap)->Enable(true);
193  XRCCTRL(*this, "output_blended_fused", wxCheckBox)->Enable(true);
194  XRCCTRL(*this, "output_blended_fused_bitmap", wxStaticBitmap)->Enable(true);
196  {
197  XRCCTRL(*this, "output_hdr", wxCheckBox)->Enable(true);
198  XRCCTRL(*this, "output_hdr_bitmap", wxStaticBitmap)->Enable(true);
199  };
200  if(m_pano.getNrOfImages() % m_stacks.size() == 0)
201  {
202  XRCCTRL(*this, "output_fused_blended", wxCheckBox)->SetValue(true);
203  }
204  else
205  {
206  if(m_exposureLayers.size()==1)
207  {
208  XRCCTRL(*this, "output_normal", wxCheckBox)->SetValue(true);
209  XRCCTRL(*this, "output_normal", wxCheckBox)->Enable(true);
210  XRCCTRL(*this, "output_normal_bitmap", wxStaticBitmap)->Enable(true);
211  }
212  else
213  {
214  XRCCTRL(*this, "output_blended_fused", wxCheckBox)->SetValue(true);
215  };
216  };
217 };
218 
219 void PanoOutputDialog::OnOk(wxCommandEvent & e)
220 {
221  bool output_normal=XRCCTRL(*this, "output_normal", wxCheckBox)->GetValue();
222  bool output_fused_blended=XRCCTRL(*this, "output_fused_blended", wxCheckBox)->GetValue();
223  bool output_blended_fused=XRCCTRL(*this, "output_blended_fused", wxCheckBox)->GetValue();
224  bool output_hdr=XRCCTRL(*this, "output_hdr", wxCheckBox)->GetValue();
225  bool keep_intermediate=XRCCTRL(*this, "output_keep_intermediate", wxCheckBox)->GetValue();
226  //normal output
227  m_newOpt.outputLDRBlended=output_normal;
228  m_newOpt.outputLDRLayers=output_normal && keep_intermediate;
229  //fused stacks, then blended
230  m_newOpt.outputLDRExposureBlended=output_fused_blended;
231  m_newOpt.outputLDRExposureRemapped=(output_fused_blended || output_blended_fused) && keep_intermediate;
232  m_newOpt.outputLDRStacks=output_fused_blended && keep_intermediate;
233  // blended exposure layers, then fused
234  m_newOpt.outputLDRExposureLayersFused=output_blended_fused;
235  m_newOpt.outputLDRExposureLayers=output_blended_fused && keep_intermediate;
236  // HDR output
237  m_newOpt.outputHDRBlended=output_hdr;
238  m_newOpt.outputHDRLayers=output_hdr && keep_intermediate;
239  m_newOpt.outputHDRStacks=output_hdr && keep_intermediate;
240  // read compression
241  if(output_normal || output_fused_blended || output_blended_fused)
242  {
243  if(m_newOpt.outputImageType=="jpg")
244  {
245  m_newOpt.quality=XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->GetValue();
246  }
247  else
248  {
249  if(m_newOpt.outputImageType=="tif")
250  {
251  switch(XRCCTRL(*this, "output_tiff_compression", wxChoice)->GetSelection())
252  {
253  case 0:
254  default:
256  m_newOpt.tiffCompression = "NONE";
257  break;
258  case 1:
260  m_newOpt.tiffCompression = "PACKBITS";
261  break;
262  case 2:
264  m_newOpt.tiffCompression = "LZW";
265  break;
266  case 3:
268  m_newOpt.tiffCompression = "DEFLATE";
269  break;
270  };
271  };
272  };
273  };
274  //HDR compression
275  if(output_hdr)
276  {
277  if(m_newOpt.outputImageTypeHDR=="tif")
278  {
279  switch(XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->GetSelection())
280  {
281  case 0:
282  default:
284  break;
285  case 1:
287  break;
288  case 2:
290  break;
291  case 3:
293  break;
294  };
295  };
296  }
297  // canvas size
298  double scale=m_edit_width->GetValue()/m_initalROIWidth;
300  //some checks to prevent some rounding errors, only for cropped outputs
302  {
303  if(m_newOpt.getROI().width()<m_edit_width->GetValue() || m_newOpt.getROI().height()<m_edit_height->GetValue())
304  {
305  m_newOpt.setWidth(m_newOpt.getWidth()+1, true);
306  };
307  vigra::Rect2D roi=m_newOpt.getROI();
308  if(roi.width()>m_edit_width->GetValue() || roi.height()>m_edit_height->GetValue())
309  {
310  roi.setSize(m_edit_width->GetValue(), m_edit_height->GetValue());
311  m_newOpt.setROI(roi);
312  };
313  };
314  //send Ok
315  EndModal(wxID_OK);
316 };
317 
318 void PanoOutputDialog::OnOutputChanged(wxCommandEvent & e)
319 {
320  bool output_normal=XRCCTRL(*this, "output_normal", wxCheckBox)->GetValue();
321  bool output_fused_blended=XRCCTRL(*this, "output_fused_blended", wxCheckBox)->GetValue();
322  bool output_blended_fused=XRCCTRL(*this, "output_blended_fused", wxCheckBox)->GetValue();
323  bool output_hdr=XRCCTRL(*this, "output_hdr", wxCheckBox)->GetValue();
324  //enable Ok only if at least one option is enabled
325  XRCCTRL(*this, "wxID_OK", wxButton)->Enable(output_normal || output_fused_blended || output_blended_fused || output_hdr);
326  XRCCTRL(*this, "output_ldr_format_label", wxStaticText)->Enable(output_normal || output_fused_blended || output_blended_fused);
327  XRCCTRL(*this, "output_ldr_format", wxChoice)->Enable(output_normal || output_fused_blended || output_blended_fused);
328  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Enable(output_normal || output_fused_blended || output_blended_fused);
329  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Enable(output_normal || output_fused_blended || output_blended_fused);
330  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Enable(output_normal || output_fused_blended || output_blended_fused);
331  XRCCTRL(*this, "output_hdr_format_label", wxStaticText)->Enable(output_hdr);
332  XRCCTRL(*this, "output_hdr_format", wxChoice)->Enable(output_hdr);
333  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Enable(output_hdr);
334  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Enable(output_hdr);
335  GetSizer()->Layout();
336 };
337 
338 void PanoOutputDialog::OnLDRFormatChanged(wxCommandEvent & e)
339 {
340  int sel = XRCCTRL(*this, "output_ldr_format", wxChoice)->GetSelection();
341  switch (sel)
342  {
343  case 1:
344  m_newOpt.outputImageType ="jpg";
345  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Show();
346  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->SetLabel(_("Quality:"));
347  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Show();
348  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Hide();
349  break;
350  case 2:
351  m_newOpt.outputImageType ="png";
352  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Hide();
353  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Hide();
354  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Hide();
355  break;
356  default:
357  case 0:
358  m_newOpt.outputImageType ="tif";
359  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Show();
360  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->SetLabel(_("Compression:"));
361  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Hide();
362  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Show();
363  break;
364  };
365  GetSizer()->Layout();
366 };
367 
368 
369 void PanoOutputDialog::OnHDRFormatChanged(wxCommandEvent & e)
370 {
371  int sel = XRCCTRL(*this, "output_hdr_format", wxChoice)->GetSelection();
372  switch (sel)
373  {
374  case 1:
376  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Show();
377  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Show();
378  break;
379  case 0:
380  default:
382  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Hide();
383  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Hide();
384  break;
385  };
386  GetSizer()->Layout();
387 };
388 
389 void PanoOutputDialog::OnWidthChanged(wxSpinEvent & e)
390 {
391  if(m_aspect>0)
392  {
393  m_edit_height->SetValue(m_edit_width->GetValue()*m_aspect);
394  };
395 };
396 
398 {
399  if(m_aspect>0)
400  {
401  m_edit_width->SetValue(m_edit_height->GetValue()/m_aspect);
402  };
403 };
int floori(double x)
Definition: hugin_math.h:65
std::vector< UIntSet > getHDRStacks(const PanoramaData &pano, UIntSet allImgs, PanoramaOptions opts)
returns vector of set of output stacks
Definition: LayerStacks.cpp:35
implementation of huginApp Class
declaration of functions to handle stacks and layers
std::vector< UIntSet > getExposureLayers(const PanoramaData &pano, UIntSet allImgs, PanoramaOptions opts)
returns vector of set of output exposure layers
Definition: LayerStacks.cpp:96
~PanoOutputDialog()
destructor, save position
int roundi(T x)
Definition: hugin_math.h:73
bool outputLDRLayers
save remapped layers (LDR)
#define HUGIN_CONV_FILENAME
Definition: platform.h:40
void OnHeightChanged(wxSpinEvent &e)
height changed
#define HUGIN_JPEG_QUALITY
std::string outputImageTypeHDRCompression
bool outputHDRLayers
save remapped layers (HDR)
UIntSet getImagesinROI(const PanoramaData &pano, const UIntSet activeImages)
returns set of images which are visible in output ROI
Dialog for setting output parameters for simple user interface.
END_EVENT_TABLE()
include file for the hugin project
wxSpinCtrl * m_edit_height
void OnOk(wxCommandEvent &e)
Saves current state of all checkboxes when closing dialog with Ok.
std::string outputImageTypeCompression
static huginApp * Get()
hack.. kind of a pseudo singleton...
Definition: huginApp.cpp:641
bool outputLDRExposureBlended
&lt; save exposure fused stacks (no exposure adjustment)
HuginBase::Panorama & m_pano
std::set< unsigned int > UIntSet
Definition: PanoramaData.h:51
const vigra::Rect2D & getROI() const
bool outputLDRBlended
save blended panorama (LDR)
std::size_t getNrOfImages() const
number of images.
Definition: Panorama.h:205
Definition of PanoOutputDialog class.
static double calcOptimalScale(PanoramaData &panorama)
bool outputHDRBlended
save blended panorama (HDR)
std::vector< HuginBase::UIntSet > m_exposureLayers
#define HUGIN_TIFF_COMPRESSION
wxSpinCtrl * m_edit_width
void setROI(const vigra::Rect2D &val)
#define HUGIN_LDR_OUTPUT_FORMAT
std::vector< HuginBase::UIntSet > m_stacks
bool outputLDRExposureLayers
save blended exposure layers, do not perform fusion (no exposure adjustment)
unsigned int getWidth() const
bool outputLDRExposureRemapped
save remapped layers (no exposure adjustment)
bool outputLDRExposureLayersFused
save blended exposure layers which are then fused (no exposure adjustment)
void OnHDRFormatChanged(wxCommandEvent &e)
HDR format changed.
HuginBase::PanoramaOptions m_newOpt
#define HUGIN_ASS_PANO_DOWNSIZE_FACTOR
platform/compiler specific stuff.
const SrcPanoImage & getImage(std::size_t nr) const
get a panorama image, counting starts with 0
Definition: Panorama.h:211
GuiLevel
Definition: GuiLevel.h:31
bool outputHDRStacks
save image stacks (HDR)
void OnLDRFormatChanged(wxCommandEvent &e)
LDR format changed.
void OnWidthChanged(wxSpinEvent &e)
width changed
void OnOutputChanged(wxCommandEvent &e)
enabled Ok button and LDR/HDR format settings depeding on selected output settings ...
void setWidth(unsigned int w, bool keepView=true)
set panorama width keep the HFOV, if keepView=true