Newer
Older
####################################################################################################
#
# Patro - A Python library to make patterns for fashion design
# Copyright (C) 2019 Fabrice Salvaire
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU 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 General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
####################################################################################################
For resources on path see :ref:`this section <path-geometry-ressources-page>`.
####################################################################################################
__all__ = [
'LinearSegment',
'QuadraticBezierSegment',
'CubicBezierSegment',
'Path2D',
]
####################################################################################################
from Patro.Common.Math.Functions import sign
from .Primitive import Primitive1P, Primitive2DMixin
from .Bezier import QuadraticBezier2D, CubicBezier2D
from .Segment import Segment2D
from .Vector import Vector2D
####################################################################################################
_module_logger = logging.getLogger(__name__)
####################################################################################################
class PathPart:
##############################################
def __init__(self, path, index):
self._index = index
##############################################
def _init_absolute(self, absolute):
self._absolute = bool(absolute)
##############################################
Fabrice Salvaire
committed
def clone(self, path):
raise NotImplementedError
##############################################
return '{0}(@{1._index})'.format(self.__class__.__name__, self)
##############################################
@property
def path(self):
return self._path
@property
def index(self):
return self._index
@index.setter
def index(self, value):
self._index = int(value)
##############################################
@property
def prev_part(self):
return self._path[self._index -1]
@property
def next_part(self):
return self._path[self._index +1]
##############################################
@property
def start_point(self):
Fabrice Salvaire
committed
# Fixme: cache ???
prev_part = self.prev_part
if prev_part is not None:
return prev_part.stop_point
else:
return self._path.p0
##############################################
@property
def stop_point(self):
raise NotImplementedError
##############################################
def to_absolute_point(self, point):
# Fixme: cache ???
if self._absolute:
return point
else:
return point + self.start_point
##############################################
@property
def geometry(self):
raise NotImplementedError
##############################################
@property
def bounding_box(self):
return self.geometry.bounding_box
####################################################################################################
class OnePointMixin:
##############################################
@property
def point(self):
return self._point
@point.setter
def point(self, value):
self._point = Vector2D(value) # self._path.__vector_cls__
##############################################
@property
def stop_point(self):
return self.to_absolute_point(self._point)
##############################################
def apply_transformation(self, transformation):
# Fixme: right for relative ???
self._point = transformation * self._point
####################################################################################################
class TwoPointMixin:
##############################################
@property
def point1(self):
return self.to_absolute_point(self._point1)
@point1.setter
def point1(self, value):
self._point1 = Vector2D(value) # self._path.__vector_cls__
##############################################
@property
def point2(self):
return self.to_absolute_point(self._point2)
@point2.setter
def point2(self, value):
self._point2 = Vector2D(value)
##############################################
def apply_transformation(self, transformation):
# Fixme: right for relative ???
self._point1 = transformation * self._point1
self._point2 = transformation * self._point2
####################################################################################################
class ThreePointMixin(TwoPointMixin):
Loading full blame...