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 PanoOutputDialog::PanoOutputDialog(wxWindow *parent, HuginBase::Panorama& pano, GuiLevel guiLevel) : m_pano(pano), m_aspect(0)
38 {
39  // load our children. some children might need special
40  // initialization. this will be done later.
41  wxXmlResource::Get()->LoadDialog(this, parent, wxT("pano_output_dialog"));
42 
43  //set parameters
44  wxConfigBase * cfg = wxConfigBase::Get();
45  //position
46  int x = cfg->Read(wxT("/PanoOutputDialog/positionX"),-1l);
47  int y = cfg->Read(wxT("/PanoOutputDialog/positionY"),-1l);
48  if ( y >= 0 && x >= 0)
49  {
50  this->Move(x, y);
51  }
52  else
53  {
54  this->Move(0, 44);
55  };
56  // get number of stacks and exposure layers
57  m_guiLevel=guiLevel;
61  // set initial width
63  wxConfigBase* config = wxConfigBase::Get();
64  if (m_newOpt.fovCalcSupported(m_newOpt.getProjection()))
65  {
66  // calc optimal size of pano, only of projection is supported
67  // otherwise use current width as start point
68  long opt_width = hugin_utils::roundi(HuginBase::CalculateOptimalScale::calcOptimalScale(m_pano) * m_newOpt.getWidth());
69  double sizeFactor = HUGIN_ASS_PANO_DOWNSIZE_FACTOR;
70  config->Read(wxT("/Assistant/panoDownsizeFactor"), &sizeFactor, HUGIN_ASS_PANO_DOWNSIZE_FACTOR);
71  m_newOpt.setWidth(hugin_utils::floori(sizeFactor*opt_width), true);
72  };
73  m_initalWidth=m_newOpt.getWidth();
74  m_initalROIWidth=m_newOpt.getROI().width();
75  m_aspect=(double)m_newOpt.getROI().height()/m_newOpt.getROI().width();
76  m_edit_width=XRCCTRL(*this, "output_width", wxSpinCtrl);
77  m_edit_height=XRCCTRL(*this, "output_height", wxSpinCtrl);
78  m_edit_width->SetValue(m_newOpt.getROI().width());
79  m_edit_height->SetValue(m_newOpt.getROI().height());
80 
81  //LDR output format, as in preferences set
82  int i = config->Read(wxT("/output/jpeg_quality"),HUGIN_JPEG_QUALITY);
83  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->SetValue(i);
84  i=config->Read(wxT("/output/tiff_compression"), HUGIN_TIFF_COMPRESSION);
85  XRCCTRL(*this, "output_tiff_compression", wxChoice)->SetSelection(i);
86  i=config->Read(wxT("/output/ldr_format"), HUGIN_LDR_OUTPUT_FORMAT);
87  XRCCTRL(*this, "output_ldr_format", wxChoice)->SetSelection(i);
88  //HDR output format, as in project given
89  if (m_newOpt.outputImageTypeHDR == "exr")
90  {
91  XRCCTRL(*this, "output_hdr_format", wxChoice)->SetSelection(0);
92  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(2);
93  }
94  else
95  {
96  XRCCTRL(*this, "output_hdr_format", wxChoice)->SetSelection(1);
97  if (m_newOpt.outputImageTypeHDRCompression == "PACKBITS")
98  {
99  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(1);
100  }
101  else
102  {
103  if (m_newOpt.outputImageTypeHDRCompression == "LZW")
104  {
105  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(2);
106  }
107  else
108  {
109  if (m_newOpt.outputImageTypeHDRCompression == "DEFLATE")
110  {
111  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(3);
112  }
113  else
114  {
115  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->SetSelection(0);
116  };
117  };
118  };
119  };
121  wxCommandEvent dummy;
122  OnOutputChanged(dummy);
123  OnLDRFormatChanged(dummy);
124  OnHDRFormatChanged(dummy);
125  // bind event handler
126  Bind(wxEVT_CHECKBOX, &PanoOutputDialog::OnOutputChanged, this, XRCID("output_normal"));
127  Bind(wxEVT_CHECKBOX, &PanoOutputDialog::OnOutputChanged, this, XRCID("output_fused_blended"));
128  Bind(wxEVT_CHECKBOX, &PanoOutputDialog::OnOutputChanged, this, XRCID("output_blended_fused"));
129  Bind(wxEVT_CHECKBOX, &PanoOutputDialog::OnOutputChanged, this, XRCID("output_hdr"));
130  Bind(wxEVT_CHOICE, &PanoOutputDialog::OnLDRFormatChanged, this, XRCID("output_ldr_format"));
131  Bind(wxEVT_CHOICE, &PanoOutputDialog::OnHDRFormatChanged, this, XRCID("output_hdr_format"));
132  Bind(wxEVT_SPINCTRL, &PanoOutputDialog::OnWidthChanged, this, XRCID("output_width"));
133  Bind(wxEVT_SPINCTRL, &PanoOutputDialog::OnHeightChanged, this, XRCID("output_height"));
134  Bind(wxEVT_BUTTON, &PanoOutputDialog::OnOk, this, wxID_OK);
135 
136 };
137 
139 {
140  wxConfigBase * cfg = wxConfigBase::Get();
141  wxPoint ps = this->GetPosition();
142  cfg->Write(wxT("/PanoOutputDialog/positionX"), ps.x);
143  cfg->Write(wxT("/PanoOutputDialog/positionY"), ps.y);
144  cfg->Flush();
145 };
146 
148 {
149  // check, if hdr images
150  wxFileName file1(wxString(m_pano.getImage(0).getFilename().c_str(), HUGIN_CONV_FILENAME));
151  wxString ext1=file1.GetExt().Lower();
152  if(ext1 == wxT(".hdr") || ext1 == wxT(".exr") || ext1==wxT("hdr") || ext1==wxT("exr"))
153  {
154  XRCCTRL(*this, "output_normal", wxCheckBox)->SetValue(true);
155  XRCCTRL(*this, "output_normal", wxCheckBox)->Enable(true);
156  XRCCTRL(*this, "output_normal_bitmap", wxStaticBitmap)->Enable(true);
157  return;
158  }
159  //hide hdr controls for simple interface
161  {
162  XRCCTRL(*this, "output_hdr", wxCheckBox)->Hide();
163  XRCCTRL(*this, "output_hdr_bitmap", wxStaticBitmap)->Hide();
164  XRCCTRL(*this, "output_hdr_format_label", wxStaticText)->Hide();
165  XRCCTRL(*this, "output_hdr_format", wxChoice)->Hide();
166  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Hide();
167  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Hide();
168  Layout();
169  GetSizer()->Fit(this);
170  };
171  //single image or normal panorama, enable only normal output
172  if(m_pano.getNrOfImages()==1 || m_stacks.size() >= 0.7 * m_pano.getNrOfImages())
173  {
174  XRCCTRL(*this, "output_normal", wxCheckBox)->SetValue(true);
175  XRCCTRL(*this, "output_normal", wxCheckBox)->Enable(true);
176  XRCCTRL(*this, "output_normal_bitmap", wxStaticBitmap)->Enable(true);
177  if(m_pano.getNrOfImages()==1 || m_stacks.size()==m_pano.getNrOfImages())
178  {
179  return;
180  };
181  };
182  XRCCTRL(*this, "output_fused_blended", wxCheckBox)->Enable(true);
183  XRCCTRL(*this, "output_fused_blended_bitmap", wxStaticBitmap)->Enable(true);
184  XRCCTRL(*this, "output_blended_fused", wxCheckBox)->Enable(true);
185  XRCCTRL(*this, "output_blended_fused_bitmap", wxStaticBitmap)->Enable(true);
187  {
188  XRCCTRL(*this, "output_hdr", wxCheckBox)->Enable(true);
189  XRCCTRL(*this, "output_hdr_bitmap", wxStaticBitmap)->Enable(true);
190  };
191  if(m_pano.getNrOfImages() % m_stacks.size() == 0)
192  {
193  XRCCTRL(*this, "output_fused_blended", wxCheckBox)->SetValue(true);
194  }
195  else
196  {
197  if(m_exposureLayers.size()==1)
198  {
199  XRCCTRL(*this, "output_normal", wxCheckBox)->SetValue(true);
200  XRCCTRL(*this, "output_normal", wxCheckBox)->Enable(true);
201  XRCCTRL(*this, "output_normal_bitmap", wxStaticBitmap)->Enable(true);
202  }
203  else
204  {
205  XRCCTRL(*this, "output_blended_fused", wxCheckBox)->SetValue(true);
206  };
207  };
208 };
209 
210 void PanoOutputDialog::OnOk(wxCommandEvent & e)
211 {
212  bool output_normal=XRCCTRL(*this, "output_normal", wxCheckBox)->GetValue();
213  bool output_fused_blended=XRCCTRL(*this, "output_fused_blended", wxCheckBox)->GetValue();
214  bool output_blended_fused=XRCCTRL(*this, "output_blended_fused", wxCheckBox)->GetValue();
215  bool output_hdr=XRCCTRL(*this, "output_hdr", wxCheckBox)->GetValue();
216  bool keep_intermediate=XRCCTRL(*this, "output_keep_intermediate", wxCheckBox)->GetValue();
217  //normal output
218  m_newOpt.outputLDRBlended=output_normal;
219  m_newOpt.outputLDRLayers=output_normal && keep_intermediate;
220  //fused stacks, then blended
221  m_newOpt.outputLDRExposureBlended=output_fused_blended;
222  m_newOpt.outputLDRExposureRemapped=(output_fused_blended || output_blended_fused) && keep_intermediate;
223  m_newOpt.outputLDRStacks=output_fused_blended && keep_intermediate;
224  // blended exposure layers, then fused
225  m_newOpt.outputLDRExposureLayersFused=output_blended_fused;
226  m_newOpt.outputLDRExposureLayers=output_blended_fused && keep_intermediate;
227  // HDR output
228  m_newOpt.outputHDRBlended=output_hdr;
229  m_newOpt.outputHDRLayers=output_hdr && keep_intermediate;
230  m_newOpt.outputHDRStacks=output_hdr && keep_intermediate;
231  // read compression
232  if(output_normal || output_fused_blended || output_blended_fused)
233  {
234  if(m_newOpt.outputImageType=="jpg")
235  {
236  m_newOpt.quality=XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->GetValue();
237  }
238  else
239  {
240  if(m_newOpt.outputImageType=="tif")
241  {
242  switch(XRCCTRL(*this, "output_tiff_compression", wxChoice)->GetSelection())
243  {
244  case 0:
245  default:
247  m_newOpt.tiffCompression = "NONE";
248  break;
249  case 1:
251  m_newOpt.tiffCompression = "PACKBITS";
252  break;
253  case 2:
255  m_newOpt.tiffCompression = "LZW";
256  break;
257  case 3:
259  m_newOpt.tiffCompression = "DEFLATE";
260  break;
261  };
262  };
263  };
264  };
265  //HDR compression
266  if(output_hdr)
267  {
268  if(m_newOpt.outputImageTypeHDR=="tif")
269  {
270  switch(XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->GetSelection())
271  {
272  case 0:
273  default:
275  break;
276  case 1:
278  break;
279  case 2:
281  break;
282  case 3:
284  break;
285  };
286  };
287  }
288  // canvas size
289  double scale=m_edit_width->GetValue()/m_initalROIWidth;
291  //some checks to prevent some rounding errors, only for cropped outputs
293  {
294  if(m_newOpt.getROI().width()<m_edit_width->GetValue() || m_newOpt.getROI().height()<m_edit_height->GetValue())
295  {
296  m_newOpt.setWidth(m_newOpt.getWidth()+1, true);
297  };
298  vigra::Rect2D roi=m_newOpt.getROI();
299  if(roi.width()>m_edit_width->GetValue() || roi.height()>m_edit_height->GetValue())
300  {
301  roi.setSize(m_edit_width->GetValue(), m_edit_height->GetValue());
302  m_newOpt.setROI(roi);
303  };
304  };
305  //send Ok
306  EndModal(wxID_OK);
307 };
308 
309 void PanoOutputDialog::OnOutputChanged(wxCommandEvent & e)
310 {
311  bool output_normal=XRCCTRL(*this, "output_normal", wxCheckBox)->GetValue();
312  bool output_fused_blended=XRCCTRL(*this, "output_fused_blended", wxCheckBox)->GetValue();
313  bool output_blended_fused=XRCCTRL(*this, "output_blended_fused", wxCheckBox)->GetValue();
314  bool output_hdr=XRCCTRL(*this, "output_hdr", wxCheckBox)->GetValue();
315  //enable Ok only if at least one option is enabled
316  XRCCTRL(*this, "wxID_OK", wxButton)->Enable(output_normal || output_fused_blended || output_blended_fused || output_hdr);
317  XRCCTRL(*this, "output_ldr_format_label", wxStaticText)->Enable(output_normal || output_fused_blended || output_blended_fused);
318  XRCCTRL(*this, "output_ldr_format", wxChoice)->Enable(output_normal || output_fused_blended || output_blended_fused);
319  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Enable(output_normal || output_fused_blended || output_blended_fused);
320  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Enable(output_normal || output_fused_blended || output_blended_fused);
321  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Enable(output_normal || output_fused_blended || output_blended_fused);
322  XRCCTRL(*this, "output_hdr_format_label", wxStaticText)->Enable(output_hdr);
323  XRCCTRL(*this, "output_hdr_format", wxChoice)->Enable(output_hdr);
324  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Enable(output_hdr);
325  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Enable(output_hdr);
326  GetSizer()->Layout();
327 };
328 
329 void PanoOutputDialog::OnLDRFormatChanged(wxCommandEvent & e)
330 {
331  int sel = XRCCTRL(*this, "output_ldr_format", wxChoice)->GetSelection();
332  switch (sel)
333  {
334  case 1:
335  m_newOpt.outputImageType ="jpg";
336  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Show();
337  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->SetLabel(_("Quality:"));
338  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Show();
339  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Hide();
340  break;
341  case 2:
342  m_newOpt.outputImageType ="png";
343  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Hide();
344  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Hide();
345  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Hide();
346  break;
347  default:
348  case 0:
349  m_newOpt.outputImageType ="tif";
350  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->Show();
351  XRCCTRL(*this, "output_ldr_compression_label", wxStaticText)->SetLabel(_("Compression:"));
352  XRCCTRL(*this, "output_jpeg_quality", wxSpinCtrl)->Hide();
353  XRCCTRL(*this, "output_tiff_compression", wxChoice)->Show();
354  break;
355  };
356  GetSizer()->Layout();
357 };
358 
359 
360 void PanoOutputDialog::OnHDRFormatChanged(wxCommandEvent & e)
361 {
362  int sel = XRCCTRL(*this, "output_hdr_format", wxChoice)->GetSelection();
363  switch (sel)
364  {
365  case 1:
367  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Show();
368  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Show();
369  break;
370  case 0:
371  default:
373  XRCCTRL(*this, "output_hdr_compression_label", wxStaticText)->Hide();
374  XRCCTRL(*this, "output_hdr_tiff_compression", wxChoice)->Hide();
375  break;
376  };
377  GetSizer()->Layout();
378 };
379 
380 void PanoOutputDialog::OnWidthChanged(wxSpinEvent & e)
381 {
382  if(m_aspect>0)
383  {
384  m_edit_height->SetValue(m_edit_width->GetValue()*m_aspect);
385  };
386 };
387 
389 {
390  if(m_aspect>0)
391  {
392  m_edit_width->SetValue(m_edit_height->GetValue()/m_aspect);
393  };
394 };
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
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
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
Model for a panorama.
Definition: Panorama.h:152
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
UIntSet getActiveImages() const
get active images
Definition: Panorama.cpp:1585
std::vector< HuginBase::UIntSet > m_stacks
bool outputLDRExposureLayers
save blended exposure layers, do not perform fusion (no exposure adjustment)
unsigned int getWidth() const
const PanoramaOptions & getOptions() const
returns the options for this panorama
Definition: Panorama.h:481
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.
PanoOutputDialog(wxWindow *parent, HuginBase::Panorama &pano, GuiLevel guiLevel)
Constructor, read from xrc ressource; restore last uses settings, size and position.
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