PCL
GridInterpolation.h
Go to the documentation of this file.
1 // ____ ______ __
2 // / __ \ / ____// /
3 // / /_/ // / / /
4 // / ____// /___ / /___ PixInsight Class Library
5 // /_/ \____//_____/ PCL 2.7.0
6 // ----------------------------------------------------------------------------
7 // pcl/GridInterpolation.h - Released 2024-06-18T15:48:54Z
8 // ----------------------------------------------------------------------------
9 // This file is part of the PixInsight Class Library (PCL).
10 // PCL is a multiplatform C++ framework for development of PixInsight modules.
11 //
12 // Copyright (c) 2003-2024 Pleiades Astrophoto S.L. All Rights Reserved.
13 //
14 // Redistribution and use in both source and binary forms, with or without
15 // modification, is permitted provided that the following conditions are met:
16 //
17 // 1. All redistributions of source code must retain the above copyright
18 // notice, this list of conditions and the following disclaimer.
19 //
20 // 2. All redistributions in binary form must reproduce the above copyright
21 // notice, this list of conditions and the following disclaimer in the
22 // documentation and/or other materials provided with the distribution.
23 //
24 // 3. Neither the names "PixInsight" and "Pleiades Astrophoto", nor the names
25 // of their contributors, may be used to endorse or promote products derived
26 // from this software without specific prior written permission. For written
27 // permission, please contact info@pixinsight.com.
28 //
29 // 4. All products derived from this software, in any form whatsoever, must
30 // reproduce the following acknowledgment in the end-user documentation
31 // and/or other materials provided with the product:
32 //
33 // "This product is based on software from the PixInsight project, developed
34 // by Pleiades Astrophoto and its contributors (https://pixinsight.com/)."
35 //
36 // Alternatively, if that is where third-party acknowledgments normally
37 // appear, this acknowledgment must be reproduced in the product itself.
38 //
39 // THIS SOFTWARE IS PROVIDED BY PLEIADES ASTROPHOTO AND ITS CONTRIBUTORS
40 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
41 // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
42 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL PLEIADES ASTROPHOTO OR ITS
43 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
44 // EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, BUSINESS
45 // INTERRUPTION; PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; AND LOSS OF USE,
46 // DATA OR PROFITS) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
47 // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
48 // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
49 // POSSIBILITY OF SUCH DAMAGE.
50 // ----------------------------------------------------------------------------
51 
52 #ifndef __PCL_GridInterpolation_h
53 #define __PCL_GridInterpolation_h
54 
56 
57 #include <pcl/Defs.h>
58 #include <pcl/Diagnostics.h>
59 
60 #include <pcl/AbstractImage.h>
62 #include <pcl/Matrix.h>
63 #include <pcl/ParallelProcess.h>
64 #include <pcl/Rectangle.h>
65 #include <pcl/ReferenceArray.h>
66 #include <pcl/Thread.h>
67 
68 #ifndef __PCL_BUILDING_PIXINSIGHT_APPLICATION
69 # include <pcl/Console.h>
70 # include <pcl/StandardStatus.h>
71 #endif
72 
73 namespace pcl
74 {
75 
76 // ----------------------------------------------------------------------------
77 
91 class PCL_CLASS GridInterpolation : public ParallelProcess
92 {
93 public:
94 
99  GridInterpolation() = default;
100 
105 
110 
114  GridInterpolation& operator =( const GridInterpolation& ) = default;
115 
119  GridInterpolation& operator =( GridInterpolation&& ) = default;
120 
158  template <class R, class SI>
159  void Initialize( const R& rect, int delta, const SI& S, bool verbose = true )
160  {
161  PCL_PRECONDITION( rect.IsRect() )
162  PCL_PRECONDITION( delta > 0 )
163 
164  m_rect = rect.Ordered();
165  double width = m_rect.Width();
166  double height = m_rect.Height();
167  if ( !m_rect.IsRect() || 1 + width == 1 || 1 + height == 1 )
168  throw Error( "GridInterpolation::Initialize(): Empty interpolation space." );
169 
170  m_delta = Abs( delta );
171  if ( 1 + m_delta == 1 )
172  throw Error( "GridInterpolation::Initialize(): Zero or insignificant grid distance." );
173 
174  int rows = 1 + int( Ceil( height/m_delta ) );
175  int cols = 1 + int( Ceil( width/m_delta ) );
176  m_G = DMatrix( rows, cols );
177 
178  StatusMonitor monitor;
179 #ifndef __PCL_BUILDING_PIXINSIGHT_APPLICATION
180  StandardStatus status;
181  if ( verbose )
182  {
183  monitor.SetCallback( &status );
184  monitor.Initialize( "Building surface interpolation grid", rows );
185  }
186 #endif
187 
189  1/*overheadLimit*/,
190  m_parallel ? m_maxProcessors : 1 );
191  AbstractImage::ThreadData data( monitor, rows );
193  for ( int i = 0, n = 0; i < int( L.Length() ); n += int( L[i++] ) )
194  threads.Add( new GridInitializationThread<SI>( data, *this, S, n, n + int( L[i] ) ) );
195  AbstractImage::RunThreads( threads, data );
196  threads.Destroy();
197 
198  m_I.Initialize( m_G.Begin(), cols, rows );
199  }
200 
231  template <class R>
232  void Initialize( const R& rect, double delta, const DMatrix& G )
233  {
234  PCL_PRECONDITION( rect.IsRect() )
235  PCL_PRECONDITION( delta > 0 )
236 
237  m_rect = DRect( rect.Ordered() );
238  double width = m_rect.Width();
239  double height = m_rect.Height();
240  if ( !m_rect.IsRect() || 1 + width == 1 || 1 + height == 1 )
241  throw Error( "GridInterpolation::Initialize(): Empty interpolation space." );
242 
243  m_delta = Abs( delta );
244  if ( 1 + m_delta == 1 )
245  throw Error( "GridInterpolation::Initialize(): Zero or insignificant grid distance." );
246 
247  int rows = 1 + int( Ceil( height/m_delta ) );
248  int cols = 1 + int( Ceil( width/m_delta ) );
249  if ( G.Rows() != rows || G.Cols() != cols )
250  throw Error( "GridInterpolation::Initialize(): Invalid matrix dimensions." );
251 
252  m_G = G;
253  m_I.Initialize( m_G.Begin(), cols, rows );
254  }
255 
260  bool IsValid() const
261  {
262  return !m_G.IsEmpty();
263  }
264 
269  void Clear()
270  {
271  m_I.Clear();
272  m_G.Clear();
273  }
274 
279  const DRect& ReferenceRect() const
280  {
281  return m_rect;
282  }
283 
288  double Delta() const
289  {
290  return m_delta;
291  }
292 
301  {
302  return m_G;
303  }
304 
308  template <typename T>
309  double operator ()( T x, T y ) const
310  {
311  double fx = (double( x ) - m_rect.x0)/m_delta;
312  double fy = (double( y ) - m_rect.y0)/m_delta;
313  return m_I( fx, fy );
314  }
315 
319  template <typename T>
320  double operator ()( const GenericPoint<T>& p ) const
321  {
322  return operator ()( p.x, p.y );
323  }
324 
325 private:
326 
332  using grid_interpolation = BicubicBSplineInterpolation<double>;
333 
334  DRect m_rect;
335  double m_delta;
336  DMatrix m_G;
337  grid_interpolation m_I;
338 
339  template <class SI>
340  class GridInitializationThread : public Thread
341  {
342  public:
343 
344  GridInitializationThread( const AbstractImage::ThreadData& data,
345  GridInterpolation& grid, const SI& surface, int startRow, int endRow )
346  : m_data( data )
347  , m_grid( grid )
348  , m_surface( surface )
349  , m_startRow( startRow )
350  , m_endRow( endRow )
351  {
352  }
353 
354  PCL_HOT_FUNCTION void Run() override
355  {
357 
358  double y = m_grid.m_rect.y0 + m_startRow*m_grid.m_delta;
359  for ( int i = m_startRow; i < m_endRow; ++i, y += m_grid.m_delta )
360  {
361  double x = m_grid.m_rect.x0;
362  for ( int j = 0; j < m_grid.m_G.Cols(); ++j, x += m_grid.m_delta )
363  m_grid.m_G[i][j] = m_surface( x, y );
364 
366  }
367  }
368 
369  private:
370 
371  const AbstractImage::ThreadData& m_data;
372  GridInterpolation& m_grid;
373  const SI& m_surface;
374  int m_startRow, m_endRow;
375  };
376 };
377 
378 // ----------------------------------------------------------------------------
379 
393 class PCL_CLASS PointGridInterpolation : public ParallelProcess
394 {
395 public:
396 
402 
407 
412 
416  PointGridInterpolation& operator =( const PointGridInterpolation& ) = default;
417 
421  PointGridInterpolation& operator =( PointGridInterpolation&& ) = default;
422 
460  template <class R, class PSI>
461  void Initialize( const R& rect, double delta, const PSI& PS, bool verbose = true )
462  {
463  PCL_PRECONDITION( rect.IsRect() )
464  PCL_PRECONDITION( delta > 0 )
465 
466  m_rect = DRect( rect.Ordered() );
467  double width = m_rect.Width();
468  double height = m_rect.Height();
469  if ( !m_rect.IsRect() || 1 + width == 1 || 1 + height == 1 )
470  throw Error( "PointGridInterpolation::Initialize(): Empty interpolation space." );
471 
472  m_delta = Abs( delta );
473  if ( 1 + m_delta == 1 )
474  throw Error( "PointGridInterpolation::Initialize(): Zero or insignificant grid distance." );
475 
476  int rows = 1 + int( Ceil( height/m_delta ) );
477  int cols = 1 + int( Ceil( width/m_delta ) );
478  m_Gx = DMatrix( rows, cols );
479  m_Gy = DMatrix( rows, cols );
480 
481  StatusMonitor monitor;
482 #ifndef __PCL_BUILDING_PIXINSIGHT_APPLICATION
483  StandardStatus status;
484  if ( verbose )
485  {
486  monitor.SetCallback( &status );
487  monitor.Initialize( "Building surface interpolation grid", rows );
488  }
489 #endif
490 
492  1/*overheadLimit*/,
493  m_parallel ? m_maxProcessors : 1 );
494  AbstractImage::ThreadData data( monitor, rows );
496  for ( int i = 0, n = 0; i < int( L.Length() ); n += int( L[i++] ) )
497  threads.Add( new GridInitializationThread<PSI>( data, *this, PS, n, n + int( L[i] ) ) );
498  AbstractImage::RunThreads( threads, data );
499  threads.Destroy();
500 
501  m_Ix.Initialize( m_Gx.Begin(), cols, rows );
502  m_Iy.Initialize( m_Gy.Begin(), cols, rows );
503  }
504 
548  template <class R, class SI>
549  void Initialize( const R& rect, double delta, const SI& Sx, const SI& Sy, bool verbose = true )
550  {
551  PCL_PRECONDITION( rect.IsRect() )
552  PCL_PRECONDITION( delta > 0 )
553 
554  m_rect = DRect( rect.Ordered() );
555  double width = m_rect.Width();
556  double height = m_rect.Height();
557  if ( !m_rect.IsRect() || 1 + width == 1 || 1 + height == 1 )
558  throw Error( "PointGridInterpolation::Initialize(): Empty interpolation space." );
559 
560  m_delta = Abs( delta );
561  if ( 1 + m_delta == 1 )
562  throw Error( "PointGridInterpolation::Initialize(): Zero or insignificant grid distance." );
563 
564  int rows = 1 + int( Ceil( height/m_delta ) );
565  int cols = 1 + int( Ceil( width/m_delta ) );
566  m_Gx = DMatrix( rows, cols );
567  m_Gy = DMatrix( rows, cols );
568 
569  StatusMonitor monitor;
570 #ifndef __PCL_BUILDING_PIXINSIGHT_APPLICATION
571  StandardStatus status;
572  if ( verbose )
573  {
574  monitor.SetCallback( &status );
575  monitor.Initialize( "Building surface interpolation grid", rows );
576  }
577 #endif
578 
580  1/*overheadLimit*/,
581  m_parallel ? m_maxProcessors : 1 );
582  AbstractImage::ThreadData data( monitor, rows );
584  for ( int i = 0, n = 0; i < int( L.Length() ); n += int( L[i++] ) )
585  threads.Add( new GridInitializationXYThread<SI>( data, *this, Sx, Sy, n, n + int( L[i] ) ) );
586  AbstractImage::RunThreads( threads, data );
587  threads.Destroy();
588 
589  m_Ix.Initialize( m_Gx.Begin(), cols, rows );
590  m_Iy.Initialize( m_Gy.Begin(), cols, rows );
591  }
592 
625  template <class R>
626  void Initialize( const R& rect, int delta, const DMatrix& Gx, const DMatrix& Gy )
627  {
628  PCL_PRECONDITION( rect.IsRect() )
629  PCL_PRECONDITION( delta > 0 )
630 
631  m_rect = DRect( rect.Ordered() );
632  double width = m_rect.Width();
633  double height = m_rect.Height();
634  if ( !m_rect.IsRect() || 1 + width == 1 || 1 + height == 1 )
635  throw Error( "PointGridInterpolation::Initialize(): Empty interpolation region." );
636 
637  m_delta = Abs( delta );
638  if ( 1 + m_delta == 1 )
639  throw Error( "PointGridInterpolation::Initialize(): Zero or insignificant grid distance." );
640 
641  int rows = 1 + int( Ceil( height/m_delta ) );
642  int cols = 1 + int( Ceil( width/m_delta ) );
643  if ( Gx.Rows() != rows || Gx.Cols() != cols || Gy.Rows() != rows || Gy.Cols() != cols )
644  throw Error( "PointGridInterpolation::Initialize(): Invalid matrix dimensions." );
645 
646  m_Gx = Gx;
647  m_Gy = Gy;
648  m_Ix.Initialize( m_Gx.Begin(), cols, rows );
649  m_Iy.Initialize( m_Gy.Begin(), cols, rows );
650  }
651 
655  template <class PSI>
656  void ApplyLocalModel( const PSI& PS,
657  const String& message = "Applying local interpolation model",
658  bool verbose = true )
659  {
660  PCL_PRECONDITION( IsValid() )
661  if ( !IsValid() )
662  throw Error( "PointGridInterpolation::ApplyLocalModel(): Uninitialized interpolation." );
663 
664  StatusMonitor monitor;
665 #ifndef __PCL_BUILDING_PIXINSIGHT_APPLICATION
666  StandardStatus status;
667  if ( verbose )
668  {
669  monitor.SetCallback( &status );
670  monitor.Initialize( message, m_Gx.Rows() );
671  }
672 #endif
673 
674  Array<size_type> L = Thread::OptimalThreadLoads( m_Gx.Rows(),
675  1/*overheadLimit*/,
676  m_parallel ? m_maxProcessors : 1 );
677  AbstractImage::ThreadData data( monitor, m_Gx.Rows() );
678  ReferenceArray<LocalModelThread<PSI> > threads;
679  for ( int i = 0, n = 0; i < int( L.Length() ); n += int( L[i++] ) )
680  threads.Add( new LocalModelThread<PSI>( data, *this, PS, n, n + int( L[i] ) ) );
681  AbstractImage::RunThreads( threads, data );
682  threads.Destroy();
683  }
684 
688  template <class SI>
689  void ApplyLocalModel( const SI& Sx, const SI& Sy,
690  const String& message = "Applying local interpolation model",
691  bool verbose = true )
692  {
693  PCL_PRECONDITION( IsValid() )
694  if ( !IsValid() )
695  throw Error( "PointGridInterpolation::ApplyLocalModel(): Uninitialized interpolation." );
696 
697  StatusMonitor monitor;
698 #ifndef __PCL_BUILDING_PIXINSIGHT_APPLICATION
699  StandardStatus status;
700  if ( verbose )
701  {
702  monitor.SetCallback( &status );
703  monitor.Initialize( message, m_Gx.Rows() );
704  }
705 #endif
706 
707  Array<size_type> L = Thread::OptimalThreadLoads( m_Gx.Rows(),
708  1/*overheadLimit*/,
709  m_parallel ? m_maxProcessors : 1 );
710  AbstractImage::ThreadData data( monitor, m_Gx.Rows() );
711  ReferenceArray<LocalModelThread2<SI> > threads;
712  for ( int i = 0, n = 0; i < int( L.Length() ); n += int( L[i++] ) )
713  threads.Add( new LocalModelThread2<SI>( data, *this, Sx, Sy, n, n + int( L[i] ) ) );
714  AbstractImage::RunThreads( threads, data );
715  threads.Destroy();
716  }
717 
722  bool IsValid() const
723  {
724  return !m_Gx.IsEmpty() && !m_Gy.IsEmpty();
725  }
726 
731  void Clear()
732  {
733  m_Ix.Clear();
734  m_Iy.Clear();
735  m_Gx.Clear();
736  m_Gy.Clear();
737  }
738 
745  const DRect& ReferenceRect() const
746  {
747  return m_rect;
748  }
749 
754  double Delta() const
755  {
756  return m_delta;
757  }
758 
767  {
768  return m_Gx;
769  }
770 
779  {
780  return m_Gy;
781  }
782 
786  template <typename T>
787  DPoint operator ()( T x, T y ) const
788  {
789  PCL_PRECONDITION( IsValid() )
790  double fx = (double( x ) - m_rect.x0)/m_delta;
791  double fy = (double( y ) - m_rect.y0)/m_delta;
792  return DPoint( m_Ix( fx, fy ), m_Iy( fx, fy ) );
793  }
794 
798  template <typename T>
799  DPoint operator ()( const GenericPoint<T>& p ) const
800  {
801  return operator ()( p.x, p.y );
802  }
803 
804 private:
805 
811  using grid_interpolation = BicubicBSplineInterpolation<double>;
812 
813  DRect m_rect;
814  double m_delta;
815  DMatrix m_Gx, m_Gy;
816  grid_interpolation m_Ix, m_Iy;
817 
818  template <class PSI>
819  class GridInitializationThread : public Thread
820  {
821  public:
822 
823  GridInitializationThread( const AbstractImage::ThreadData& data,
824  PointGridInterpolation& grid, const PSI& surface, int startRow, int endRow )
825  : m_data( data )
826  , m_grid( grid )
827  , m_surface( surface )
828  , m_startRow( startRow )
829  , m_endRow( endRow )
830  {
831  }
832 
833  PCL_HOT_FUNCTION void Run() override
834  {
836 
837  double y = m_grid.m_rect.y0 + m_startRow*m_grid.m_delta;
838  for ( int i = m_startRow; i < m_endRow; ++i, y += m_grid.m_delta )
839  {
840  double x = m_grid.m_rect.x0;
841  for ( int j = 0; j < m_grid.m_Gx.Cols(); ++j, x += m_grid.m_delta )
842  {
843  DPoint p = m_surface( x, y );
844  m_grid.m_Gx[i][j] = p.x;
845  m_grid.m_Gy[i][j] = p.y;
846  }
847 
849  }
850  }
851 
852  private:
853 
854  const AbstractImage::ThreadData& m_data;
855  PointGridInterpolation& m_grid;
856  const PSI& m_surface;
857  int m_startRow, m_endRow;
858  };
859 
860  template <class SI>
861  class GridInitializationXYThread : public Thread
862  {
863  public:
864 
865  GridInitializationXYThread( const AbstractImage::ThreadData& data,
866  PointGridInterpolation& grid,
867  const SI& surfaceX, const SI& surfaceY, int startRow, int endRow )
868  : m_data( data )
869  , m_grid( grid )
870  , m_surfaceX( surfaceX )
871  , m_surfaceY( surfaceY )
872  , m_startRow( startRow )
873  , m_endRow( endRow )
874  {
875  }
876 
877  PCL_HOT_FUNCTION void Run() override
878  {
880 
881  double y = m_grid.m_rect.y0 + m_startRow*m_grid.m_delta;
882  for ( int i = m_startRow; i < m_endRow; ++i, y += m_grid.m_delta )
883  {
884  double x = m_grid.m_rect.x0;
885  for ( int j = 0; j < m_grid.m_Gx.Cols(); ++j, x += m_grid.m_delta )
886  {
887  m_grid.m_Gx[i][j] = m_surfaceX( x, y );
888  m_grid.m_Gy[i][j] = m_surfaceY( x, y );
889  }
890 
892  }
893  }
894 
895  private:
896 
897  const AbstractImage::ThreadData& m_data;
898  PointGridInterpolation& m_grid;
899  const SI& m_surfaceX;
900  const SI& m_surfaceY;
901  int m_startRow, m_endRow;
902  };
903 
904  template <class PSI>
905  class LocalModelThread : public Thread
906  {
907  public:
908 
909  LocalModelThread( const AbstractImage::ThreadData& data,
910  PointGridInterpolation& grid, const PSI& model, int startRow, int endRow )
911  : m_data( data )
912  , m_grid( grid )
913  , m_model( model )
914  , m_startRow( startRow )
915  , m_endRow( endRow )
916  {
917  }
918 
919  PCL_HOT_FUNCTION void Run() override
920  {
922 
923  double y = m_grid.m_rect.y0 + m_startRow*m_grid.m_delta;
924  for ( int i = m_startRow; i < m_endRow; ++i, y += m_grid.m_delta )
925  {
926  double x = m_grid.m_rect.x0;
927  for ( int j = 0; j < m_grid.m_Gx.Cols(); ++j, x += m_grid.m_delta )
928  {
929  DPoint d = m_model( x, y );
930  m_grid.m_Gx[i][j] += d.x;
931  m_grid.m_Gy[i][j] += d.y;
932  }
933 
935  }
936  }
937 
938  private:
939 
940  const AbstractImage::ThreadData& m_data;
941  PointGridInterpolation& m_grid;
942  const PSI& m_model;
943  int m_startRow, m_endRow;
944  };
945 
946  template <class SI>
947  class LocalModelThread2 : public Thread
948  {
949  public:
950 
951  LocalModelThread2( const AbstractImage::ThreadData& data,
952  PointGridInterpolation& grid, const SI& modelX, const SI& modelY, int startRow, int endRow )
953  : m_data( data )
954  , m_grid( grid )
955  , m_modelX( modelX )
956  , m_modelY( modelY )
957  , m_startRow( startRow )
958  , m_endRow( endRow )
959  {
960  }
961 
962  PCL_HOT_FUNCTION void Run() override
963  {
965 
966  double y = m_grid.m_rect.y0 + m_startRow*m_grid.m_delta;
967  for ( int i = m_startRow; i < m_endRow; ++i, y += m_grid.m_delta )
968  {
969  double x = m_grid.m_rect.x0;
970  for ( int j = 0; j < m_grid.m_Gx.Cols(); ++j, x += m_grid.m_delta )
971  {
972  m_grid.m_Gx[i][j] += m_modelX( x, y );
973  m_grid.m_Gy[i][j] += m_modelY( x, y );
974  }
975 
977  }
978  }
979 
980  private:
981 
982  const AbstractImage::ThreadData& m_data;
983  PointGridInterpolation& m_grid;
984  const SI& m_modelX, m_modelY;
985  int m_startRow, m_endRow;
986  };
987 
988  friend class SplineWorldTransformation;
989 };
990 
991 // ----------------------------------------------------------------------------
992 
993 } // pcl
994 
995 #endif // __PCL_GridInterpolation_h
996 
997 // ----------------------------------------------------------------------------
998 // EOF pcl/GridInterpolation.h - Released 2024-06-18T15:48:54Z
static void RunThreads(ReferenceArray< thread > &threads, ThreadData &data, bool useAffinity=true)
Generic dynamic array.
Definition: Array.h:100
64-bit floating-point point in the R^2 space.
A simple exception with an associated error message.
Definition: Exception.h:239
Generic dynamic matrix of arbitrary dimensions.
Definition: Matrix.h:123
int Cols() const noexcept
Definition: Matrix.h:969
int Rows() const noexcept
Definition: Matrix.h:960
A generic point in the two-dimensional space.
Definition: Point.h:100
component x
Abscissa (horizontal, or X-axis coordinate).
Definition: Point.h:111
component y
Ordinate (vertical, or Y-axis coordinate).
Definition: Point.h:112
A generic rectangle in the two-dimensional space.
Definition: Rectangle.h:314
bool IsRect() const noexcept
Definition: Rectangle.h:762
component y0
Vertical coordinate of the upper left corner.
Definition: Rectangle.h:333
component x0
Horizontal coordinate of the upper left corner.
Definition: Rectangle.h:332
component Width() const noexcept
Definition: Rectangle.h:635
component Height() const noexcept
Definition: Rectangle.h:644
Discretized scalar surface interpolation/approximation in two dimensions.
GridInterpolation(GridInterpolation &&)=default
void Initialize(const R &rect, double delta, const DMatrix &G)
GridInterpolation(const GridInterpolation &)=default
const DMatrix & InterpolationMatrix() const
const DRect & ReferenceRect() const
void Initialize(const R &rect, int delta, const SI &S, bool verbose=true)
A process using multiple concurrent execution threads.
Discretized vector surface interpolation/approximation in two dimensions.
void Initialize(const R &rect, double delta, const SI &Sx, const SI &Sy, bool verbose=true)
const DMatrix & XInterpolationMatrix() const
void Initialize(const R &rect, double delta, const PSI &PS, bool verbose=true)
PointGridInterpolation(const PointGridInterpolation &)=default
const DMatrix & YInterpolationMatrix() const
void Initialize(const R &rect, int delta, const DMatrix &Gx, const DMatrix &Gy)
PointGridInterpolation(PointGridInterpolation &&)=default
const DRect & ReferenceRect() const
Dynamic array of pointers to objects providing direct iteration and element access by reference.
void Destroy(iterator i, size_type n=1)
void Add(const ReferenceArray &x)
A status monitoring callback that sends progress information to the process console.
An asynchronous status monitoring system.
void SetCallback(StatusCallback *callback)
void Initialize(const String &info, size_type count=0)
Unicode (UTF-16) string.
Definition: String.h:8113
Client-side interface to a PixInsight thread.
Definition: Thread.h:130
static Array< size_type > OptimalThreadLoads(size_type count, size_type overheadLimit=1u, int maxThreads=PCL_MAX_PROCESSORS)
T Abs(const Complex< T > &c) noexcept
Definition: Complex.h:429
constexpr T Ceil(T x) noexcept
Definition: Math.h:562
#define INIT_THREAD_MONITOR()
Declares and initializes local variables used for synchronization of thread status monitoring.
#define UPDATE_THREAD_MONITOR(N)
Synchronized status monitoring of a set of image processing threads.
PCL root namespace.
Definition: AbstractImage.h:77
Thread synchronization data for status monitoring of parallel image processing tasks.