File: Script.c

package info (click to toggle)
openclonk 7.0-4
  • links: PTS, VCS
  • area: main
  • in suites: stretch
  • size: 145,828 kB
  • ctags: 33,094
  • sloc: cpp: 163,891; ansic: 82,846; xml: 29,876; python: 1,203; php: 767; makefile: 138; sh: 77
file content (275 lines) | stat: -rwxr-xr-x 5,711 bytes parent folder | download | duplicates (6)
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
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
/**
 Library for vector operations.
 
 @author Marky
 @credits Randrian, since many functions have their origin in the rope physics library.
 */


/**
 Addition of two vectors of the same dimension.
 Note: Cannot be named 'Add' because the scenario
 save mechanism will throw a lot of warnings.
 @par a The first vector.
 @par b The second vector.
 @return array The vector (a_i + b_i), i=1,...,n.
*/
public func Sum(array a, array b)
{
	AssertVectorOperation(a, b);

	var vector = [];
	
	for (var i = 0; i < GetLength(a); i++)
	{
		vector[i] = a[i] + b[i];
	}

	return vector;
}


/**
 Subtraction of two vectors of the same dimension.
 @par a The first vector.
 @par b The second vector.
 @return array The vector (a_i - b_i), i=1,...,n.
*/
public func Subtract(array a, array b)
{
	AssertVectorOperation(a, b);

	var vector = [];

	for (var i = 0; i < GetLength(a); i++)
	{
		vector[i] = a[i] - b[i];
	}

	return vector;
}


/**
 Multiplication of a vector and a number.
 @par a The vector
 @par b The number
 @return array The vector (b * a_i), i=1,...,n.
*/
public func Multiply(array a, int b)
{
	AssertNotNil(a, "vector 'a'");

	var vector = [];

	for (var i = 0; i < GetLength(a); i++)
	{
		vector[i] = b * a[i];
	}

	return vector;
}


/**
 Division of a vector and a number.
 @par a The vector
 @par b The number
 @return array The vector (a_i / b), i=1,...,n.
*/
public func Divide(array a, int b)
{
	AssertNotNil(a, "vector 'a'");

	var vector = [];

	for (var i = 0; i < GetLength(a); i++)
	{
		vector[i] = a[i] / b;
	}

	return vector;
}


/**
 Dot product of two vectors of the same dimension.
 @par a The first vector
 @par b The second vector
 @return int Sum of a_i * b_i, for i = 1,...,n
*/
public func DotProduct(array a, array b)
{
	AssertVectorOperation(a, b);

	var sum = 0;

	for (var i = 0; i < GetLength(a); i++)
	{
		sum += a[i] * b[i];
	}

	return sum;
}

/**
 Product of the elements of vectors of the same dimension.
 @par a The first vector
 @par b The second vector
 @return array the vector c_i of c_i = a_i * b_i, for i = 1,...,n
*/
public func Product(array a, array b)
{
	AssertVectorOperation(a, b);

	var vector = [];

	for (var i = 0; i < GetLength(a); i++)
	{
		vector[i] = a[i] * b[i];
	}

	return vector;
}

/**
 Euclidean length of a vector.
 @par a The vector.
 @return int Square root of the sum of a_i * a_i, for i=1,...,n.
*/
public func Length(array a)
{
	return Sqrt(DotProduct(a, a));
}


/**
 The dimension of a vector.
 @par a The vector
 @return int The number of elements of the vector.
 */
public func Dimension(array a)
{
	AssertNotNil(a, "vector 'a'");

	return GetLength(a);
}


/**
 Angle between two vectors.
 @par a A two-dimensional vector.
 @par b A two-dimensional vector.
 @return int The angle between a and b. If you rotate a by this angle,
             then it will point in the same direction as b.
*/
public func AngleBetween(array a, array b, int precision)
{
	AssertVectorOperation(a, b);
	if (!precision) precision = 1;

	var rot_a = GetRotation(a, precision);
	var rot_b = GetRotation(b, precision);
	return rot_b - rot_a;
}


/**
 Angle of a vector.
 @par a A two-dimensional vector.
 @par precision [opt] Multiplied with the angle, for higher precision. A precision of 10 will produce values from 0 to 3600.
 @return int The angle of a, relative to the coordinate system.
*/
public func GetRotation(array a, int precision)
{
	AssertDimension(a, 2);
	if (!precision) precision = 1;

	return Angle(0, 0, a[0], a[1], precision);
}


/**
 Normalizes a vector with precision.
 @par a The vector.
 @par precision Factor for the resultion length.
 @return array The normalized vector with length = 1 * precision
*/
public func Normalize(array a, int precision)
{
	if (!precision) precision = 1;
	return Divide(Multiply(a, precision), Length(a));
}


/**
 Rotates a vector by an angle.
 @par a The vector.
 @par angle The angle that the vector is rotated by, clockwise.
 @return array The rotated vector.
 */
public func Rotate(array a, int angle, int precision)
{
	AssertDimension(a, 2);
	if (!precision) precision = 1;
	var length_precision = 1000;

	var cos = Cos(angle, length_precision, precision);
	var sin = Sin(angle, length_precision, precision);

	var rotated_x = cos * a[0] - sin * a[1];
	var rotated_y = sin * a[0] + cos * a[1];

	return [rotated_x / length_precision, rotated_y / length_precision];
}


/**
 Assert that a vector operation can be done with these two vectors.
 The vectors have to be of the same dimension and their elements
 must have the same names.
 @par a The first vector, must not be nil.
 @par b The second vector, must not be nil.
 */
public func AssertVectorOperation(array a, array b)
{
	AssertNotNil(a, "vector 'a'");
	AssertNotNil(b, "vector 'b'");

	var length_a = GetLength(a);
	var length_b = GetLength(b);
	if (length_a != length_b)
	{
		FatalError(Format("This method only works with vectors of the same length. Vector 'a' has %d elements, vector 'b' has %d elements", length_a, length_b));
	}
}


/**
 Asserts that a vector has a specific dimesion.
 @par a The vector.
 @par dimension The dimension.
 */
public func AssertDimension(array a, int dimension)
{
	var dim = Dimension(a); 
	if (dim != dimension)
	{
		FatalError(Format("The function expects a vector of length %d, got length %d", dimension, dim));
	}
}

/**
 Asserts that a parameter is not nil.
 @par parameter The parameter that is checked.
 @par message [optional] a descriptive message for the parameter that is printed in the fatal error.
 */
public func AssertNotNil(parameter, string message)
{
	if (parameter == nil)
	{
		if (!message) message = "parameter";
		
		FatalError(Format("Expected %s that is not nil", message));
	}
}