Camera.java 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. /**
  2. * This class represents a digital camera with an autofocus feature.
  3. *
  4. * @author Markus Iser, Martin Thoma
  5. *
  6. */
  7. public class Camera {
  8. /** This epsilon is used for internal float comparisons. */
  9. private static final double EPSILON = 1E-6;
  10. /** The objective that is currently used by the camera. */
  11. private final Objective objective;
  12. /**
  13. * The constructor for objective.
  14. *
  15. * @param objective
  16. * an objective
  17. */
  18. public Camera(final Objective objective) {
  19. this.objective = objective;
  20. }
  21. /**
  22. * Check two doubles for equality.
  23. *
  24. * @param fp1 first floating point number
  25. * @param fp2 second floating point number
  26. * @return {@code true} if both floats are equal, otherwise {@code false}
  27. */
  28. private boolean fpEquals(final double fp1, final double fp2) {
  29. return Math.abs(fp1 - fp2) < EPSILON;
  30. }
  31. /**
  32. * Determine if the contrast on the left is higher than on the current
  33. * position.
  34. *
  35. * @param objective the objective you are manipulating
  36. * @return {@code true} the contrast on the left of the current position is
  37. * higher, otherwise {@code false}
  38. */
  39. private boolean isLeftContrastHigher(Objective objective) {
  40. double contrast = objective.getContrast();
  41. objective.stepLeft();
  42. double contrastNew = objective.getContrast();
  43. objective.stepRight();
  44. // check if the contrast - according to our EPSILON - is the same
  45. if (fpEquals(contrast, contrastNew)) {
  46. return false;
  47. }
  48. return contrastNew > contrast;
  49. }
  50. /**
  51. * Adjust objective to get the optimum focus. The optimum focus is
  52. * determined by the highest contrast.
  53. */
  54. public void autofocus() {
  55. boolean stepLeft;
  56. double contrast = objective.getContrast();
  57. // determine direction
  58. stepLeft = isLeftContrastHigher(objective);
  59. // loop until optimum passed
  60. while (objective.getContrast() > contrast
  61. && !fpEquals(contrast, objective.getContrast())) {
  62. contrast = objective.getContrast();
  63. if (stepLeft) {
  64. objective.stepLeft();
  65. } else {
  66. objective.stepRight();
  67. }
  68. }
  69. // optional correction-move back
  70. if (!fpEquals(contrast, objective.getContrast())) {
  71. if (stepLeft) {
  72. objective.stepRight();
  73. } else {
  74. objective.stepLeft();
  75. }
  76. }
  77. }
  78. }