-
Notifications
You must be signed in to change notification settings - Fork 2
/
BeauchampFig4.m
122 lines (98 loc) · 3.22 KB
/
BeauchampFig4.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
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
% BeauchampFig4.m
%
% Finds best cortical mapping (a,k,squish) and electrode array location
% (ang,xc,yc) for an array on our V1 map to match the projections of
% phosphenes from Beauchamp (2020).
% Note: electrode spacing dx is fixed at a 2mm for both x and y.
% load in phosphene parameters
T = readtable('datasets/Beauchamp_2020_data.xlsx','Sheet','ElectrodeLocations');
eid =strcmp(T.experiment,'Figure 4');
% figure 4-grid are locations based on the electrode array Figure 4 are
% locations based on patient report
T = T(eid,:)
% Phosphene locations in visual space
id = strcmp(T(:,:).patient,'YBN');
vx = T(id,:).x';
vy = T(id,:).y';
% model parameters
% kmapping parameters
p.k = 15;
p.a = 0.5; %.1474;
p.squish = 1; %.63;
p.k= 16.1703
p.a= 0.2630
p.squish= 0.6479
% electrode location and spacing on cortex
p.ang = -30*pi/180;
p.xc = -44;
p.yc = -8;
p.dx = 2; %mm
% Axis range for plotting:
% zoomed in:
p.eccList = [4,8,16];
p.angList = 0:pi/8:pi/2;
% zoomed out:
% p.eccList = [0.01,0.25,.5,1,2,4,8,16];
% p.angList = -pi/2:pi/8:pi/2;
% Draw the phosphene locations in visual space
figure(1)
clf
hold on
% Draw the grid
ecc = repmat(p.eccList,101,1);
ang = repmat(linspace(min(p.angList),max(p.angList),101)',1,length(p.eccList));
gridx = ecc.*cos(ang);
gridy = ecc.*sin(ang);
plot(gridx,gridy,'k-','Color',[.5,.5,.5]);
ang = repmat(p.angList,101,1);
ecc = repmat(exp(linspace(-20,log(max(p.eccList)),101))',1,length(p.angList));
gridx = ecc.*cos(ang);
gridy = ecc.*sin(ang);
plot(gridx,gridy,'k-','Color',[.5,.5,.5]);
% Plot the phosphenes in visual space (blue)
drawLocations(vx,vy,[0,0,1]);
axis equal
title('Visual Space');
xlabel('x (deg)');
ylabel('y (deg)');
% Fit the array
p = fit('p2p_c.fitElectrodeGrid',p,{'ang','a','k','squish','xc','yc'},vx,vy);
p.shift = p.k*log(p.a); % shouldn't really be a parameter
% Get the predictions
[err,predcx,predcy,cx,cy] = p2p_c.fitElectrodeGrid(p,vx,vy);
% Draw the projected phosphenes (blue) and the best fitting array (green)
figure(2)
clf
hold on
% Plot the grid
ecc = repmat(p.eccList,101,1);
ang = repmat(linspace(min(p.angList),max(p.angList),101)',1,length(p.eccList));
x = ecc.*cos(ang);
y = ecc.*sin(ang);
[gridx,gridy] = p2p_c.v2c_real(p,x,y);
plot(gridx,gridy,'k-','Color',[.5,.5,.5]);
ang = repmat(p.angList,101,1);
ecc = repmat(exp(linspace(log(min(p.eccList)),log(max(p.eccList)),101))',1,length(p.angList));
x = ecc.*cos(ang);
y = ecc.*sin(ang);
[gridx,gridy] = p2p_c.v2c_real(p,x,y);
plot(gridx,gridy,'k-','Color',[.5,.5,.5]);
title('Cortical Space');
xlabel('x (mm)');
ylabel('y (mm)');
axis equal
% Projected phosphenes
drawLocations(cx,cy,[0,0,1]);
% Best fitting array
drawLocations(predcx,predcy,[0,1,0]);
% project best fitting electrode array back to visual space
[predvx,predvy] = p2p_c.c2v_real(p,predcx,predcy);
% Plot the projected best fitting array in visual space (green)
figure(1)
drawLocations(predvx,predvy,[0,1,0]);
function drawLocations(x,y,col)
for i=1:length(x)
plot(x(i),y(i),'ko','MarkerSize',14,'Color',col,'MarkerFaceColor','none');
text(x(i),y(i),num2str(i),'HorizontalAlignment','center','VerticalAlignment','middle','Color',col);
end
end