Hide keyboard shortcuts

Hot-keys on this page

r m x p   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

# Copyright (C) 2015 Chintalagiri Shashank 

# 

# This file is part of Tendril. 

# 

# This program is free software: you can redistribute it and/or modify 

# it under the terms of the GNU Affero General Public License as published by 

# the Free Software Foundation, either version 3 of the License, or 

# (at your option) any later version. 

# 

# This program 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 Affero General Public License for more details. 

# 

# You should have received a copy of the GNU Affero General Public License 

# along with this program.  If not, see <http://www.gnu.org/licenses/>. 

""" 

This file is part of tendril 

See the COPYING, README, and INSTALL files for more information 

""" 

 

import math 

 

from decimal import Decimal 

from .lengths import Length 

 

 

class CartesianPoint(object): 

    unit = 'mm' 

 

    def __init__(self, x, y): 

        self.x = self._norm_repr(x) 

        self.y = self._norm_repr(y) 

 

    @staticmethod 

    def _norm_repr(v): 

        return Decimal(v) 

 

    def __eq__(self, other): 

        if self.x == other.x and self.y == other.y: 

            return True 

        else: 

            return False 

 

 

class CartesianLineSegment(object): 

    def __init__(self, p1, p2): 

        self.p1 = p1 

        self.p2 = p2 

        if p1 == p2: 

            raise Exception("Line can't have zero length") 

        if p1.unit != p2.unit: 

            raise ValueError 

 

    def x(self, t): 

        return self.p1.x + t * (self.p2.x - self.p1.x) 

 

    def y(self, t): 

        return self.p1.y + t * (self.p2.y - self.p1.y) 

 

    def t_x(self, x): 

        if self.p1.x != self.p2.x: 

            return (Decimal(x) - self.p1.x) / (self.p2.x - self.p1.x) 

        else: 

            raise ZeroDivisionError 

 

    def t_y(self, y): 

        if self.p1.y != self.p2.y: 

            return (Decimal(y) - self.p1.y) / (self.p2.y - self.p1.y) 

        else: 

            raise ZeroDivisionError 

 

    def length(self): 

        return Length(str( 

            math.sqrt((self.p2.x - self.p1.x)**2 + (self.p2.y - self.p1.y)**2) 

        ) + self.p1.unit) 

 

    def __contains__(self, p): 

        try: 

            t = self.t_x(p.x) 

            if 0 <= t <= 1: 

                try: 

                    if t == self.t_y(p.y): 

                        return True 

                    else: 

                        return False 

                except ZeroDivisionError: 

                    if p.y == self.p1.y: 

                        return True 

            else: 

                return False 

        except ZeroDivisionError: 

            t = self.t_y(p.y) 

            if 0 <= t <= 1 and p.x == self.p1.x: 

                return True 

            else: 

                return False