-
Notifications
You must be signed in to change notification settings - Fork 2
/
Surface.m
64 lines (56 loc) · 2.23 KB
/
Surface.m
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
classdef Surface < handle
% SURFACE base class for optic elements
%
% Member functions:
%
% b = a.copy - copy surface a to surface b
%
% rotate( rot_axis, rot_angle ) - rotate the surface by rot_angle
% (radians) about the 1x3 rotation axis, inherited by derived classes.
%
% Copyright: Yury Petrov, 2016
%
properties % public access
r = [ 0 0 0 ]; % location vector
R = []; % radius of the tangent sphere
k = []; % conic constant
glass = { 'air' 'air' }; % material in front and behind the surface
end
properties ( SetAccess = private )
rotax = [ 1 0 0 ]; % rotation axis for rotation transformation
rotang = 0; % rotation angle about the rotax, radians
n = [ 1 0 0 ]; % orientation (normal) vector, can be set by a rotate function only
end
methods
function b = copy( self )
b = feval( class( self ) );
p = properties( self );
for i = 1:length( p )
b.( p{ i } ) = self.( p{ i } );
end
end
function rotate( self, rot_axis, rot_angle )
if abs( rot_angle ) > pi
error( 'Rotation angle should be [ -pi pi ]!' );
end
% rotate the normal about the rot_axis by rot_angle (radians)
self.rotax = rot_axis;
self.rotang = self.rotang + rot_angle;
self.n = rodrigues_rot( self.n, rot_axis, rot_angle );
if abs( self.rotang ) > pi/2
self.rotang = self.rotang - sign( self.rotang ) * pi;
self.R = -self.R; % surface upside-down
self.glass = fliplr( self.glass ); % change material ordering
self.n = -self.n; % make the surface normal point along the rays
end
end
function rotate_euler( self, rot_angles )
% convert it to the corresponding axis-angle rotation
[ axis, angle ] = euler_to_axisangle( rot_angles );
self.rotate( axis, angle );
end
function reverse_glasses( self )
self.glass = { self.glass{ 2 }, self.glass{ 1 } };
end
end
end