-
Notifications
You must be signed in to change notification settings - Fork 3
Expand file tree
/
Copy pathadjacencyMatrix.m
More file actions
executable file
·343 lines (287 loc) · 14.8 KB
/
adjacencyMatrix.m
File metadata and controls
executable file
·343 lines (287 loc) · 14.8 KB
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
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
function adjacencyMatrix(directory, fileNames, boundaryType, frameidind,verbose)
% directory = '/eno/cllee3/DATA/240208/run2/' % location of image files
% %topDirectory = './testdata/square/'
% %topDirectory = '/Users/carmenlee/Desktop/20150731reprocesseduniaxial/'
% % %topDirectory = './DATA/test/Step09/'
% fileNames = '50Hz_5spfT_*.jpg'; %image format and regex
% frameidind = 15;
if not(isfolder(append(directory,'adjacency'))) %make a new folder with warped images
mkdir(append(directory,'adjacency'));
end
%
%files = dir([topDirectory,imageNames])
% boundaryType = "annulus"; %if airtable use "airtable" if annulus use "annulus"
% radiusRange = [40, 57];
%radiusRange = [45, 78]; %airtable
directoryini = directory
if boundaryType == "annulus"
directory = [directory, 'warpedimg/'];
end
files = dir([directory,fileNames(1:end-4),'_solved_update.mat']) %which files are we processing ?
nFrames = length(files) %how many files are we processing ?
nFrames = 92
%camImageFileName = '/eno/cllee3/DATA/230420/150Hz_2fps_run1/warpedimg/150Hz_*warped.tif'
%camImageFileName = [directory, '100Hz_1fps_Img0021warped.tif']
%camImageFileName = '/eno/cllee3/DATA/230428/run1/warpedimg/150Hz_*warped.tif'
%PARAMETERS NEEDED TO RUN THIS SCRIPT ARE SET HERE
go = true;
fmin = 0.000001; %minimum force (in Newton) to consider a contact a valid contact
fmax = 1000; %maximum force (in Newton) to consider a contact a valid contact
emax = 2800; %maximum fit error/residual to consider a contact a valid contact
fs=16; %plot font size
verbose = true; %make lots of plots as we go
% jut in case your data coordinate system is offset from the image
% coordinate system (i.e. you only processed a small part of a larger
% image)
% xoffset = 1000;
% yoffset = 700;
% xsize = 2470-xoffset;
% ysize = 2260-yoffset;
%%
%Global Metrics will be stored in these structures
%allContacts = struct('fAbs',0,'fNorm',0,'fTan',0); %data structure to store information about contacts
%aID = 1; %Global contact counter over all contacts in all cycles.
if go==true
for cycle = 90:nFrames %loop over these cycles
%cycle = cycle+820
clearvars particle;
clearvars contact;
%input filnames
peOutfilename = files(cycle).name %input filename
if boundaryType =="airtable"
camImageFileName = [peOutfilename(1:end-18),'.jpg']; %adjusted force image filename
elseif boundaryType == "annulus"
camImageFileName = [directoryini, 'warpedimg/',peOutfilename(1:end-18),'.tif']; %adjusted force image filename
end
%camImageFileName = [directory,'100Hz_1fps_Img0021warped.tif']; %adjusted force image filename
%output filenames
%workspacefilename = [peOutfilename(1:end-9),'-postProcessingWorkspace.mat'];
%workspacefilename = [peOutfilename(1:end-10),'-postProcessingWorkspace.mat'];
%synthImgFilename = [peOutfilename(1:end-10),'update-Synth.jpg']; %output filename
adjMatAbsFilename = [directoryini, 'adjacency/',peOutfilename(1:end-11),'-joAdjacencyAbs.dlm']; %output filename
adjMatNorFilename = [directoryini, 'adjacency/',peOutfilename(1:end-11),'-joAdjacency_N.dlm'];
adjMatTanFilename = [directoryini, 'adjacency/',peOutfilename(1:end-11),'-joAdjacency_T.dlm'] ;
%particlelocFilename = [peOutfilename(1:end-10),'-particle.dlm'];
% NO PARAMETERS SHOULD BE SET BY HAND BELOW THIS LINE
%check if the data we want to read exists
%if it does, load it, else abort
if ~(exist([directoryini, 'warpedimg/',peOutfilename], 'file') == 2) %if the file we try to open does not exist
disp(['File not Found:', peOutfilename]); %complain about it
return %and end the execution of this script
else
pres = load([directoryini, 'warpedimg/', peOutfilename]); %read peDiscSolve ouput
particle = pres.pres;
NN = length(particle);
IDN = max([particle.id]);
end
% Gernate Combined Syntehtic Force Image
%img = imread(camImageFileName); %camera force image
%img = imcrop(img,[xoffset, yoffset, xsize, ysize]); %particle image
%DATA EVALUATION AND ANALYSIS STARTS HERE
%particle(1:size(data,1)) = struct('id',0,'x',0,'y',0,'z',0,'fx',0,'fy',0); %data structure to store particle information
contact = struct('id1',0,'id2',0,'x',0,'y',0,'fAbs',0,'fNorm',0,'fTan',0,'alpha',0,'beta',0,'contactX',0,'contactY',0,'error',0); %data structure to store information about contacts
cID = 1; %contact counter
%A = zeros(NN); %empty binary adjacency matrix
W = NaN(IDN); %empty force weighted adjacency matrix
N = NaN(IDN); %empty normal force weighted adjacency matrix
T = NaN(IDN); %empty tangential force weighted adjacency matrix
%P = NaN(NN);
for n = 1:NN %for each particle
err = particle(n).fitError; %get fit error
z = particle(n).z; %get coordination number
r = particle(n).r; %get particle radius in pixel
rm = particle(n).rm; %get particle radius in meters
if ~isempty(particle(n).neighbours) % particle is in contact
contacts = particle(n).neighbours; %get IDs of all contacting particles
betas = particle(n).betas+pi; %get the beta angle (position of contact point) associated with each contact
forces = particle(n).forces; %get the force associated with each contact
alphas = particle(n).alphas; %get the alpha angle (direction of force) associated with each contact
for m=1:length(forces) %for each contact
%if(forces(m) > fmin && err < emax && forces(m) < fmax) %is this a valid contact ?
if (forces(m) < fmax && forces(m)> 0)% && err <emax)
%put information about the first particle involved in this
%contact in the corresponding particle structure vector
%ideally the accumulated fx and fy should be zero, that is
%the particle is in force balance
%particle(n).fx = particle(n).fx + forces(m) * cos(betas(m)-pi); %x component of total force vector %CHECK AGAIN IF THIS IS GEOMETRICALLY CORRECT
%particle(n).fy = particle(n).fy + forces(m) * sin(betas(m)-pi); %y component of total force vector %CHECK AGAIN IF THIS IS GEOMETRICALLY CORRECT
%particle(n).z = particle(n).z+1; %increment the real contact number for the current particle
%put all the information about this contact
%into the contact struct vector
% contact(cID).id1 = particle(n).id; %first particle involved in this contact
targetid = contacts(m);
ids = [particle.id];
tind1m = ids == targetid;
tind1 = find(tind1m);
contact(cID).id2 = targetid; %second particle involved in this contact
contact(cID).x = particle(n).x;
contact(cID).y = particle(n).y;
contact(cID).fAbs = forces(m); %absolute force
contact(cID).fNorm = forces(m)*cos(alphas(m)); %normal force (see Eq. 4.16)
contact(cID).fTan = forces(m)*sin(alphas(m)); %tangential force
contact(cID).alpha = alphas(m); %the alpha angle (direction of force) associated with this contact
contact(cID).beta = betas(m); %the beta angle (position of contact point) associated with this contact
contact(cID).contactX = r * cos(betas(m)-pi); %x component of vector to contact point
contact(cID).contactY = r * sin(betas(m)-pi); %y component of vector to contact point
contact(cID).error = err; %fit error for this particle (the first particle in the contact)
%
cID = cID + 1; %increment contact counter
%
% allContacts(aID).fAbs = forces(m); %absolute force
% allContacts(aID).fNorm = forces(m)*cos(alphas(m)); %normal force (see Eq. 4.16)
% allContacts(aID).fTan = forces(m)*sin(alphas(m)); %tangential force
%
% aID = aID+1;
%build some adjacency matrices
%if (contacts(m)>0) %correct for negative contact IDs in peDiscsolve, i.e.non-wall contacts only
%A(n,contacts(m)) = 1; %mark contact in the binary adjacency matrix
W(particle(n).id,particle(tind1).id) = real(forces(m)); %write the corrsponding force as a weight into an adjacency matrix
N(particle(n).id,particle(tind1).id) = real(forces(m))*cos(alphas(m)); %write the corrsponding normal force as a weight into an adjacency matrix
T(particle(n).id,particle(tind1).id) = real(forces(m))*sin(alphas(m)); %write the corrsponding tangential force as a weight into an adjacency matrix
%P(n, tind1) = [x, y, rm]
%end
end
end
end
end
%%
% length(nonzeros(W))
% edges = 10.^(-5:0.1:2);
% [N,edges] = histcounts(W,edges,'Normalization','countdensity');
% figure;
% g = histogram('BinEdges',edges,'BinCounts',N);
% set(gca, "Xscale", "log")
% figure;
% plot(nonzeros(W), '.')
% drawnow;
%make sure our adjacency matrix is nice
%discard singular contacts
% B = double((W.*W') > 0);
% W = (W.*B);
%
% B = double((N.*N') > 0);
% N = (N.*B);
%
% B = double((T.*T') > 0);
% T = (T.*B);
%average reciprocal contacts so the matrix is fully symmetric
% W = (W+W')/2;
% N = (N+N')/2;
% T = (T+T')/2;
%DATA OUTPUT STARTS HERE
%write out the weighte adjacency matrix for the current frame
dlmwrite(adjMatAbsFilename,W);
dlmwrite(adjMatNorFilename,N);
dlmwrite(adjMatTanFilename,T);
%write out the synthetic force image for the current frame
%imwrite(bigSynthImg,synthImgFilename);
%Plot what we have learned so far
%set up a new figure environment and scale it appropriately
%close all;
%pFig = figure ;
%set(pFig,'Position',[0 0 2000 1200]);
%set(pFig,'paperorientation','landscape');
%this suplot shows the original image, overlayed with the
%detected contacts
%if verbose
%figure(1)
%read and display the original image used as input to peDisc
%img = imcrop(imread(camImageFileName),[xoffset, yoffset, xsize, ysize]); %force image
img = imread(camImageFileName); %force image
imshow(img); hold on;
colormap(gray);
%plot the centers of all particles associated with a contact
plot([contact.x],[contact.y],'or')
%plot arrows from the centers of all particles associated with a contact to
%the contact point
f = [contact.fAbs];
norm = max(max(f));
shift = min(min(f));
linewidths = 10*(f-shift+0.001)/norm;
for m= 1:length(f)
quiver([contact(m).x],[contact(m).y],[contact(m).contactX],[contact(m).contactY],0,'LineWidth',linewidths(m), Color='b')
end
%set font sizes and labels
set(gca,'FontSize',fs);
title('camera image','FontSize',fs);
drawnow;
% figure(2)
% %read and display the original image used as input to peDisc
% %img = imcrop(imread(camImageFileName),[xoffset, yoffset, xsize, ysize]); %force image
% img = bigSynthImg; %force image
% imshow(img); hold on;
% colormap(gray);
% %plot the centers of all particles associated with a contact
% %plot([contact.x],[contact.y],'or')
% %plot arrows from the centers of all particles associated with a contact to
% %the contact point
% %quiver([contact.x],[contact.y],[contact.contactX],[contact.contactY],0,'LineWidth',1.5)
% %set font sizes and labels
% set(gca,'FontSize',fs);
% title('camera image','FontSize',fs);
% hold off;
% figure(3)
% imagesc(W);
% colormap(jet);
%end
end
end
%%
[directoryini,fileNames(1:end-4),'_solved-joAdjacencyAbs.dlm']
Adj_ABS = dir([directoryini, 'adjacency/',fileNames(1:end-4),'_solved-joAdjacencyAbs.dlm']);
Adj_T = dir([directoryini, 'adjacency/',fileNames(1:end-4),'_solved-joAdjacency_T.dlm']);
Adj_N = dir([directoryini,'adjacency/',fileNames(1:end-4),'_solved-joAdjacency_N.dlm']);
if ~isfile([directoryini, 'centers_tracked.txt']);
centers = dlmread([directoryini, 'centers_tracked.txt'],',', 1,0);
%Adj_T_Newton = dir([directory,'*newtonized2-joAdjacency_NewtonizedT.dlm']);
%Adj_N_Newton = dir([directory,'*newtonized2-joAdjacency_NewtonizedN.dlm']);
% Adj_theta = dir([directory,'*solved-joAdjacencyN.dlm']);
% add as many as you want...
%% Make a list
Adj_list = [];
%numbers = [10, 18]
unique(centers(:,1));
for i = 1:216
%for i = 1:length(2)
frameid = str2num(Adj_T(i).name(frameidind:frameidind+3))
T = dlmread([directory,Adj_T(i).name]);
N = dlmread([directory,Adj_N(i).name]);
%T_Newtonized = dlmread([directory,Adj_T_Newton(i).name]);
%N_Newtonized = dlmread([directory,Adj_N_Newton(i).name]);
% Theta = dlmread([directory,Adj_theta(i).name]);
%list = [];
con = find(centers(:,1) == i); %the data that goes with the frame
con;
pos2ind = centers(con, 2); %
d = ~isnan(T); %where there is data that is actually a force
[row , col] = find(d==1); %which indices correspond to that contact
pos2ind;
newrow = pos2ind(row);
newcol = pos2ind(col);
ind=sub2ind(size(T),row,col);
ind;
length(row), length(newrow), length(newcol), real(T(ind)), real(N(ind));
% list_T = [row , col , T(row,col) , N(row,col) , Theta(row,col)];
list = [ones(length(row),1).*frameid,newrow , newcol , T(ind) , N(ind)];%, T_Newtonized(ind),N_Newtonized(ind)];
Adj_list=[Adj_list;list];
end
else
Adj_list = [];
for i = 1:length(Adj_T)
%for i = 1:
Adj_T(i).name;
frameid = str2num(Adj_T(i).name(frameidind:frameidind+3))
T = dlmread([directoryini, 'adjacency/',Adj_T(i).name]);
N = dlmread([directoryini, 'adjacency/',Adj_N(i).name]);
% Theta = dlmread([directory,Adj_theta(i).name]);
list = [];
d = ~isnan(T);
[row , col] = find(d==1);
ind=sub2ind(size(T),row,col);
% list_T = [row , col , T(row,col) , N(row,col) , Theta(row,col)];
list = [ones(length(row),1).*frameid,row , col , T(ind) , N(ind)];
Adj_list=[Adj_list;list];
end
end
%fram number, particle 1, particle id 2, tangential force, normal force
dlmwrite([directoryini,'Adjacency_list.txt'],Adj_list);