<commit_before>/**
 * L I N E A R   A L G E B R A   O P C O D E S   F O R   C S O U N D
 * Michael Gogins
 *
 * These opcodes implement many linear algebra operations,
 * from scalar, vector, and matrix arithmetic up to
 * and including eigenvalue decompositions.
 * The opcodes are designed to facilitate signal processing,
 * and of course other mathematical operations,
 * in the Csound orchestra language.
 *
 * Linear Algebra Data Types
 *
 * Mathematical    Code   Corresponding Csound Type or Types
 * --------------  -----  --------------------------------------------------------
 * real scalar     r      Native i-rate or k-rate variable
 * complex scalar  c      Pair of native i-rate or k-rate variables, e.g. "kr, ki"
 * real vector     rv     Pointer to array used as native i-rate or k-rate variable
 *                 a      Native a-rate variable
 *                 t      Native function table number
 * complex vector  cv     Pointer to array used as native i-rate or k-rate variable
 *                 f      Native fsig variable
 * real matrix     rm     Pointer to array used as native i-rate or k-rate variable
 * complex matrix  cm     Pointer to array used as native i-rate or k-rate variable
 *
 * All arrays are 0-based.
 *
 * All arrays are considered to be column-major
 * (x or i goes along columnns, y or j goes along rows).
 *
 * All arrays are general and dense; banded, Hermitian, symmetric
 * and sparse routines are not implemented.
 *
 * All operands must be pre-allocated; no operation allocates any arrays.
 * However, some operations may reshape arrays to hold results.
 *
 * Data is stored in i-rate and k-rate "array" objects,
 * which can be of type code vr, vc, mr, or mc, and
 * which internally store type code and shape.
 * In orchestra code the "array" variable is passed in the same way
 * as a MYFLT i-rate or i-rate variable, but it is in reality
 * a pointer to the creator opcode instance.
 *
 * The processing rate and operation name
 * are deterministically and exhaustively encoded into the opcode name as follows.
 * Each part below is separated by an underscore.
 * 1. Opcode family: "la" for "linear algebra".
 * 2. Processing rate: "i" for i-rate or "k" for k-rate.
 * 3. For creators only: type code of the created array.
 * 4. Operation: the common mathematical term or abbreviation, e.g.
 *    "plus", "minus", "prod", "div", "dot", "abs", "conj", "norm1", "det", "hermite", and so on.
 * 5. Where the array type(s) are not implicit: type code of parameter(s).
 *
 * Array Creators
 * --------------
 *
 * iarray                  la_i_vr_create    irows
 * iarray                  la_i_vc_create    irows
 * iarray                  la_i_mr_create    irows, icolumns  [, jdiagonal]
 * iarray                  la_i_mc_create    irows, icolumns  [, jdiagonal]
 * iarray                  la_i_copy         iarray
 * iarray                  la_i_copy_a       asig
 * iarray                  la_i_copy_f       fsig
 * iarray                  la_i_copy_t       itable
 *
 * Array Introspection
 * -------------------
 *
 * itype, irows, icolumns  la_i_info         iarray
 *
 * Array Element Access
 * --------------------
 *
 *                         la_i_vr_set       iarray, icolumn, ivalue
 *                         la_i_vc_set       iarray, icolumn, irvalue, iivalue
 *                         la_i mr_set       iarray, icolumn, irow, ivalue
 *                         la_i_mc_set       iarray, icolumn, irow, irvalue, iivalue
 * ivalue                  la_i_vr_get       iarray, icolumn
 * irvalue, iivalue        la_i_vc_get       iarray, icolumn, irow
 * ivalue                  la_i_mr_get       iarray, icolumn
 * irvalue, iivalue        la_i_mc_get       iarray, icolumn, irow
 *
 * Single Array Operations
 * -----------------------
 *
 * iarray                  la_i_conjugate    iarray
 * iarray                  la_i_transpose    iarray
 *
 * Scalar Operations
 * -----------------
 *
 * ir                      la_i_norm1        iarray
 * ir                      la_i_norm2        iarray
 * ir                      la_i_norm_inf     iarray
 * ir                      la_i_trace        iarray
 * ir                      la_i_lu_det       imatrix
 * iarray                  la_i_scale_r      iarray, ir
 * iarray                  la_i_scale_c      iarray, ireal, iimaginary
 *
 * Elementwise Array-Array Operations
 * ----------------------------------
 *
 * iarray                 la_i_add           iarray_a, iarray_b
 * iarray                 la_i_subtract      iarray_a, iarray_b
 * iarray                 la_i_multiply      iarray_a, iarray_b
 * iarray                 la_i_divide        iarray_a, iarray-b
 *
 * Inner Products
 * --------------
 *
 * iarray                 la_i_dot           iarray_a, iarray_b
 * iarray                 la_i_lu_invert     imatrix
 *
 * Array Decompositions
 * --------------------
 *
 * iarray                 la_i_upper_solve   imatrix [, j_1_diagonal]
 * iarray                 la_i_lower_solve   imatrix [, j_1_diagonal]
 * iarray                 la_i_lu_factor     imatrix, ivector_pivot
 * iarray                 la_i_lu_solve      imatrix, ivector, ivector_pivot
 * imatrix_q, imatrix_r   la_i_qr_factor     imatrix
 * ivector_eigenvalues    la_i_qr_eigen      imatrix, ia_tolerance
 * ivec_eval, imat_evec   la_i_qr_sym_eigen  imatrix, ia_tolerance
 *
 */

extern "C"
{
  // a-rate, k-rate, FUNC, SPECDAT
#include <csoundCore.h>
  // PVSDAT
#include <pstream.h>
}

#include <OpcodeBase.hpp>
#include <gmm/gmm.h>
#include <vector>

struct Array
{
  char code[4];
  size_t rows;
  size_t columns;
  MYFLT *storage;
};

extern "C"
{
  PUBLIC int csoundModuleCreate(CSOUND *csound)
  {
    return 0;
  }

  PUBLIC int csoundModuleInit(CSOUND *csound)
  {
    int status = 0;
    return status;
  }

  PUBLIC int csoundModuleDestroy(CSOUND *csound)
  {
    return 0;
  }
}
<commit_msg>no message<commit_after>/**
 * L I N E A R   A L G E B R A   O P C O D E S   F O R   C S O U N D
 * Michael Gogins
 *
 * These opcodes implement many linear algebra operations,
 * from scalar, vector, and matrix arithmetic up to
 * and including eigenvalue decompositions.
 * The opcodes are designed to facilitate signal processing,
 * and of course other mathematical operations,
 * in the Csound orchestra language.
 *
 * Linear Algebra Data Types
 * -------------------------
 *
 * Mathematical    Code   Corresponding Csound Type or Types
 * --------------  -----  --------------------------------------------------------
 * real scalar     r      Native i-rate or k-rate variable
 * complex scalar  c      Pair of native i-rate or k-rate variables, e.g. "kr, ki"
 * real vector     rv     Pointer to array used as native i-rate or k-rate variable
 *                 a      Native a-rate variable
 *                 t      Native function table number
 * complex vector  cv     Pointer to array used as native i-rate or k-rate variable
 *                 f      Native fsig variable
 * real matrix     rm     Pointer to array used as native i-rate or k-rate variable
 * complex matrix  cm     Pointer to array used as native i-rate or k-rate variable
 *
 * All arrays are 0-based.
 *
 * All arrays are considered to be column-major
 * (x or i goes along columnns, y or j goes along rows).
 *
 * All arrays are general and dense; banded, Hermitian, symmetric
 * and sparse routines are not implemented.
 *
 * All operands must be pre-allocated; no operation allocates any arrays.
 * However, some operations may reshape arrays to hold results.
 *
 * Data is stored in i-rate and k-rate "array" objects,
 * which can be of type code vr, vc, mr, or mc, and
 * which internally store type code and shape.
 * In orchestra code the "array" variable is passed in the same way
 * as a MYFLT i-rate or i-rate variable, but it is in reality
 * a pointer to the creator opcode instance.
 *
 * The processing rate and operation name
 * are deterministically and exhaustively encoded into the opcode name as follows.
 * Each part below is separated by an underscore.
 * 1. Opcode family: "la" for "linear algebra".
 * 2. Processing rate: "i" for i-rate or "k" for k-rate.
 * 3. For creators only: type code of the created array.
 * 4. Operation: the common mathematical term or abbreviation, e.g.
 *    "plus", "minus", "prod", "div", "dot", "abs", "conj", "norm1", "det", "hermite", and so on.
 * 5. Where the array type(s) are not implicit: type code of parameter(s).
 *
 * Array Creators
 * --------------
 *
 * iarray                  la_i_vr_create    irows
 * iarray                  la_i_vc_create    irows
 * iarray                  la_i_mr_create    irows, icolumns  [, jdiagonal]
 * iarray                  la_i_mc_create    irows, icolumns  [, jdiagonal]
 * iarray                  la_i_copy         iarray
 * iarray                  la_i_copy_a       asig
 * iarray                  la_i_copy_f       fsig
 * iarray                  la_i_copy_t       itable
 * iarray                  la_i_a_copy       ivr
 * iarray                  la_i_f_copy       ivc
 * iarray                  la_i_t_copy       ivr
 *
 * Array Introspection
 * -------------------
 *
 * itype, irows, icolumns  la_i_info         iarray
 *
 * Array Element Access
 * --------------------
 *
 *                         la_i_vr_set       iarray, icolumn, ivalue
 *                         la_i_vc_set       iarray, icolumn, irvalue, iivalue
 *                         la_i mr_set       iarray, icolumn, irow, ivalue
 *                         la_i_mc_set       iarray, icolumn, irow, irvalue, iivalue
 * ivalue                  la_i_vr_get       iarray, icolumn
 * irvalue, iivalue        la_i_vc_get       iarray, icolumn, irow
 * ivalue                  la_i_mr_get       iarray, icolumn
 * irvalue, iivalue        la_i_mc_get       iarray, icolumn, irow
 *
 * Single Array Operations
 * -----------------------
 *
 * iarray                  la_i_conjugate    iarray
 * iarray                  la_i_transpose    iarray
 *
 * Scalar Operations
 * -----------------
 *
 * ir                      la_i_norm1        iarray
 * ir                      la_i_norm2        iarray
 * ir                      la_i_norm_inf     iarray
 * ir                      la_i_trace        iarray
 * ir                      la_i_lu_det       imatrix
 * iarray                  la_i_scale_r      iarray, ir
 * iarray                  la_i_scale_c      iarray, ireal, iimaginary
 *
 * Elementwise Array-Array Operations
 * ----------------------------------
 *
 * iarray                 la_i_add           iarray_a, iarray_b
 * iarray                 la_i_subtract      iarray_a, iarray_b
 * iarray                 la_i_multiply      iarray_a, iarray_b
 * iarray                 la_i_divide        iarray_a, iarray-b
 *
 * Inner Products
 * --------------
 *
 * iarray                 la_i_dot           iarray_a, iarray_b
 * iarray                 la_i_lu_invert     imatrix
 *
 * Array Decompositions
 * --------------------
 *
 * iarray                 la_i_upper_solve   imatrix [, j_1_diagonal]
 * iarray                 la_i_lower_solve   imatrix [, j_1_diagonal]
 * iarray                 la_i_lu_factor     imatrix, ivector_pivot
 * iarray                 la_i_lu_solve      imatrix, ivector, ivector_pivot
 * imatrix_q, imatrix_r   la_i_qr_factor     imatrix
 * ivector_eigenvalues    la_i_qr_eigen      imatrix, ia_tolerance
 * ivec_eval, imat_evec   la_i_qr_sym_eigen  imatrix, ia_tolerance
 *
 */

extern "C"
{
  // a-rate, k-rate, FUNC, SPECDAT
#include <csoundCore.h>
  // PVSDAT
#include <pstream.h>
}

#include <OpcodeBase.hpp>
#include <gmm/gmm.h>
#include <vector>

struct Array
{
  OPDS h;
  MYFLT *array;
  MYFLT *rows;
  MYFLT *columns;
  MYFLT *code;
};

int noteoff(CSOUND *csound, Array *array)
{

}

extern "C"
{
  PUBLIC int csoundModuleCreate(CSOUND *csound)
  {
    return 0;
  }

  PUBLIC int csoundModuleInit(CSOUND *csound)
  {
    int status = 0;
    return status;
  }

  PUBLIC int csoundModuleDestroy(CSOUND *csound)
  {
    return 0;
  }
}
<|endoftext|>


<commit_before>#include <set>
#include <string>
#include <vector>

#include "InferArguments.h"
#include "IRVisitor.h"

namespace Halide {
namespace Internal {

using std::set;
using std::string;
using std::vector;

namespace {

class InferArguments : public IRGraphVisitor {
public:
    vector<InferredArgument> &args;

    InferArguments(vector<InferredArgument> &a, const vector<Function> &o, Stmt body)
        : args(a), outputs(o) {
        args.clear();
        for (const Function &f : outputs) {
            visit_function(f);
        }
        if (body.defined()) {
            body.accept(this);
        }
    }

private:
    vector<Function> outputs;
    set<string> visited_functions;

    using IRGraphVisitor::visit;

    bool already_have(const string &name) {
        // Ignore dependencies on the output buffers
        for (const Function &output : outputs) {
            if (name == output.name() || starts_with(name, output.name() + ".")) {
                return true;
            }
        }
        for (const InferredArgument &arg : args) {
            if (arg.arg.name == name) {
                return true;
            }
        }
        return false;
    }

    void visit_exprs(const vector<Expr>& v) {
        for (Expr i : v) {
            visit_expr(i);
        }
    }

    void visit_expr(Expr e) {
        if (!e.defined()) return;
        e.accept(this);
    }

    void visit_function(const Function& func) {
        if (visited_functions.count(func.name())) return;
        visited_functions.insert(func.name());

        func.accept(this);

        // Function::accept hits all the Expr children of the
        // Function, but misses the buffers and images that might be
        // extern arguments.
        if (func.has_extern_definition()) {
            for (const ExternFuncArgument &extern_arg : func.extern_arguments()) {
                if (extern_arg.is_func()) {
                    visit_function(Function(extern_arg.func));
                } else if (extern_arg.is_buffer()) {
                    include_buffer(extern_arg.buffer);
                } else if (extern_arg.is_image_param()) {
                    include_parameter(extern_arg.image_param);
                }
            }
        }
    }

    void include_parameter(Parameter p) {
        if (!p.defined()) return;
        if (already_have(p.name())) return;

        Expr def, min, max;
        if (!p.is_buffer()) {
            def = p.get_scalar_expr();
            min = p.get_min_value();
            max = p.get_max_value();
        }

        InferredArgument a = {
            Argument(p.name(),
                     p.is_buffer() ? Argument::InputBuffer : Argument::InputScalar,
                     p.type(), p.dimensions(), def, min, max),
            p,
            Buffer<>()};
        args.push_back(a);

        // Visit child expressions
        if (!p.is_buffer()) {
            visit_expr(def);
            visit_expr(min);
            visit_expr(max);
        } else {
            for (int i = 0; i < p.dimensions(); i++) {
                visit_expr(p.min_constraint(i));
                visit_expr(p.extent_constraint(i));
                visit_expr(p.stride_constraint(i));
            }
        }
    }

    void include_buffer(Buffer<> b) {
        if (!b.defined()) return;
        if (already_have(b.name())) return;

        InferredArgument a = {
            Argument(b.name(), Argument::InputBuffer, b.type(), b.dimensions()),
            Parameter(),
            b};
        args.push_back(a);
    }

    void visit(const Load *op) {
        IRGraphVisitor::visit(op);
        include_parameter(op->param);
        include_buffer(op->image);
    }

    void visit(const Variable *op) {
        IRGraphVisitor::visit(op);
        include_parameter(op->param);
        include_buffer(op->image);
    }

    void visit(const Call *op) {
        IRGraphVisitor::visit(op);
        if (op->func.defined()) {
            Function fn(op->func);
            visit_function(fn);
        }
        include_buffer(op->image);
        include_parameter(op->param);
    }
};

}

vector<InferredArgument> infer_arguments(Stmt body, const vector<Function> &outputs) {
    vector<InferredArgument> inferred_args;
    // Infer an arguments vector by walking the IR
    InferArguments infer_args(inferred_args,
                              outputs,
                              body);

    // Sort the Arguments with all buffers first (alphabetical by name),
    // followed by all non-buffers (alphabetical by name).
    std::sort(inferred_args.begin(), inferred_args.end());

#if 0
    // Add the user context argument.
    inferred_args.push_back(user_context_arg);

    // Return the inferred argument types, minus any constant images
    // (we'll embed those in the binary by default), and minus the user_context arg.
    vector<Argument> result;
    for (const InferredArgument &arg : inferred_args) {
        debug(1) << "Inferred argument: " << arg.arg.type << " " << arg.arg.name << "\n";
        if (!arg.buffer.defined() &&
            arg.arg.name != user_context_arg.arg.name) {
            result.push_back(arg.arg);
        }
    }
#endif

    return inferred_args;
}

}
}
<commit_msg>Remove dead code.<commit_after>#include <set>
#include <string>
#include <vector>

#include "InferArguments.h"
#include "IRVisitor.h"

namespace Halide {
namespace Internal {

using std::set;
using std::string;
using std::vector;

namespace {

class InferArguments : public IRGraphVisitor {
public:
    vector<InferredArgument> &args;

    InferArguments(vector<InferredArgument> &a, const vector<Function> &o, Stmt body)
        : args(a), outputs(o) {
        args.clear();
        for (const Function &f : outputs) {
            visit_function(f);
        }
        if (body.defined()) {
            body.accept(this);
        }
    }

private:
    vector<Function> outputs;
    set<string> visited_functions;

    using IRGraphVisitor::visit;

    bool already_have(const string &name) {
        // Ignore dependencies on the output buffers
        for (const Function &output : outputs) {
            if (name == output.name() || starts_with(name, output.name() + ".")) {
                return true;
            }
        }
        for (const InferredArgument &arg : args) {
            if (arg.arg.name == name) {
                return true;
            }
        }
        return false;
    }

    void visit_exprs(const vector<Expr>& v) {
        for (Expr i : v) {
            visit_expr(i);
        }
    }

    void visit_expr(Expr e) {
        if (!e.defined()) return;
        e.accept(this);
    }

    void visit_function(const Function& func) {
        if (visited_functions.count(func.name())) return;
        visited_functions.insert(func.name());

        func.accept(this);

        // Function::accept hits all the Expr children of the
        // Function, but misses the buffers and images that might be
        // extern arguments.
        if (func.has_extern_definition()) {
            for (const ExternFuncArgument &extern_arg : func.extern_arguments()) {
                if (extern_arg.is_func()) {
                    visit_function(Function(extern_arg.func));
                } else if (extern_arg.is_buffer()) {
                    include_buffer(extern_arg.buffer);
                } else if (extern_arg.is_image_param()) {
                    include_parameter(extern_arg.image_param);
                }
            }
        }
    }

    void include_parameter(Parameter p) {
        if (!p.defined()) return;
        if (already_have(p.name())) return;

        Expr def, min, max;
        if (!p.is_buffer()) {
            def = p.get_scalar_expr();
            min = p.get_min_value();
            max = p.get_max_value();
        }

        InferredArgument a = {
            Argument(p.name(),
                     p.is_buffer() ? Argument::InputBuffer : Argument::InputScalar,
                     p.type(), p.dimensions(), def, min, max),
            p,
            Buffer<>()};
        args.push_back(a);

        // Visit child expressions
        if (!p.is_buffer()) {
            visit_expr(def);
            visit_expr(min);
            visit_expr(max);
        } else {
            for (int i = 0; i < p.dimensions(); i++) {
                visit_expr(p.min_constraint(i));
                visit_expr(p.extent_constraint(i));
                visit_expr(p.stride_constraint(i));
            }
        }
    }

    void include_buffer(Buffer<> b) {
        if (!b.defined()) return;
        if (already_have(b.name())) return;

        InferredArgument a = {
            Argument(b.name(), Argument::InputBuffer, b.type(), b.dimensions()),
            Parameter(),
            b};
        args.push_back(a);
    }

    void visit(const Load *op) {
        IRGraphVisitor::visit(op);
        include_parameter(op->param);
        include_buffer(op->image);
    }

    void visit(const Variable *op) {
        IRGraphVisitor::visit(op);
        include_parameter(op->param);
        include_buffer(op->image);
    }

    void visit(const Call *op) {
        IRGraphVisitor::visit(op);
        if (op->func.defined()) {
            Function fn(op->func);
            visit_function(fn);
        }
        include_buffer(op->image);
        include_parameter(op->param);
    }
};

}

vector<InferredArgument> infer_arguments(Stmt body, const vector<Function> &outputs) {
    vector<InferredArgument> inferred_args;
    // Infer an arguments vector by walking the IR
    InferArguments infer_args(inferred_args,
                              outputs,
                              body);

    // Sort the Arguments with all buffers first (alphabetical by name),
    // followed by all non-buffers (alphabetical by name).
    std::sort(inferred_args.begin(), inferred_args.end());

    return inferred_args;
}

}
}
<|endoftext|>


<commit_before><commit_msg>`ChunkMaster::render`: render only if `this->should_be_rendered`.<commit_after><|endoftext|>


<commit_before>/*=========================================================================

  Program:   Monteverdi2
  Language:  C++
  Date:      $Date$
  Version:   $Revision$

  Copyright (c) Centre National d'Etudes Spatiales. All rights reserved.
  See OTBCopyright.txt for details.

     This software is distributed WITHOUT ANY WARRANTY; without even
     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
     PURPOSE.  See the above copyright notices for more information.

=========================================================================*/

#include "mvdMainWindow.h"
#include "ui_mvdMainWindow.h"

//
// Qt includes (sorted by alphabetic order)
//// Must be included before system/custom includes.
#include <QtGui>

//
// System includes (sorted by alphabetic order)

//
// ITK includes (sorted by alphabetic order)

//
// OTB includes (sorted by alphabetic order)

//
// Monteverdi includes (sorted by alphabetic order)
#include "mvdAboutDialog.h"
#include "mvdApplication.h"
#include "mvdColorDynamicsController.h"
#include "mvdColorDynamicsWidget.h"
#include "mvdColorSetupController.h"
#include "mvdDatasetModel.h"
#include "mvdGLImageWidget.h"
#include "mvdImageModelRenderer.h"
#include "mvdImageViewManipulator.h"
#include "mvdQuicklookModel.h"
#include "mvdQuicklookViewManipulator.h"
#include "mvdVectorImageModel.h"

namespace mvd
{
/*
  TRANSLATOR mvd::MainWindow

  Necessary for lupdate to be aware of C++ namespaces.

  Context comment for translator.
*/

/*****************************************************************************/
MainWindow
::MainWindow( QWidget* parent, Qt::WindowFlags flags ) :
  QMainWindow( parent, flags ),
  m_UI( new mvd::Ui::MainWindow() )
{
  m_UI->setupUi( this );

  Initialize();
}

/*****************************************************************************/
MainWindow
::~MainWindow()
{
}

/*****************************************************************************/
void
MainWindow
::Initialize()
{
  setObjectName( "mvd::MainWindow" );
  setWindowTitle( PROJECT_NAME );

  // instanciate the manipulator and the renderer relative to this widget
  m_ImageViewManipulator = new ImageViewManipulator();
  m_ImageModelRenderer   = new ImageModelRenderer();

  // set the GLImageWidget as the centralWidget in MainWindow.
  setCentralWidget(
    new GLImageWidget(
      m_ImageViewManipulator,
      m_ImageModelRenderer,
      this
    )
  );

  // instanciate the Ql manipulator/renderer
  m_QLModelRenderer   = new ImageModelRenderer();
  m_QLViewManipulator = new QuicklookViewManipulator();

  // Connect centralWidget manipulator to Ql renderer when viewportRegionChanged
  QObject::connect(
    m_ImageViewManipulator, SIGNAL( ViewportRegionRepresentationChanged(const PointType&, const PointType&) ),
    m_QLModelRenderer, SLOT( OnViewportRegionRepresentationChanged(const PointType&, const PointType&) )
    );

  // Connect ql mousePressEventpressed to centralWidget manipulator
  QObject::connect(
    m_QLViewManipulator, SIGNAL( ViewportRegionChanged(double, double) ),
    m_ImageViewManipulator, SLOT( OnViewportRegionChanged(double, double) )
  );

  // add the needed docks
  InitializeDockWidgets();

  // add needed widget to the status bar
  InitializeStatusBarWidgets();

  // Connect Quit action of main menu to QApplication's quit() slot.
  QObject::connect(
    m_UI->action_Quit, SIGNAL( activated() ),
    qApp, SLOT( quit() )
  );

  // Connect Appllication and MainWindow when selected model is about
  // to change.
  QObject::connect(
    qApp, SIGNAL( AboutToChangeSelectedModel( const AbstractModel* ) ),
    this, SLOT( OnAboutToChangeSelectedModel( const AbstractModel* ) )
  );

  // Connect Appllication and MainWindow when selected model has been
  // changed.
  QObject::connect(
    qApp, SIGNAL( SelectedModelChanged( AbstractModel* ) ),
    this, SLOT( OnSelectedModelChanged( AbstractModel* ) )
  );

  // Change to NULL model to force emitting GUI signals when GUI is
  // instanciated. So, GUI will be initialized and controller-widgets
  // disabled.
  Application::Instance()->SetModel( NULL );
}

/*****************************************************************************/
void
MainWindow
::InitializeStatusBarWidgets()
{
  // Add a QLabel to the status bar to show pixel coordinates
  QLabel * currentPixelLabel = new QLabel(statusBar());
  currentPixelLabel->setAlignment(Qt::AlignCenter);

  // connect this widget to receive notification from
  // ImageViewManipulator
  QObject::connect(
    m_ImageViewManipulator,
    SIGNAL( CurrentCoordinatesUpdated(const QString& ) ),
    currentPixelLabel,
    SLOT( setText(const QString &) )
  );

  statusBar()->addWidget(currentPixelLabel);
}

/*****************************************************************************/
void
MainWindow
::InitializeDockWidgets()
{
  //
  // EXPERIMENTAL QUICKLOOK Widget.
  assert( qobject_cast< GLImageWidget* >( centralWidget() )!=NULL );

  GLImageWidget* qlWidget = new GLImageWidget(
    m_QLViewManipulator,
    m_QLModelRenderer,
    this,
    qobject_cast< GLImageWidget* >( centralWidget() )
  );
  // TODO: Set better minimum size for quicklook GL widget.
  qlWidget->setMinimumSize(100,100);

  AddWidgetToDock(
    qlWidget,
    QUICKLOOK_DOCK,
    tr( "Quicklook" ),
    Qt::LeftDockWidgetArea
    );

  //
  // COLOR SETUP.
  ColorSetupWidget* colorSetupWgt = new ColorSetupWidget( this );

  ColorSetupController* colorSetupCtrl = new ColorSetupController(
    // wraps:
    colorSetupWgt,
    // as child of:
    AddWidgetToDock(
      colorSetupWgt,
      VIDEO_COLOR_SETUP_DOCK,
      tr( "Video color setup" ),
      Qt::LeftDockWidgetArea
    )
  );

  //
  // COLOR DYNAMICS.
  ColorDynamicsWidget* colorDynWgt = new ColorDynamicsWidget( this );

  // Controller is childed to dock.
  ColorDynamicsController* colorDynamicsCtrl = new ColorDynamicsController(
    // wraps:
    colorDynWgt,
    // as child of:
    AddWidgetToDock(
      colorDynWgt,
      VIDEO_COLOR_DYNAMICS_DOCK,
      tr( "Video color dynamics" ),
      Qt::LeftDockWidgetArea
    )
  );

  //
  // CHAIN CONTROLLERS.
  // Forward model update signals of color-setup controller...
  QObject::connect(
    colorSetupCtrl,
    SIGNAL( RgbChannelIndexChanged( RgbaChannel, int ) ),
    // to: ...color-dynamics controller model update signal.
    colorDynamicsCtrl,
    SLOT( OnRgbChannelIndexChanged( RgbaChannel, int ) )
  );

  //
  // EXPERIMENTAL TOOLBOX.

#if 0

  QToolBox* toolBox = new QToolBox( this );

  toolBox->setObjectName( "mvd::VideoColorToolBox" );

  toolBox->addItem( new ColorSetupWidget( toolBox ), tr( "Video color setup" ) );
  toolBox->addItem( new ColorDynamicsWidget( toolBox ), tr( "Video color dynamics" ) );

  AddWidgetToDock(
    toolBox,
    "videoColorSettingsDock",
    tr( "Video color dynamics" ),
    Qt::LeftDockWidgetArea
  );
#endif
}

/*****************************************************************************/
QDockWidget*
MainWindow
::AddWidgetToDock( QWidget* widget,
		   const QString& dockName,
		   const QString& dockTitle,
		   Qt::DockWidgetArea dockArea )
{
  // New dock.
  QDockWidget* dockWidget = new QDockWidget( dockTitle, this );

  // You can use findChild( dockName ) to get dock-widget.
  dockWidget->setObjectName( dockName );
  dockWidget->setWidget( widget );

  // Features.
  dockWidget->setFloating( false );
  dockWidget->setFeatures(
    QDockWidget::DockWidgetMovable |
    QDockWidget::DockWidgetFloatable
  );

  // Add dock.
  addDockWidget( dockArea, dockWidget );

  return dockWidget;
}

/*****************************************************************************/
/* SLOTS                                                                     */
/*****************************************************************************/
void
MainWindow
::on_action_Open_activated()
{
  QString filename(
    QFileDialog::getOpenFileName( this, tr( "Open file..." ) )
  );

  if( filename.isNull() )
    {
    return;
    }

  try
    {
    // TODO: Replace with complex model (list of DatasetModel) when implemented.
    DatasetModel* model = Application::LoadDatasetModel(
      filename,
      // TODO: Remove width and height from dataset model loading.
      centralWidget()->width(), centralWidget()->height()
    );

    Application::Instance()->SetModel( model );
    }
  catch( std::exception& exc )
    {
    QMessageBox::warning( this, tr("Exception!"), exc.what() );
    return;
    }
}

/*****************************************************************************/
void
MainWindow
::on_action_About_activated()
{
  AboutDialog aboutDialog( this );

  aboutDialog.exec();
}

/*****************************************************************************/
void
MainWindow
::OnAboutToChangeSelectedModel( const AbstractModel* )
{
  //
  // COLOR SETUP.
  SetControllerModel( GetColorSetupDock(), NULL );

  //
  // COLOR DYNAMICS.
  SetControllerModel( GetColorDynamicsDock(), NULL );

  // De-assign models to view after controllers (LIFO disconnect).
  qobject_cast< GLImageWidget *>( centralWidget() )->SetImageModel( NULL );
  qobject_cast< GLImageWidget * >( GetQuicklookDock()->widget() )->SetImageModel(
    NULL
  );

  //
  //
  const Application* app = Application::ConstInstance();
  assert( app!=NULL );

  const DatasetModel* datasetModel =
    qobject_cast< const DatasetModel* >( app->GetModel() );

  // It is Ok there is no previously selected model (e.g. at
  // application startup.
  if( datasetModel==NULL )
    {
    return;
    }

  assert( datasetModel->HasSelectedImageModel() );

  const VectorImageModel* vectorImageModel =
    qobject_cast< const VectorImageModel* >(
      datasetModel->GetSelectedImageModel()
    );

  assert( vectorImageModel!=NULL );

  //
  // MAIN VIEW.

  // Disconnect previously selected model from view.
  QObject::disconnect(
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    centralWidget(),
    SLOT( updateGL() )
  );

  // TODO : where to do this
  QObject::disconnect(
    // vectorImageModel->GetQuicklookModel(),
    // TODO: Remove temporary hack by better design.
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );

  //
  // disconnect the vectorimage model spacing change (when zooming)
  QObject::disconnect(
    vectorImageModel,
    SIGNAL( SpacingChanged(const SpacingType&) ),
    // to:
    centralWidget(),
    SLOT( OnSpacingChanged(const SpacingType&)  )
  );

  // disconnect signal used to update the ql widget
  QObject::disconnect(
    centralWidget(),
    SIGNAL( CentralWidgetUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );

}

/*****************************************************************************/
void
MainWindow
::OnSelectedModelChanged( AbstractModel* model )
{
  if( model==NULL )
    return;

  DatasetModel* datasetModel = qobject_cast< DatasetModel* >( model );

  assert( datasetModel!=NULL );
  assert( datasetModel->HasSelectedImageModel() );

  VectorImageModel* vectorImageModel =
    qobject_cast< VectorImageModel* >(
      datasetModel->GetSelectedImageModel()
    );

  assert( vectorImageModel!=NULL );

  //
  // COLOR SETUP.
  SetControllerModel( GetColorSetupDock(), vectorImageModel );

  //
  // COLOR DYNAMICS.
  SetControllerModel( GetColorDynamicsDock(), vectorImageModel );

  //
  // MAIN VIEW.

  // Assign newly selected model to view.
  qobject_cast< GLImageWidget *>( centralWidget() )->SetImageModel(
    vectorImageModel
  );

  // Connect newly selected model to view (after all other widgets are
  // connected to prevent signals/slots to produce multiple view
  // refreshes).
  QObject::connect(
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    centralWidget(),
    SLOT( updateGL()  )
  );

  //
  // QUICKLOOK VIEW.

  // Assign newly selected model to view.
  qobject_cast< GLImageWidget * >( GetQuicklookDock()->widget() )->SetImageModel(
    vectorImageModel->GetQuicklookModel()
  );

  // Connect newly selected model to view (after all other widgets are
  // connected to prevent signals/slots to produce multiple view
  // refreshes).
  // TODO : find where to do this
  QObject::connect(
    // vectorImageModel->GetQuicklookModel(),
    // TODO: Remove temporary hack by better design.
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );

  //
  // connect the vectorimage model spacing change (when zooming)
  QObject::connect(
    vectorImageModel,
    SIGNAL( SpacingChanged(const SpacingType&) ),
    // to:
    centralWidget(),
    SLOT( OnSpacingChanged(const SpacingType&)  )
  );

  // signal used to update the ql widget
  QObject::connect(
    centralWidget(),
    SIGNAL( CentralWidgetUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );
}

/*****************************************************************************/

} // end namespace 'mvd'
<commit_msg>ENH: More informative window title<commit_after>/*=========================================================================

  Program:   Monteverdi2
  Language:  C++
  Date:      $Date$
  Version:   $Revision$

  Copyright (c) Centre National d'Etudes Spatiales. All rights reserved.
  See OTBCopyright.txt for details.

     This software is distributed WITHOUT ANY WARRANTY; without even
     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
     PURPOSE.  See the above copyright notices for more information.

=========================================================================*/

#include "mvdMainWindow.h"
#include "ui_mvdMainWindow.h"

//
// Qt includes (sorted by alphabetic order)
//// Must be included before system/custom includes.
#include <QtGui>

//
// System includes (sorted by alphabetic order)

//
// ITK includes (sorted by alphabetic order)

//
// OTB includes (sorted by alphabetic order)

//
// Monteverdi includes (sorted by alphabetic order)
#include "mvdAboutDialog.h"
#include "mvdApplication.h"
#include "mvdColorDynamicsController.h"
#include "mvdColorDynamicsWidget.h"
#include "mvdColorSetupController.h"
#include "mvdDatasetModel.h"
#include "mvdGLImageWidget.h"
#include "mvdImageModelRenderer.h"
#include "mvdImageViewManipulator.h"
#include "mvdQuicklookModel.h"
#include "mvdQuicklookViewManipulator.h"
#include "mvdVectorImageModel.h"

namespace mvd
{
/*
  TRANSLATOR mvd::MainWindow

  Necessary for lupdate to be aware of C++ namespaces.

  Context comment for translator.
*/

/*****************************************************************************/
MainWindow
::MainWindow( QWidget* parent, Qt::WindowFlags flags ) :
  QMainWindow( parent, flags ),
  m_UI( new mvd::Ui::MainWindow() )
{
  m_UI->setupUi( this );

  Initialize();
}

/*****************************************************************************/
MainWindow
::~MainWindow()
{
}

/*****************************************************************************/
void
MainWindow
::Initialize()
{
  setObjectName( "mvd::MainWindow" );
  setWindowTitle( PROJECT_NAME );

  // instanciate the manipulator and the renderer relative to this widget
  m_ImageViewManipulator = new ImageViewManipulator();
  m_ImageModelRenderer   = new ImageModelRenderer();

  // set the GLImageWidget as the centralWidget in MainWindow.
  setCentralWidget(
    new GLImageWidget(
      m_ImageViewManipulator,
      m_ImageModelRenderer,
      this
    )
  );

  // instanciate the Ql manipulator/renderer
  m_QLModelRenderer   = new ImageModelRenderer();
  m_QLViewManipulator = new QuicklookViewManipulator();

  // Connect centralWidget manipulator to Ql renderer when viewportRegionChanged
  QObject::connect(
    m_ImageViewManipulator, SIGNAL( ViewportRegionRepresentationChanged(const PointType&, const PointType&) ),
    m_QLModelRenderer, SLOT( OnViewportRegionRepresentationChanged(const PointType&, const PointType&) )
    );

  // Connect ql mousePressEventpressed to centralWidget manipulator
  QObject::connect(
    m_QLViewManipulator, SIGNAL( ViewportRegionChanged(double, double) ),
    m_ImageViewManipulator, SLOT( OnViewportRegionChanged(double, double) )
  );

  // add the needed docks
  InitializeDockWidgets();

  // add needed widget to the status bar
  InitializeStatusBarWidgets();

  // Connect Quit action of main menu to QApplication's quit() slot.
  QObject::connect(
    m_UI->action_Quit, SIGNAL( activated() ),
    qApp, SLOT( quit() )
  );

  // Connect Appllication and MainWindow when selected model is about
  // to change.
  QObject::connect(
    qApp, SIGNAL( AboutToChangeSelectedModel( const AbstractModel* ) ),
    this, SLOT( OnAboutToChangeSelectedModel( const AbstractModel* ) )
  );

  // Connect Appllication and MainWindow when selected model has been
  // changed.
  QObject::connect(
    qApp, SIGNAL( SelectedModelChanged( AbstractModel* ) ),
    this, SLOT( OnSelectedModelChanged( AbstractModel* ) )
  );

  // Change to NULL model to force emitting GUI signals when GUI is
  // instanciated. So, GUI will be initialized and controller-widgets
  // disabled.
  Application::Instance()->SetModel( NULL );
}

/*****************************************************************************/
void
MainWindow
::InitializeStatusBarWidgets()
{
  // Add a QLabel to the status bar to show pixel coordinates
  QLabel * currentPixelLabel = new QLabel(statusBar());
  currentPixelLabel->setAlignment(Qt::AlignCenter);

  // connect this widget to receive notification from
  // ImageViewManipulator
  QObject::connect(
    m_ImageViewManipulator,
    SIGNAL( CurrentCoordinatesUpdated(const QString& ) ),
    currentPixelLabel,
    SLOT( setText(const QString &) )
  );

  statusBar()->addWidget(currentPixelLabel);
}

/*****************************************************************************/
void
MainWindow
::InitializeDockWidgets()
{
  //
  // EXPERIMENTAL QUICKLOOK Widget.
  assert( qobject_cast< GLImageWidget* >( centralWidget() )!=NULL );

  GLImageWidget* qlWidget = new GLImageWidget(
    m_QLViewManipulator,
    m_QLModelRenderer,
    this,
    qobject_cast< GLImageWidget* >( centralWidget() )
  );
  // TODO: Set better minimum size for quicklook GL widget.
  qlWidget->setMinimumSize(100,100);

  AddWidgetToDock(
    qlWidget,
    QUICKLOOK_DOCK,
    tr( "Quicklook" ),
    Qt::LeftDockWidgetArea
    );

  //
  // COLOR SETUP.
  ColorSetupWidget* colorSetupWgt = new ColorSetupWidget( this );

  ColorSetupController* colorSetupCtrl = new ColorSetupController(
    // wraps:
    colorSetupWgt,
    // as child of:
    AddWidgetToDock(
      colorSetupWgt,
      VIDEO_COLOR_SETUP_DOCK,
      tr( "Video color setup" ),
      Qt::LeftDockWidgetArea
    )
  );

  //
  // COLOR DYNAMICS.
  ColorDynamicsWidget* colorDynWgt = new ColorDynamicsWidget( this );

  // Controller is childed to dock.
  ColorDynamicsController* colorDynamicsCtrl = new ColorDynamicsController(
    // wraps:
    colorDynWgt,
    // as child of:
    AddWidgetToDock(
      colorDynWgt,
      VIDEO_COLOR_DYNAMICS_DOCK,
      tr( "Video color dynamics" ),
      Qt::LeftDockWidgetArea
    )
  );

  //
  // CHAIN CONTROLLERS.
  // Forward model update signals of color-setup controller...
  QObject::connect(
    colorSetupCtrl,
    SIGNAL( RgbChannelIndexChanged( RgbaChannel, int ) ),
    // to: ...color-dynamics controller model update signal.
    colorDynamicsCtrl,
    SLOT( OnRgbChannelIndexChanged( RgbaChannel, int ) )
  );

  //
  // EXPERIMENTAL TOOLBOX.

#if 0

  QToolBox* toolBox = new QToolBox( this );

  toolBox->setObjectName( "mvd::VideoColorToolBox" );

  toolBox->addItem( new ColorSetupWidget( toolBox ), tr( "Video color setup" ) );
  toolBox->addItem( new ColorDynamicsWidget( toolBox ), tr( "Video color dynamics" ) );

  AddWidgetToDock(
    toolBox,
    "videoColorSettingsDock",
    tr( "Video color dynamics" ),
    Qt::LeftDockWidgetArea
  );
#endif
}

/*****************************************************************************/
QDockWidget*
MainWindow
::AddWidgetToDock( QWidget* widget,
		   const QString& dockName,
		   const QString& dockTitle,
		   Qt::DockWidgetArea dockArea )
{
  // New dock.
  QDockWidget* dockWidget = new QDockWidget( dockTitle, this );

  // You can use findChild( dockName ) to get dock-widget.
  dockWidget->setObjectName( dockName );
  dockWidget->setWidget( widget );

  // Features.
  dockWidget->setFloating( false );
  dockWidget->setFeatures(
    QDockWidget::DockWidgetMovable |
    QDockWidget::DockWidgetFloatable
  );

  // Add dock.
  addDockWidget( dockArea, dockWidget );

  return dockWidget;
}

/*****************************************************************************/
/* SLOTS                                                                     */
/*****************************************************************************/
void
MainWindow
::on_action_Open_activated()
{
  QString filename(
    QFileDialog::getOpenFileName( this, tr( "Open file..." ) )
  );

  if( filename.isNull() )
    {
    return;
    }

  try
    {
    // TODO: Replace with complex model (list of DatasetModel) when implemented.
    DatasetModel* model = Application::LoadDatasetModel(
      filename,
      // TODO: Remove width and height from dataset model loading.
      centralWidget()->width(), centralWidget()->height()
    );

    Application::Instance()->SetModel( model );
    }
  catch( std::exception& exc )
    {
    QMessageBox::warning( this, tr("Exception!"), exc.what() );
    return;
    }
}

/*****************************************************************************/
void
MainWindow
::on_action_About_activated()
{
  AboutDialog aboutDialog( this );

  aboutDialog.exec();
}

/*****************************************************************************/
void
MainWindow
::OnAboutToChangeSelectedModel( const AbstractModel* )
{
  //
  // COLOR SETUP.
  SetControllerModel( GetColorSetupDock(), NULL );

  //
  // COLOR DYNAMICS.
  SetControllerModel( GetColorDynamicsDock(), NULL );

  // De-assign models to view after controllers (LIFO disconnect).
  qobject_cast< GLImageWidget *>( centralWidget() )->SetImageModel( NULL );
  qobject_cast< GLImageWidget * >( GetQuicklookDock()->widget() )->SetImageModel(
    NULL
  );

  //
  //
  const Application* app = Application::ConstInstance();
  assert( app!=NULL );

  const DatasetModel* datasetModel =
    qobject_cast< const DatasetModel* >( app->GetModel() );

  // It is Ok there is no previously selected model (e.g. at
  // application startup.
  if( datasetModel==NULL )
    {
    return;
    }

  assert( datasetModel->HasSelectedImageModel() );

  const VectorImageModel* vectorImageModel =
    qobject_cast< const VectorImageModel* >(
      datasetModel->GetSelectedImageModel()
    );

  assert( vectorImageModel!=NULL );

  //
  // MAIN VIEW.

  // Disconnect previously selected model from view.
  QObject::disconnect(
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    centralWidget(),
    SLOT( updateGL() )
  );

  // TODO : where to do this
  QObject::disconnect(
    // vectorImageModel->GetQuicklookModel(),
    // TODO: Remove temporary hack by better design.
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );

  //
  // disconnect the vectorimage model spacing change (when zooming)
  QObject::disconnect(
    vectorImageModel,
    SIGNAL( SpacingChanged(const SpacingType&) ),
    // to:
    centralWidget(),
    SLOT( OnSpacingChanged(const SpacingType&)  )
  );

  // disconnect signal used to update the ql widget
  QObject::disconnect(
    centralWidget(),
    SIGNAL( CentralWidgetUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );

}

/*****************************************************************************/
void
MainWindow
::OnSelectedModelChanged( AbstractModel* model )
{
  if( model==NULL )
    return;

  DatasetModel* datasetModel = qobject_cast< DatasetModel* >( model );

  assert( datasetModel!=NULL );
  assert( datasetModel->HasSelectedImageModel() );

  VectorImageModel* vectorImageModel =
    qobject_cast< VectorImageModel* >(
      datasetModel->GetSelectedImageModel()
    );

  assert( vectorImageModel!=NULL );

  itk::OStringStream oss;
  oss<<PROJECT_NAME<<" - "<<ToStdString(vectorImageModel->GetFilename());
  //<<" ("<<vectorImageModel->ToImageBase()->GetNumberOfComponentsPerPixel()<<tr(" bands, ")<<vectorImageModel->ToImageBase()->GetLargestPossibleRegion().GetSize()[0]<<"x"<<vectorImageModel->ToImageBase()->GetLargestPossibleRegion().GetSize()[1]<<tr(" pixels)");

  setWindowTitle( FromStdString(oss.str()) );

  //
  // COLOR SETUP.
  SetControllerModel( GetColorSetupDock(), vectorImageModel );

  //
  // COLOR DYNAMICS.
  SetControllerModel( GetColorDynamicsDock(), vectorImageModel );

  //
  // MAIN VIEW.

  // Assign newly selected model to view.
  qobject_cast< GLImageWidget *>( centralWidget() )->SetImageModel(
    vectorImageModel
  );

  // Connect newly selected model to view (after all other widgets are
  // connected to prevent signals/slots to produce multiple view
  // refreshes).
  QObject::connect(
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    centralWidget(),
    SLOT( updateGL()  )
  );

  //
  // QUICKLOOK VIEW.

  // Assign newly selected model to view.
  qobject_cast< GLImageWidget * >( GetQuicklookDock()->widget() )->SetImageModel(
    vectorImageModel->GetQuicklookModel()
  );

  // Connect newly selected model to view (after all other widgets are
  // connected to prevent signals/slots to produce multiple view
  // refreshes).
  // TODO : find where to do this
  QObject::connect(
    // vectorImageModel->GetQuicklookModel(),
    // TODO: Remove temporary hack by better design.
    vectorImageModel,
    SIGNAL( SettingsUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );

  //
  // connect the vectorimage model spacing change (when zooming)
  QObject::connect(
    vectorImageModel,
    SIGNAL( SpacingChanged(const SpacingType&) ),
    // to:
    centralWidget(),
    SLOT( OnSpacingChanged(const SpacingType&)  )
  );

  // signal used to update the ql widget
  QObject::connect(
    centralWidget(),
    SIGNAL( CentralWidgetUpdated() ),
    // to:
    GetQuicklookDock()->widget(),
    SLOT( updateGL()  )
  );
}

/*****************************************************************************/

} // end namespace 'mvd'
<|endoftext|>


<commit_before>#ifndef __COMPUTE_TASK_HPP_INCLUDED
#define __COMPUTE_TASK_HPP_INCLUDED

#include "entity.hpp"
#include "compute_task_struct.hpp"
#include "pre_iterate_callback.hpp"
#include "post_iterate_callback.hpp"
#include "family_templates.hpp"
#include "code/ylikuutio/opengl/opengl.hpp"
#include "code/ylikuutio/hierarchy/hierarchy_templates.hpp"

// Include GLEW
#include "code/ylikuutio/opengl/ylikuutio_glew.hpp" // GLfloat, GLuint etc.

// Include standard headers
#include <cstddef>  // std::size_t
#include <iostream> // std::cout, std::cin, std::cerr
#include <memory>   // std::make_shared, std::shared_ptr
#include <queue>    // std::queue
#include <stdint.h> // uint32_t etc.
#include <vector>   // std::vector

// `yli::ontology::ComputeTask` is a class which contains the data for a single
// computing task. `ComputeTask` does not have the OpenGL shaders used to process
// the data. Instead, the shaders are contained by the parent `Entity` which is
// an `yli::ontology::ComputeTask` instance.
//
// For example, `yli::ontology::Shader` can have vertex and fragment shaders for
// computing the distances between nodes of a graph. Then, each `ComputeTask`
// would contain the graph data, eg. as a distance matrix. Then, rendering a
// `ComputeTask` means computing that task.
//
// Rendering a `ComputeTask` is done by iterating the task until either
// `end_condition_callback_engine->execute()` returns `true`, or until
// `n_max_iterations` is reached. If `end_condition_callback_engine` is `nullptr`
// or `end_condition_callback_engine->execute()` does not not return an `AnyValue`
// which contains `datatypes::BOOL`, then `end_condition_callback_engine` is ignored
// and `n_max_iterations` is the exact number of iterations to be done. However,
// even if `end_condition_callback_engine->execute()` would return an invalid return
// value, that is, not an `AnyValue` which contains `datatypes::BOOL`,
// `end_condition_callback_engine->execute()` is still called and taken into account
// in every iteration.
//
// When iterating, there is a `PreIterateCallback` which is executed before each iteration,
// and also a `PostIterateCallback` which is executed correspondingly after each iteration.
// Of course `PreRenderCallback` and `PostRenderCallback` can be used as well.
// `PreRenderCallback` gets executed before the first `PreIterateCallback` call, and
// `PostRenderCallback` gets executed after the last `PostRenderCallback` call.
// All these callbacks are optional and can be left to `nullptr` if they are not needed.

namespace yli
{
    namespace callback_system
    {
        class CallbackEngine;
    }

    namespace ontology
    {
        class Shader;

        class ComputeTask: public yli::ontology::Entity
        {
            public:
                ComputeTask(yli::ontology::Universe* const universe, const ComputeTaskStruct& compute_task_struct)
                    : Entity(universe)
                {
                    // constructor.
                    this->parent = compute_task_struct.parent;
                    this->end_condition_callback_engine = compute_task_struct.end_condition_callback_engine;
                    this->n_max_iterations = compute_task_struct.n_max_iterations;
                    this->compute_taskID = compute_task_struct.compute_taskID;
                    this->texture_width = compute_task_struct.texture_width;
                    this->texture_height = compute_task_struct.texture_height;

                    this->framebuffer = 0;
                    this->texture = 0;
                    this->render_buffer = 0;
                    this->vertex_position_modelspaceID = 0;
                    this->vertexUVID                   = 0;
                    this->vertexbuffer                 = 0;
                    this->uvbuffer                     = 0;

                    this->preiterate_callback = compute_task_struct.preiterate_callback;
                    this->postiterate_callback = compute_task_struct.postiterate_callback;

                    // Get `childID` from `Shader` and set pointer to this `ComputeTask`.
                    this->bind_to_parent();

                    // Create FBO (off-screen framebuffer object).
                    glGenFramebuffers(1, &this->framebuffer);

                    // Bind offscreen buffer.
                    glBindFramebuffer(GL_FRAMEBUFFER, this->framebuffer);

                    // Create texture.
                    glGenTextures(1, &this->texture);
                    glBindTexture(GL_TEXTURE_2D, this->texture);

                    // Define texture.
                    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, this->texture_width, this->texture_height, 0, GL_RGB, GL_UNSIGNED_BYTE, NULL);

                    yli::opengl::set_filtering_parameters();

                    // Attach texture.
                    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, this->texture, 0);

                    // Create and bind render buffer with depth and stencil attachments.
                    glGenRenderbuffers(1, &this->render_buffer);
                    glBindRenderbuffer(GL_RENDERBUFFER, this->render_buffer);
                    glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8, this->texture_width, this->texture_height);
                    glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_RENDERBUFFER, this->render_buffer);

                    if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
                    {
                        std::cerr << "ERROR: `ComputeTask::ComputeTask`: framebuffer is not complete!\n";
                    }

                    // `yli::ontology::Entity` member variables begin here.
                    this->type_string = "yli::ontology::ComputeTask*";
                    this->can_be_erased = true;
                }

                // destructor.
                ~ComputeTask();

                yli::ontology::Entity* get_parent() const override;

                template<class T1>
                    friend void yli::hierarchy::bind_child_to_parent(T1 child_pointer, std::vector<T1>& child_pointer_vector, std::queue<std::size_t>& free_childID_queue, std::size_t& number_of_children);
                template<class T1>
                    friend std::size_t yli::ontology::get_number_of_descendants(const std::vector<T1>& child_pointer_vector);
                template<class T1>
                    friend void yli::ontology::render_children(const std::vector<T1>& child_pointer_vector);

            private:
                void bind_to_parent();

                // This method renders this `ComputeTask`, that is, computes this task.
                void render();

                void preiterate() const;
                void postiterate() const;

                std::size_t get_number_of_children() const override;
                std::size_t get_number_of_descendants() const override;

                yli::ontology::Shader* parent; // pointer to the `Shader`.

                // End iterating when `end_condition_callback_engine` returns `true`.
                std::shared_ptr<yli::callback_system::CallbackEngine> end_condition_callback_engine;

                // This is the maximum number of iterations.
                // If `end_condition_callback_engine` is `nullptr`, then this is the number of iterations.
                // If `end_condition_callback_engine` is not `nullptr`, then this is the maximum number of iterations.
                std::size_t n_max_iterations;

                std::size_t compute_taskID;

                std::size_t texture_width;
                std::size_t texture_height;

                uint32_t framebuffer;
                uint32_t texture;
                uint32_t render_buffer;

                uint32_t vertex_position_modelspaceID;
                uint32_t vertexUVID;

                uint32_t vertexbuffer;
                uint32_t uvbuffer;

                PreIterateCallback preiterate_callback;
                PostIterateCallback postiterate_callback;
        };
    }
}

#endif
<commit_msg>`yli::ontology::ComputeTask`: edited whitespace.<commit_after>#ifndef __COMPUTE_TASK_HPP_INCLUDED
#define __COMPUTE_TASK_HPP_INCLUDED

#include "entity.hpp"
#include "compute_task_struct.hpp"
#include "pre_iterate_callback.hpp"
#include "post_iterate_callback.hpp"
#include "family_templates.hpp"
#include "code/ylikuutio/opengl/opengl.hpp"
#include "code/ylikuutio/hierarchy/hierarchy_templates.hpp"

// Include GLEW
#include "code/ylikuutio/opengl/ylikuutio_glew.hpp" // GLfloat, GLuint etc.

// Include standard headers
#include <cstddef>  // std::size_t
#include <iostream> // std::cout, std::cin, std::cerr
#include <memory>   // std::make_shared, std::shared_ptr
#include <queue>    // std::queue
#include <stdint.h> // uint32_t etc.
#include <vector>   // std::vector

// `yli::ontology::ComputeTask` is a class which contains the data for a single
// computing task. `ComputeTask` does not have the OpenGL shaders used to process
// the data. Instead, the shaders are contained by the parent `Entity` which is
// an `yli::ontology::ComputeTask` instance.
//
// For example, `yli::ontology::Shader` can have vertex and fragment shaders for
// computing the distances between nodes of a graph. Then, each `ComputeTask`
// would contain the graph data, eg. as a distance matrix. Then, rendering a
// `ComputeTask` means computing that task.
//
// Rendering a `ComputeTask` is done by iterating the task until either
// `end_condition_callback_engine->execute()` returns `true`, or until
// `n_max_iterations` is reached. If `end_condition_callback_engine` is `nullptr`
// or `end_condition_callback_engine->execute()` does not not return an `AnyValue`
// which contains `datatypes::BOOL`, then `end_condition_callback_engine` is ignored
// and `n_max_iterations` is the exact number of iterations to be done. However,
// even if `end_condition_callback_engine->execute()` would return an invalid return
// value, that is, not an `AnyValue` which contains `datatypes::BOOL`,
// `end_condition_callback_engine->execute()` is still called and taken into account
// in every iteration.
//
// When iterating, there is a `PreIterateCallback` which is executed before each iteration,
// and also a `PostIterateCallback` which is executed correspondingly after each iteration.
// Of course `PreRenderCallback` and `PostRenderCallback` can be used as well.
// `PreRenderCallback` gets executed before the first `PreIterateCallback` call, and
// `PostRenderCallback` gets executed after the last `PostRenderCallback` call.
// All these callbacks are optional and can be left to `nullptr` if they are not needed.

namespace yli
{
    namespace callback_system
    {
        class CallbackEngine;
    }

    namespace ontology
    {
        class Shader;

        class ComputeTask: public yli::ontology::Entity
        {
            public:
                ComputeTask(yli::ontology::Universe* const universe, const ComputeTaskStruct& compute_task_struct)
                    : Entity(universe)
                {
                    // constructor.
                    this->parent = compute_task_struct.parent;
                    this->end_condition_callback_engine = compute_task_struct.end_condition_callback_engine;
                    this->n_max_iterations = compute_task_struct.n_max_iterations;
                    this->compute_taskID = compute_task_struct.compute_taskID;
                    this->texture_width = compute_task_struct.texture_width;
                    this->texture_height = compute_task_struct.texture_height;

                    this->framebuffer                  = 0;
                    this->texture                      = 0;
                    this->render_buffer                = 0;
                    this->vertex_position_modelspaceID = 0;
                    this->vertexUVID                   = 0;
                    this->vertexbuffer                 = 0;
                    this->uvbuffer                     = 0;

                    this->preiterate_callback = compute_task_struct.preiterate_callback;
                    this->postiterate_callback = compute_task_struct.postiterate_callback;

                    // Get `childID` from `Shader` and set pointer to this `ComputeTask`.
                    this->bind_to_parent();

                    // Create FBO (off-screen framebuffer object).
                    glGenFramebuffers(1, &this->framebuffer);

                    // Bind offscreen buffer.
                    glBindFramebuffer(GL_FRAMEBUFFER, this->framebuffer);

                    // Create texture.
                    glGenTextures(1, &this->texture);
                    glBindTexture(GL_TEXTURE_2D, this->texture);

                    // Define texture.
                    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, this->texture_width, this->texture_height, 0, GL_RGB, GL_UNSIGNED_BYTE, NULL);

                    yli::opengl::set_filtering_parameters();

                    // Attach texture.
                    glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, this->texture, 0);

                    // Create and bind render buffer with depth and stencil attachments.
                    glGenRenderbuffers(1, &this->render_buffer);
                    glBindRenderbuffer(GL_RENDERBUFFER, this->render_buffer);
                    glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8, this->texture_width, this->texture_height);
                    glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT, GL_RENDERBUFFER, this->render_buffer);

                    if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != GL_FRAMEBUFFER_COMPLETE)
                    {
                        std::cerr << "ERROR: `ComputeTask::ComputeTask`: framebuffer is not complete!\n";
                    }

                    // `yli::ontology::Entity` member variables begin here.
                    this->type_string = "yli::ontology::ComputeTask*";
                    this->can_be_erased = true;
                }

                // destructor.
                ~ComputeTask();

                yli::ontology::Entity* get_parent() const override;

                template<class T1>
                    friend void yli::hierarchy::bind_child_to_parent(T1 child_pointer, std::vector<T1>& child_pointer_vector, std::queue<std::size_t>& free_childID_queue, std::size_t& number_of_children);
                template<class T1>
                    friend std::size_t yli::ontology::get_number_of_descendants(const std::vector<T1>& child_pointer_vector);
                template<class T1>
                    friend void yli::ontology::render_children(const std::vector<T1>& child_pointer_vector);

            private:
                void bind_to_parent();

                // This method renders this `ComputeTask`, that is, computes this task.
                void render();

                void preiterate() const;
                void postiterate() const;

                std::size_t get_number_of_children() const override;
                std::size_t get_number_of_descendants() const override;

                yli::ontology::Shader* parent; // pointer to the `Shader`.

                // End iterating when `end_condition_callback_engine` returns `true`.
                std::shared_ptr<yli::callback_system::CallbackEngine> end_condition_callback_engine;

                // This is the maximum number of iterations.
                // If `end_condition_callback_engine` is `nullptr`, then this is the number of iterations.
                // If `end_condition_callback_engine` is not `nullptr`, then this is the maximum number of iterations.
                std::size_t n_max_iterations;

                std::size_t compute_taskID;

                std::size_t texture_width;
                std::size_t texture_height;

                uint32_t framebuffer;
                uint32_t texture;
                uint32_t render_buffer;

                uint32_t vertex_position_modelspaceID;
                uint32_t vertexUVID;

                uint32_t vertexbuffer;
                uint32_t uvbuffer;

                PreIterateCallback preiterate_callback;
                PostIterateCallback postiterate_callback;
        };
    }
}

#endif
<|endoftext|>


<commit_before>/*
 * %injeqt copyright begin%
 * Copyright 2014 Rafał Malinowski (rafal.przemyslaw.malinowski@gmail.com)
 * %injeqt copyright end%
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */

#include "dependency-extractor.h"

#include "dependency.h"
#include "implements-extractor.h"
#include "setter-method.h"
#include "type.h"
#include "type-relations.h"
#include "type-relations-factory.h"

#include <QtCore/QMetaMethod>
#include <QtCore/QMetaType>
#include <algorithm>
#include <set>

namespace injeqt { namespace v1 {

namespace {

std::string exception_message(const QMetaObject *meta_object, const QMetaObject *dependency_meta_object)
{
	return std::string{meta_object->className()} + "::" + dependency_meta_object->className();
}

std::vector<setter_method> extract_setters(const type &for_type)
{
	auto result = std::vector<setter_method>{};

	auto meta_object = for_type.meta_object();
	auto method_count = meta_object->methodCount();
	for (decltype(method_count) i = 0; i < method_count; i++)
	{
		auto probably_setter = meta_object->method(i);
		auto tag = std::string{probably_setter.tag()};
		if (tag != "injeqt_setter")
			continue;

		result.emplace_back(setter_method{probably_setter});
	}

	return result;
}

}

dependencies dependency_extractor::extract_dependencies(const type &for_type) const
try
{
	auto setters = extract_setters(for_type);
	auto types = std::vector<type>{};
	std::transform(std::begin(setters), std::end(setters), std::back_inserter(types),
		[](const setter_method &setter){ return setter.parameter_type(); }
	);

	auto relations = type_relations_factory{}.create_type_relations(types);
	for (auto &&ambiguous : relations.ambiguous())
	{
		auto types_it = std::find(std::begin(types), std::end(types), ambiguous);
		if (types_it != std::end(types))
			throw dependency_duplicated_exception(exception_message(for_type.meta_object(), types_it->meta_object()));
	}

	auto result = std::vector<dependency>{};
	std::transform(std::begin(setters), std::end(setters), std::back_inserter(result),
		[](const setter_method &setter){ return dependency{setter}; }
	);

	return dependencies{result};
}
catch (setter_too_many_parameters_exception &e)
{
	throw dependency_too_many_parameters_exception();
}
catch (invalid_setter_exception &e)
{
	throw dependency_not_qobject_exception();
}

}}
<commit_msg>use match method for testing for conflicting dependencies<commit_after>/*
 * %injeqt copyright begin%
 * Copyright 2014 Rafał Malinowski (rafal.przemyslaw.malinowski@gmail.com)
 * %injeqt copyright end%
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */

#include "dependency-extractor.h"

#include "dependency.h"
#include "implements-extractor.h"
#include "setter-method.h"
#include "type.h"
#include "type-relations.h"
#include "type-relations-factory.h"

#include <QtCore/QMetaMethod>
#include <QtCore/QMetaType>
#include <algorithm>
#include <set>

namespace injeqt { namespace v1 {

namespace {

std::string exception_message(const QMetaObject *meta_object, const QMetaObject *dependency_meta_object)
{
	return std::string{meta_object->className()} + "::" + dependency_meta_object->className();
}

std::vector<setter_method> extract_setters(const type &for_type)
{
	auto result = std::vector<setter_method>{};

	auto meta_object = for_type.meta_object();
	auto method_count = meta_object->methodCount();
	for (decltype(method_count) i = 0; i < method_count; i++)
	{
		auto probably_setter = meta_object->method(i);
		auto tag = std::string{probably_setter.tag()};
		if (tag != "injeqt_setter")
			continue;

		result.emplace_back(setter_method{probably_setter});
	}

	return result;
}

std::vector<type> extract_parameter_types(const std::vector<setter_method> &setters)
{
	auto result = std::vector<type>{};

	std::transform(std::begin(setters), std::end(setters), std::back_inserter(result),
		[](const setter_method &setter){ return setter.parameter_type(); }
	);

	return result;
}

}

dependencies dependency_extractor::extract_dependencies(const type &for_type) const
try
{
	auto setters = extract_setters(for_type);
	auto parameter_types = extract_parameter_types(setters);
	auto relations = type_relations_factory{}.create_type_relations(parameter_types);

	auto matches = match(types{parameter_types}.content(), relations.ambiguous().content());
	if (!matches.matched.empty())
		throw dependency_duplicated_exception(exception_message(for_type.meta_object(), matches.matched.begin()->first.meta_object()));

	auto result = std::vector<dependency>{};
	std::transform(std::begin(setters), std::end(setters), std::back_inserter(result),
		[](const setter_method &setter){ return dependency{setter}; }
	);

	return dependencies{result};
}
catch (setter_too_many_parameters_exception &e)
{
	throw dependency_too_many_parameters_exception();
}
catch (invalid_setter_exception &e)
{
	throw dependency_not_qobject_exception();
}

}}
<|endoftext|>


<commit_before>/*=========================================================================

  Program:   Monteverdi2
  Language:  C++

  Copyright (c) Centre National d'Etudes Spatiales. All rights reserved.
  See Copyright.txt for details.

  Monteverdi2 is distributed under the CeCILL licence version 2. See
  Licence_CeCILL_V2-en.txt or
  http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt for more details.

  This software is distributed WITHOUT ANY WARRANTY; without even
  the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
  PURPOSE.  See the above copyright notices for more information.

=========================================================================*/

#include "mvdI18nApplication.h"

//
// Qt includes (sorted by alphabetic order)
//// Must be included before system/custom includes.

//
// System includes (sorted by alphabetic order)

//
// OTB includes (sorted by alphabetic order)

//
// Monteverdi includes (sorted by alphabetic order)

//
// Class implementation.
namespace mvd
{
/*
  TRANSLATOR mvd::I18nApplication

  Necessary for lupdate to be aware of C++ namespaces.

  Context comment for translator.
*/

/*******************************************************************************/
I18nApplication
::I18nApplication( int& argc, char** argv ) :
  QApplication( argc, argv ),
  m_IsRunningFromBuildDir( false )
{
  InitializeLocale();
}

/*******************************************************************************/
I18nApplication
::~I18nApplication()
{
}

/*******************************************************************************/
void
I18nApplication
::InitializeLocale()
{
  QTextCodec::setCodecForTr( QTextCodec::codecForName( "utf8" ) );

  //
  // 1. default UI language is english (no translation).
  QLocale sys_lc( QLocale::system() );
  if( sys_lc.language()==QLocale::C ||
      ( sys_lc.language()==QLocale::English &&
	sys_lc.country()==QLocale::UnitedStates ) )
    {
    return;
    }

  //
  // 2. Choose i18n path between build dir and install dir.
  QDir i18n_dir;
  QDir bin_dir( QDir::cleanPath( QCoreApplication::applicationDirPath() ) );
  QDir build_i18n_dir( bin_dir );

  // If build dir is identified...
  if( build_i18n_dir.cd( "../i18n" ) &&
      build_i18n_dir.exists( "../" Monteverdi2_CONFIGURE_FILE ) )
    {
    m_IsRunningFromBuildDir = true;

    // ...use build dir as prioritary load path for translation.
    i18n_dir = build_i18n_dir;

    // TODO: Use log system to trace message.
    qDebug()
      << tr( "Running from build directory '%1'." ).arg( bin_dir.path() );
    }
  // Otherwise...
  else
    {
    m_IsRunningFromBuildDir = false;

    QDir install_i18n_dir( QDir::cleanPath( Monteverdi2_INSTALL_DATA_I18N_DIR ) );
    // ...if install data dir is identified
    if( install_i18n_dir.exists() )
      {
      // ...use install data dir as load path for translation.
      i18n_dir = install_i18n_dir;

      // TODO: Use log system to trace message.
      qDebug()
	<< tr( "Running from install directory '%1'." ).arg( Monteverdi2_INSTALL_BIN_DIR );
      }
    // Otherwise
    else
      {
      QString message(
	tr( "Failed to access translation-files directory '%1'." )
	.arg( install_i18n_dir.path() )
      );

      // TODO: Use log system to trace error while loading locale translation file.

      qDebug() << message;

      // TODO: morph into better HMI design.
      QMessageBox::critical( NULL, tr( "Critical error!" ), message );

      return;
      }
    }

  //
  // 3.1 Stack Qt translator.
  LoadAndInstallTranslator(
    "qt_" + sys_lc.name(),
    QLibraryInfo::location( QLibraryInfo::TranslationsPath  )
  );

  //
  // 3.2 Stack Monteverdi2 translator as prioritary over Qt translator.
  LoadAndInstallTranslator( sys_lc.name(), i18n_dir.path() );

  // TODO: Record locale translation filename(s) used in UI component (e.g.
  // AboutDialog, Settings dialog, Information dialog etc.)
}

/*******************************************************************************/
bool
I18nApplication
::LoadAndInstallTranslator(const QString& filename,
			   const QString& directory,
			   const QString& searchDelimiters,
			   const QString& suffix )
{
  QString filename_ext(
    filename +
    ( suffix.isNull()
	? ".qm"
	: suffix )
  );

  // (a) Do need to new QTranslator() here!
  QTranslator* lc_translator = new QTranslator( this );

  if( !lc_translator->load( filename, directory, searchDelimiters, suffix ) )
    {
    QString message(
      tr( "Failed to load '%1' translation file from '%2'." )
      .arg( filename_ext )
      .arg( directory )
    );

    // TODO: Use log system to trace error while loading locale translation file.

    qWarning() << message;

    // TODO: morph into better HMI design.
    QMessageBox::warning( NULL, tr( "Warning!" ), message );

    return false;
    }

  // (a) ...because QTranslator needs to be alive during the whole
  // lifespan of the application.
  QCoreApplication::installTranslator( lc_translator );

  QString message(
    tr( "Successfully loaded '%1' translation file from '%2'." )
    .arg( filename_ext )
    .arg( directory )
  );

  // TODO: Log locale translation filename used.

  qDebug() << message;

  return true;
}

/*******************************************************************************/
/* SLOTS                                                                       */
/*******************************************************************************/

} // end namespace 'mvd'
<commit_msg>COMP: support windows build dir<commit_after>/*=========================================================================

  Program:   Monteverdi2
  Language:  C++

  Copyright (c) Centre National d'Etudes Spatiales. All rights reserved.
  See Copyright.txt for details.

  Monteverdi2 is distributed under the CeCILL licence version 2. See
  Licence_CeCILL_V2-en.txt or
  http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt for more details.

  This software is distributed WITHOUT ANY WARRANTY; without even
  the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
  PURPOSE.  See the above copyright notices for more information.

=========================================================================*/

#include "mvdI18nApplication.h"

//
// Qt includes (sorted by alphabetic order)
//// Must be included before system/custom includes.

//
// System includes (sorted by alphabetic order)

//
// OTB includes (sorted by alphabetic order)

//
// Monteverdi includes (sorted by alphabetic order)

//
// Class implementation.
namespace mvd
{
/*
  TRANSLATOR mvd::I18nApplication

  Necessary for lupdate to be aware of C++ namespaces.

  Context comment for translator.
*/

/*******************************************************************************/
I18nApplication
::I18nApplication( int& argc, char** argv ) :
  QApplication( argc, argv ),
  m_IsRunningFromBuildDir( false )
{
  InitializeLocale();
}

/*******************************************************************************/
I18nApplication
::~I18nApplication()
{
}

/*******************************************************************************/
void
I18nApplication
::InitializeLocale()
{
  QTextCodec::setCodecForTr( QTextCodec::codecForName( "utf8" ) );

  //
  // 1. default UI language is english (no translation).
  QLocale sys_lc( QLocale::system() );
  if( sys_lc.language()==QLocale::C ||
      ( sys_lc.language()==QLocale::English &&
	sys_lc.country()==QLocale::UnitedStates ) )
    {
    return;
    }

  //
  // 2. Choose i18n path between build dir and install dir.
  QDir i18n_dir;
  QDir bin_dir( QDir::cleanPath( QCoreApplication::applicationDirPath() ) );
  QDir build_i18n_dir( bin_dir );

  qDebug() << "build_i18n_dir.exists( ../i18n )" << build_i18n_dir.exists( "../i18n" );
  qDebug() << "build_i18n_dir.exists( ../../i18n )" << build_i18n_dir.exists( "../../i18n" );
  qDebug() << "build_i18n_dir.exists( ../../i18n )" << build_i18n_dir.exists( "../../" Monteverdi2_CONFIGURE_FILE );

  // If build dir is identified...
  if( build_i18n_dir.exists( "../i18n" )
         && build_i18n_dir.cd( "../i18n" )
         && build_i18n_dir.exists( "../" Monteverdi2_CONFIGURE_FILE )
       || build_i18n_dir.exists( "../../i18n" )
         && build_i18n_dir.cd( "../../i18n" )
         && build_i18n_dir.exists( "../" Monteverdi2_CONFIGURE_FILE ) )
    {
    m_IsRunningFromBuildDir = true;

    // ...use build dir as prioritary load path for translation.
    i18n_dir = build_i18n_dir;

    // TODO: Use log system to trace message.
    qDebug()
      << tr( "Running from build directory '%1'." ).arg( bin_dir.path() );
    }
  // Otherwise...
  else
    {
    m_IsRunningFromBuildDir = false;

    QDir install_i18n_dir( QDir::cleanPath( Monteverdi2_INSTALL_DATA_I18N_DIR ) );
    // ...if install data dir is identified
    if( install_i18n_dir.exists() )
      {
      // ...use install data dir as load path for translation.
      i18n_dir = install_i18n_dir;

      // TODO: Use log system to trace message.
      qDebug()
        << tr( "Running from install directory '%1'." ).arg( Monteverdi2_INSTALL_BIN_DIR );
      }
    // Otherwise
    else
      {
      QString message(
        tr( "Failed to access translation-files directory '%1'." )
        .arg( install_i18n_dir.path() )
      );

      // TODO: Use log system to trace error while loading locale translation file.

      qDebug() << message;

      // TODO: morph into better HMI design.
      QMessageBox::critical( NULL, tr( "Critical error!" ), message );

      return;
      }
    }

  //
  // 3.1 Stack Qt translator.
  LoadAndInstallTranslator(
    "qt_" + sys_lc.name(),
    QLibraryInfo::location( QLibraryInfo::TranslationsPath  )
  );

  //
  // 3.2 Stack Monteverdi2 translator as prioritary over Qt translator.
  LoadAndInstallTranslator( sys_lc.name(), i18n_dir.path() );

  // TODO: Record locale translation filename(s) used in UI component (e.g.
  // AboutDialog, Settings dialog, Information dialog etc.)
}

/*******************************************************************************/
bool
I18nApplication
::LoadAndInstallTranslator(const QString& filename,
			   const QString& directory,
			   const QString& searchDelimiters,
			   const QString& suffix )
{
  QString filename_ext(
    filename +
    ( suffix.isNull()
	? ".qm"
	: suffix )
  );

  // (a) Do need to new QTranslator() here!
  QTranslator* lc_translator = new QTranslator( this );

  if( !lc_translator->load( filename, directory, searchDelimiters, suffix ) )
    {
    QString message(
      tr( "Failed to load '%1' translation file from '%2'." )
      .arg( filename_ext )
      .arg( directory )
    );

    // TODO: Use log system to trace error while loading locale translation file.

    qWarning() << message;

    // TODO: morph into better HMI design.
    QMessageBox::warning( NULL, tr( "Warning!" ), message );

    return false;
    }

  // (a) ...because QTranslator needs to be alive during the whole
  // lifespan of the application.
  QCoreApplication::installTranslator( lc_translator );

  QString message(
    tr( "Successfully loaded '%1' translation file from '%2'." )
    .arg( filename_ext )
    .arg( directory )
  );

  // TODO: Log locale translation filename used.

  qDebug() << message;

  return true;
}

/*******************************************************************************/
/* SLOTS                                                                       */
/*******************************************************************************/

} // end namespace 'mvd'
<|endoftext|>


<commit_before>/*=========================================================================
 *
 *  Copyright Insight Software Consortium
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/

#include "itkOtsuThresholdImageFilter.h"
#include "itkImage.h"
#include "itkImageFileReader.h"
#include "itkImageFileWriter.h"
#include "itkBinaryThresholdImageFilter.h"
#include "itkConnectedComponentImageFilter.h"
#include "itkRelabelComponentImageFilter.h"
#include "itkRescaleIntensityImageFilter.h"

int main( int argc, char * argv[] )
{
  if( argc < 5 )
    {
    std::cerr << "Usage: " << argv[0];
    std::cerr << " inputImageFile outputImageFile ";
    std::cerr << " insideValue    outsideValue   "  << std::endl;
    return EXIT_FAILURE;
    }

  typedef  unsigned char  InputPixelType;
  typedef  unsigned char  OutputPixelType;
  const unsigned int      Dimension = 2;

  typedef itk::Image< InputPixelType,  Dimension >   InputImageType;
  typedef itk::Image< OutputPixelType, Dimension >   OutputImageType;

  typedef itk::OtsuThresholdImageFilter<
               InputImageType, OutputImageType >  OtsuFilterType;

  typedef itk::ImageFileReader< InputImageType >  ReaderType;
  typedef itk::ImageFileWriter< OutputImageType >  WriterType;

  ReaderType::Pointer reader = ReaderType::New();
  OtsuFilterType::Pointer otsuFilter = OtsuFilterType::New();
  reader->SetFileName( argv[1] );

  otsuFilter->SetInput( reader->GetOutput() );

  const OutputPixelType outsideValue = atoi( argv[3] );
  const OutputPixelType insideValue  = atoi( argv[4] );

  otsuFilter->SetOutsideValue( outsideValue );
  otsuFilter->SetInsideValue(  insideValue  );

  try
    {
    otsuFilter->Update();
    }
  catch( itk::ExceptionObject & excp )
    {
    std::cerr << "Exception thrown " << excp << std::endl;
    }

  int threshold = otsuFilter->GetThreshold();
  std::cout << "Threshold = " << threshold << std::endl;

  typedef unsigned short ComponentPixelType;
  typedef itk::Image< ComponentPixelType, Dimension >  ComponentImageType;

  typedef itk::ConnectedComponentImageFilter <InputImageType, ComponentImageType >
    ConnectedComponentImageFilterType;

  ConnectedComponentImageFilterType::Pointer connected = ConnectedComponentImageFilterType::New ();
  connected->SetInput(otsuFilter->GetOutput());
  connected->Update();

  std::cout << "Number of objects: " << connected->GetObjectCount() << std::endl;

  typedef itk::RelabelComponentImageFilter<
               ComponentImageType, ComponentImageType >  RelabelFilterType;
  RelabelFilterType::Pointer relabeler = RelabelFilterType::New();

  relabeler->SetInput( connected->GetOutput() );

  typedef itk::BinaryThresholdImageFilter<
               ComponentImageType, OutputImageType >  ThresholdFilterType;
  ThresholdFilterType::Pointer thresholder = ThresholdFilterType::New();
  thresholder->SetLowerThreshold(1);
  thresholder->SetUpperThreshold(1);
  thresholder->SetOutsideValue(0);
  thresholder->SetInsideValue(255);

  thresholder->SetInput( relabeler->GetOutput() );

  WriterType::Pointer writer = WriterType::New();
  writer->SetFileName( argv[2] );
  writer->SetInput( thresholder->GetOutput() );
  writer->Update();

  std::cout << "Largest object of " << connected->GetObjectCount() << " objects";

  typedef std::vector< itk::SizeValueType > SizesInPixelsType;
  const SizesInPixelsType & sizesInPixels = relabeler->GetSizeOfObjectsInPixels();
  std::cout << "Number of pixels in largest component = " << sizesInPixels[0] << std::endl;
  std::cout << "Number of pixels in second  component = " << sizesInPixels[1] << std::endl;

  return EXIT_SUCCESS;
}
<commit_msg>Integrated end to end, producing north and south curves.<commit_after>/*=========================================================================
 *
 *  Copyright Insight Software Consortium
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *         http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 *=========================================================================*/

#include "itkBinaryThresholdImageFilter.h"
#include "itkConnectedComponentImageFilter.h"
#include "itkImage.h"
#include "itkImageFileReader.h"
#include "itkImageFileWriter.h"
#include "itkImageLinearIteratorWithIndex.h"
#include "itkImageRegionIterator.h"
#include "itkOtsuMultipleThresholdsImageFilter.h"
#include "itkOtsuThresholdImageFilter.h"
#include "itkRelabelComponentImageFilter.h"
#include "itkRescaleIntensityImageFilter.h"

int main( int argc, char * argv[] )
{
  if( argc < 3 )
    {
    std::cerr << "Usage: " << argv[0];
    std::cerr << " inputImageFile outputImageFile ";
    return EXIT_FAILURE;
    }

  typedef  unsigned char  InputPixelType;
  typedef  unsigned char  OutputPixelType;
  const unsigned int      Dimension = 2;

  typedef itk::Image< InputPixelType,  Dimension >   InputImageType;
  typedef itk::Image< OutputPixelType, Dimension >   OutputImageType;

  typedef itk::OtsuThresholdImageFilter<
               InputImageType, OutputImageType >  OtsuFilterType;

  typedef itk::ImageFileReader< InputImageType >  ReaderType;
  typedef itk::ImageFileWriter< OutputImageType >  WriterType;

  ReaderType::Pointer reader = ReaderType::New();
  OtsuFilterType::Pointer otsuFilter = OtsuFilterType::New();
  reader->SetFileName( argv[1] );

  otsuFilter->SetInput( reader->GetOutput() );

  const OutputPixelType outsideValue = 255;
  const OutputPixelType insideValue  = 0;

  otsuFilter->SetOutsideValue( outsideValue );
  otsuFilter->SetInsideValue(  insideValue  );

  try
    {
    otsuFilter->Update();
    }
  catch( itk::ExceptionObject & excp )
    {
    std::cerr << "Exception thrown " << excp << std::endl;
    }

  int threshold = otsuFilter->GetThreshold();
  std::cout << "Threshold = " << threshold << std::endl;

  typedef unsigned short ComponentPixelType;
  typedef itk::Image< ComponentPixelType, Dimension >  ComponentImageType;

  typedef itk::ConnectedComponentImageFilter <InputImageType, ComponentImageType >
    ConnectedComponentImageFilterType;

  ConnectedComponentImageFilterType::Pointer connected = ConnectedComponentImageFilterType::New ();
  connected->SetInput(otsuFilter->GetOutput());
  connected->Update();

  std::cout << "Number of objects: " << connected->GetObjectCount() << std::endl;

  typedef itk::RelabelComponentImageFilter<
               ComponentImageType, ComponentImageType >  RelabelFilterType;
  RelabelFilterType::Pointer relabeler = RelabelFilterType::New();

  relabeler->SetInput( connected->GetOutput() );

  typedef itk::BinaryThresholdImageFilter<
               ComponentImageType, OutputImageType >  ThresholdFilterType;
  ThresholdFilterType::Pointer thresholder = ThresholdFilterType::New();
  thresholder->SetLowerThreshold(1);
  thresholder->SetUpperThreshold(1);
  thresholder->SetOutsideValue(0);
  thresholder->SetInsideValue(255);

  thresholder->SetInput( relabeler->GetOutput() );

  WriterType::Pointer writer = WriterType::New();
  writer->SetFileName( argv[2] );
  writer->SetInput( thresholder->GetOutput() );
  writer->Update();

  std::cout << "Largest object of " << connected->GetObjectCount() << " objects";

  typedef std::vector< itk::SizeValueType > SizesInPixelsType;
  const SizesInPixelsType & sizesInPixels = relabeler->GetSizeOfObjectsInPixels();
  std::cout << "Number of pixels in largest component = " << sizesInPixels[0] << std::endl;
  std::cout << "Number of pixels in second  component = " << sizesInPixels[1] << std::endl;

  //
  // Compute integrated projection and use Otsu to find borders.
  //
  typedef itk::ImageLinearConstIteratorWithIndex< InputImageType > ConstIteratorType;

  InputImageType::ConstPointer inputImage = thresholder->GetOutput();

  const unsigned int CountDimension = 1;
  typedef unsigned short CountPixelType;
  typedef itk::Image< CountPixelType, CountDimension > CountImageType;
  CountImageType::IndexType start;
  start[0] = 0;
  CountImageType::SizeType  size;
  size[0]  = inputImage->GetRequestedRegion().GetSize()[0];

  CountImageType::RegionType region;
  region.SetSize( size );
  region.SetIndex( start );

  CountImageType::Pointer countImage = CountImageType::New();
  countImage->SetRegions( region );
  countImage->Allocate();

  typedef itk::ImageRegionIterator< CountImageType > CountIteratorType;
  CountIteratorType outputIt( countImage, countImage->GetLargestPossibleRegion() );
  outputIt.GoToBegin();

  ConstIteratorType inputIt( inputImage, inputImage->GetRequestedRegion() );

  inputIt.SetDirection(1); // walk faster along the vertical direction.

  std::vector<unsigned short> counter;

  unsigned short line = 0;
  for ( inputIt.GoToBegin(); ! inputIt.IsAtEnd(); inputIt.NextLine() )
    {
    unsigned short count = 0;
    inputIt.GoToBeginOfLine();
    while ( ! inputIt.IsAtEndOfLine() )
      {
      InputPixelType value = inputIt.Get();
      if (value == 255 ) {
        ++count;
        }
      ++inputIt;
      }
    outputIt.Set(count);
    ++outputIt;
    counter.push_back(count);
    std::cout << line << " " << count << std::endl;
    ++line;
    }

  CountImageType::IndexType leftIndex;
  CountImageType::IndexType rightIndex;

  typedef itk::OtsuMultipleThresholdsImageFilter<
    CountImageType, CountImageType >  OtsuMultipleFilterType;
  OtsuMultipleFilterType::Pointer otsuMultipleFilter = OtsuMultipleFilterType::New();
  otsuMultipleFilter->SetInput( countImage );
  otsuMultipleFilter->SetNumberOfThresholds(2);
  otsuMultipleFilter->Update();
  CountImageType::Pointer otsuOutput = otsuMultipleFilter->GetOutput();

  CountIteratorType bandsIt( otsuOutput, otsuOutput->GetLargestPossibleRegion() );
  bandsIt.GoToBegin();
  CountPixelType currentValue = bandsIt.Get();
  while (!bandsIt.IsAtEnd()) {
    if (bandsIt.Get() != currentValue) {
      leftIndex = bandsIt.GetIndex();
      currentValue = bandsIt.Get();
      break;
      }
    ++bandsIt;
    }
  while (!bandsIt.IsAtEnd()) {
    if (bandsIt.Get() != currentValue) {
      rightIndex = bandsIt.GetIndex();
      break;
      }
    ++bandsIt;
    }

  // Add a safety band
  leftIndex[0] += 100;
  rightIndex[0] -= 100;

  std::cout << "leftIndex " << leftIndex << std::endl;
  std::cout << "rightIndex " << rightIndex << std::endl;

  std::vector< unsigned short > north;
  std::vector< unsigned short > south;

  unsigned short xpos = 0;
  ConstIteratorType rangeIt( inputImage, inputImage->GetRequestedRegion() );
  rangeIt.SetDirection(1); // walk faster along the vertical direction.

  for ( rangeIt.GoToBegin(); ! rangeIt.IsAtEnd(); rangeIt.NextLine(), ++xpos )
    {
    unsigned short bottom = 0;
    unsigned short top = 0;
    rangeIt.GoToBeginOfLine();
    while ( ! rangeIt.IsAtEndOfLine() )
      {
      InputPixelType value = rangeIt.Get();
      if (value == 255 ) {
        if ( bottom == 0 ) {
          bottom = rangeIt.GetIndex()[1];
          }
        top = rangeIt.GetIndex()[1];
        }
      ++rangeIt;
      }

    if (xpos >= leftIndex[0] && xpos <= rightIndex[0]) {
      north.push_back(top);
      south.push_back(bottom);
      }
    }

  std::string northFilename(argv[1]);
  northFilename.erase(northFilename.end()-4, northFilename.end());
  northFilename += "_north.csv";

  std::string southFilename(argv[1]);
  southFilename.erase(southFilename.end()-4, southFilename.end());
  southFilename += "_south.csv";

  std::cout << northFilename << std::endl;
  std::cout << southFilename << std::endl;

  std::ofstream northFile(northFilename.c_str());
  std::vector<unsigned short>::const_iterator curveIt = north.begin();
  xpos = leftIndex[0];
  while (curveIt != north.end()) {
    northFile << xpos << ", " << *curveIt << std::endl;
    ++xpos;
    ++curveIt;
  }
  northFile.close();

  std::ofstream southFile(southFilename.c_str());
  curveIt = south.begin();
  xpos = leftIndex[0];
  while (curveIt != south.end()) {
    southFile << xpos << ", " << *curveIt << std::endl;
    ++xpos;
    ++curveIt;
  }
  southFile.close();

  return EXIT_SUCCESS;
}
<|endoftext|>