// SPDX-FileCopyrightText: Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
// SPDX-License-Identifier: BSD-3-Clause
#include "vtkBiDimensionalRepresentation2D.h"

#include <cstdlib>
#include <iostream>

#include "vtkImageData.h"
#include "vtkProperty2D.h"
#include "vtkTextProperty.h"

#include "WidgetTestingMacros.h"

int vtkBiDimensionalRepresentation2DTest1(int, char*[])
{
  vtkSmartPointer<vtkBiDimensionalRepresentation2D> node1 =
    vtkSmartPointer<vtkBiDimensionalRepresentation2D>::New();

  EXERCISE_BASIC_REPRESENTATION_METHODS(vtkBiDimensionalRepresentation2D, node1);

  double pos[3] = { 55.0, 66.6, 77.9 };
  double p[3];

  // world position
  node1->SetPoint1WorldPosition(pos);
  node1->GetPoint1WorldPosition(p);
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != pos[2])
  {
    std::cerr << "Failure in Get/Set Point1WorldPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  pos[2] = 99.9;
  node1->SetPoint2WorldPosition(pos);
  node1->GetPoint2WorldPosition(p);
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != pos[2])
  {
    std::cerr << "Failure in Get/Set Point2WorldPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  pos[2] = -88.9;
  node1->SetPoint3WorldPosition(pos);
  node1->GetPoint3WorldPosition(p);
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != pos[2])
  {
    std::cerr << "Failure in Get/Set Point3WorldPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  pos[0] = -44.9;
  node1->SetPoint4WorldPosition(pos);
  node1->GetPoint4WorldPosition(p);
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != pos[2])
  {
    std::cerr << "Failure in Get/Set Point4WorldPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  // display position
  node1->SetPoint1DisplayPosition(pos);
  node1->GetPoint1DisplayPosition(p);
  // only compare first two points in vector, last is always zero
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != 0.0)
  {
    std::cerr << "Failure in Get/Set Point1DisplayPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  pos[1] = 99.9;
  node1->SetPoint2DisplayPosition(pos);
  node1->GetPoint2DisplayPosition(p);
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != 0.0)
  {
    std::cerr << "Failure in Get/Set Point2DisplayPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  pos[1] = -88.9;
  node1->SetPoint3DisplayPosition(pos);
  node1->GetPoint3DisplayPosition(p);
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != 0.0)
  {
    std::cerr << "Failure in Get/Set Point3DisplayPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  pos[0] = -44.9;
  node1->SetPoint4DisplayPosition(pos);
  node1->GetPoint4DisplayPosition(p);
  if (p[0] != pos[0] || p[1] != pos[1] || p[2] != 0.0)
  {
    std::cerr << "Failure in Get/Set Point4DisplayPosition, expected " << pos[0] << ", " << pos[1]
              << ", " << pos[2] << ", instead got " << p[0] << ", " << p[1] << ", " << p[2]
              << std::endl;
    return EXIT_FAILURE;
  }

  TEST_SET_GET_BOOLEAN(node1, Line1Visibility);
  TEST_SET_GET_BOOLEAN(node1, Line2Visibility);

  vtkSmartPointer<vtkHandleRepresentation> hRep;
  hRep = node1->GetPoint1Representation();
  hRep = node1->GetPoint2Representation();
  hRep = node1->GetPoint4Representation();
  hRep = node1->GetPoint4Representation();

  vtkSmartPointer<vtkProperty2D> prop2d;
  prop2d = node1->GetLineProperty();
  prop2d = node1->GetSelectedLineProperty();

  vtkSmartPointer<vtkTextProperty> textProp;
  textProp = node1->GetTextProperty();

  TEST_SET_GET_INT_RANGE(node1, Tolerance, 2, 99);

  std::cout << "Length 1 = " << node1->GetLength1() << std::endl;
  std::cout << "Length 2 = " << node1->GetLength2() << std::endl;

  TEST_SET_GET_STRING(node1, LabelFormat);

  double e[2] = { 10.0, 8.0 };
  node1->Point2WidgetInteraction(e);
  e[1] = 7.0;
  // node1->Point3WidgetInteraction(e);

  TEST_SET_GET_BOOLEAN(node1, ShowLabelAboveWidget);

  TEST_SET_GET_INT_RANGE(node1, ID, 1, 10000);

  std::cout << "LabelText = "
            << (node1->GetLabelText() == nullptr ? "nullptr" : node1->GetLabelText()) << std::endl;
  double* labelPos = node1->GetLabelPosition();
  if (labelPos)
  {
    std::cout << "LabelPosition: " << labelPos[0] << ", " << labelPos[1] << ", " << labelPos[2]
              << std::endl;
  }
  else
  {
    std::cout << "LabelPosition is null" << std::endl;
  }
  double labelPosition[3];
  node1->GetLabelPosition(labelPosition);
  std::cout << "LabelPosition [3]: " << labelPosition[0] << ", " << labelPosition[1] << ", "
            << labelPosition[2] << std::endl;
  //  node1->GetWorldLabelPosition(labelPosition);
  //  std::cout << "WorldLabelPosition: " << labelPosition[0] << ", " << labelPosition[1] << ", " <<
  //  labelPosition[2] << std::endl;
  return EXIT_SUCCESS;
}
