File indexing completed on 2025-01-19 03:59:55
0001 import operator 0002 import math 0003 0004 0005 def vop(op, a, b): 0006 return list(map(op, a, b)) 0007 0008 0009 class NVector(): 0010 def __init__(self, *components): 0011 self.components = list(components) 0012 0013 def __str__(self): 0014 return str(self.components) 0015 0016 def __repr__(self): 0017 return "<NVector %s>" % self 0018 0019 def __len__(self): 0020 return len(self.components) 0021 0022 def to_list(self): 0023 return list(self.components) 0024 0025 def __add__(self, other): 0026 return type(self)(*vop(operator.add, self.components, other.components)) 0027 0028 def __sub__(self, other): 0029 return type(self)(*vop(operator.sub, self.components, other.components)) 0030 0031 def __mul__(self, scalar): 0032 if isinstance(scalar, NVector): 0033 return type(self)(*vop(operator.mul, self.components, scalar.components)) 0034 return type(self)(*(c * scalar for c in self.components)) 0035 0036 def __truediv__(self, scalar): 0037 return type(self)(*(c / scalar for c in self.components)) 0038 0039 def __iadd__(self, other): 0040 self.components = vop(operator.add, self.components, other.components) 0041 return self 0042 0043 def __isub__(self, other): 0044 self.components = vop(operator.sub, self.components, other.components) 0045 return self 0046 0047 def __imul__(self, scalar): 0048 if isinstance(scalar, NVector): 0049 self.components = vop(operator.mul, self.components, scalar.components) 0050 else: 0051 self.components = [c * scalar for c in self.components] 0052 return self 0053 0054 def __itruediv__(self, scalar): 0055 self.components = [c / scalar for c in self.components] 0056 return self 0057 0058 def __neg__(self): 0059 return type(self)(*(-c for c in self.components)) 0060 0061 def __getitem__(self, key): 0062 if isinstance(key, slice): 0063 return NVector(*self.components[key]) 0064 return self.components[key] 0065 0066 def __setitem__(self, key, value): 0067 self.components[key] = value 0068 0069 def __eq__(self, other): 0070 return self.components == other.components 0071 0072 def __abs__(self): 0073 return type(self)(*(abs(c) for c in self.components)) 0074 0075 @property 0076 def length(self): 0077 return math.sqrt(sum(map(lambda x: x**2, self.components))) 0078 0079 def dot(self, other): 0080 return sum(map(operator.mul, self.components, other.components)) 0081 0082 def clone(self): 0083 return NVector(*self.components) 0084 0085 def lerp(self, other, t): 0086 return self * (1-t) + other * t 0087 0088 @property 0089 def x(self): 0090 return self.components[0] 0091 0092 @x.setter 0093 def x(self, v): 0094 self.components[0] = v 0095 0096 @property 0097 def y(self): 0098 return self.components[1] 0099 0100 @y.setter 0101 def y(self, v): 0102 self.components[1] = v 0103 0104 @property 0105 def z(self): 0106 return self.components[2] 0107 0108 @z.setter 0109 def z(self, v): 0110 self.components[2] = v 0111 0112 def element_scaled(self, other): 0113 return type(self)(*vop(operator.mul, self.components, other.components)) 0114 0115 def cross(self, other): 0116 """ 0117 @pre len(self) == len(other) == 3 0118 """ 0119 a = self 0120 b = other 0121 return type(self)( 0122 a[1] * b[2] - a[2] * b[1], 0123 a[2] * b[0] - a[0] * b[2], 0124 a[0] * b[1] - a[1] * b[0], 0125 ) 0126 0127 @property 0128 def polar_angle(self): 0129 """ 0130 @pre len(self) == 2 0131 """ 0132 return math.atan2(self.y, self.x) 0133 0134 0135 def Point(x, y): 0136 return NVector(x, y) 0137 0138 0139 def Size(x, y): 0140 return NVector(x, y) 0141 0142 0143 def Point3D(x, y, z): 0144 return NVector(x, y, z) 0145 0146 0147 def PolarVector(length, theta): 0148 return NVector(length * math.cos(theta), length * math.sin(theta))