mtex-toolbox / mtex

MTEX is a free Matlab toolbox for quantitative texture analysis. Homepage:
http://mtex-toolbox.github.io/
GNU General Public License v2.0
278 stars 183 forks source link

GOS calculation in deformed map applying initial boundary #2008

Closed KIMSseongho closed 8 months ago

KIMSseongho commented 8 months ago

50x50_Initial.zip Hello, I'm leaving a code for my current problem in hopes of getting some help.

I currently have two types of .ctf files. 1) Original EBSD data (Mean orientation) 2) Data given a new predicted Euler angle by performing uniaxial tension simulation based on original EBSD data The size of the EBSD data is the same (50x50x1), and the only difference is the Euler angle.

When GrainID is 5 degrees, it can be seen that although the size is the same, the Euler angle has changed, so the number of defined grains varies from 14 in 1) to 213 in 2).

If you draw the ND IPF map included in the code, you will be able to compare the EBSD data before and after transformation.

Therefore, the following code created a code with GrainID initial.boundary based on ebsd_deformed data, and calculated each for KAM/GAM/GOS.

It was confirmed that KAM/GAM is calculated normally because it is calculated according to the misorientation relationship between pixels regardless of the assigned boundary.

The problem is when calculating GOS. When applying the above method, GOS defines grains according to grain ID for pre-calculated EBSD values, so it does not seem meaningful to calculate by assigning an initial boundary in the above manner. In other words, when done in the above manner, inaccurate results are obtained. (result of GOS value: 10~50)

What I want is to create grains with the same grain ID so that the EBSD data in 2) can be compared one-to-one with the grain ID defined in 1), and then compare grains with the same deformed data as the grain defined based on the initial boundary. I want to derive GOS.

I would be grateful if you could write modified code for this. Below is the MTEX code used I will attach a picture of the Initial/deformed IPF map. also .ctf file uploaded !

[MTEX code]

%% File selection for the initial EBSD dataset
disp('Select the Initial EBSD Data File');
[file, path] = uigetfile({'.ctf'; '.ang'; '.h5'; '.osc'}, 'File Selector');
if isequal(file, 0)
disp('File selection cancelled. Exiting script.');
return;
end
initialEbsdFile = fullfile(path, file);

% Load initial EBSD data
ebsd_initial = EBSD.load(initialEbsdFile, 'convertEuler2SpatialReferenceFrame');
% Calculate grains with 5 degrees threshold
[grains_initial, grainId_initial] = calcGrains(ebsd_initial, 'angle', 5*degree);

%% File selection for the deformed EBSD dataset
disp('Select the Deformed EBSD Data File');
[file, path] = uigetfile({'.ctf'; '.ang'; '.h5'; '.osc'}, 'File Selector');
if isequal(file, 0)
disp('File selection cancelled. Exiting script.');
return;
end
deformedEbsdFile = fullfile(path, file);

% Load deformed EBSD data
ebsd_deformed = EBSD.load(deformedEbsdFile, 'convertEuler2SpatialReferenceFrame');

% Directly assign grain IDs from initial to deformed dataset based on pixel position
ebsd_deformed.prop.grainId = grainId_initial;

% Calculate grains for the deformed dataset
[grains_deformed, grainId_deformed] = calcGrains(ebsd_deformed, 'angle', 5degree);
%% Plotting the initial EBSD data with grain boundaries and ID numbers
figure;
plot(ebsd_initial, ebsd_initial.orientations);
plotx2east;
plotzOutOfPlane;
hold on;
plot(grains_initial.boundary, 'linewidth', 2);
text(grains_initial,int2str(grains_initial.id));
title('Initial EBSD Data with Grain Boundaries and IDs');
saveas(gcf, 'Initial_IPF.png')
%% Plotting the deformed EBSD data with corresponding grain boundaries and ID numbers
figure;
plot(ebsd_deformed, ebsd_deformed.orientations);
hold on;
plot(grains_initial.boundary, 'linewidth', 2);
%plotx2east;
plotzIntoPlane;
text(grains_initial,int2str(grains_initial.id))
title('Deformed EBSD Data with Grain Boundaries and Mapped IDs');
saveas(gcf, 'Pred_IPF.png')
%% KAM of Original grains
ebsd_deformed = ebsd_deformed.gridify;
kam = ebsd_deformed.KAM / degree;
% plot the first order KAM
% Plot full KAM map
figure
plot(ebsd_deformed,ebsd_deformed.KAM('threshold',5degree,'order',5) ./ degree,'micronbar','off')
mtexColorbar('title','KAM in degree')
% Use LaboTeX for red colour KAM map
mtexColorMap WhiteJet
hold on
% For full map
plot(grains_initial.boundary, 'linewidth', 2);
hold off
text(grains_initial,int2str(grains_initial.id))
saveas(gcf, 'KAM_whole.png')
%% GAM Plot for orignal grains
% calculate the GAM
gam_original = ebsd_deformed.grainMean(ebsd_deformed.KAM)./degree;
figure
plot(1:10);
% plot the GAM map for original grains
plot(grains_initial,gam_original,'micronbar', 'off')
mtexColorbar('title','GAM in degree')
title('GAM map for Original Grains')
text(grains_initial,int2str(grains_initial.id))
saveas(gcf, 'GAM_whole.png')
%% Grain oreientation spread calcualtion
% Calculate GROD for original grains
grod = ebsd_deformed.calcGROD(grains_deformed);
% Calculate GOS and MGOS for original grains
GOS_orig = grainMean(ebsd_deformed, grod.angle)./degree;
% Plot GOS for original grains
figure;
plot(grains_initial, GOS_orig,'micronbar', 'off')
% overlay grain and subgrain boundaries
hold on
plot(grains_initial.boundary,'lineWidth',1.5)
hold off
text(grains_initial, int2str(grains_initial.id));
mtexColorbar('title','Original GOS in degree')
saveas(gcf, 'GOS_whole.png')
output_table_GOS = table(grains_initial.id,GOS_orig,gam_original ,'VariableNames',{'Grain ID','GOS','GAM'});
writetable(output_table_GOS,'GOS_data_original.xlsx')

result Input_file(Ini, Def).zip

zmichels commented 8 months ago

Hi,

I think you'll want to post/share the datasets (.CTFs) for troubleshooting this. It doesn't sound like MTEX is doing anything out of the ordinary or unexpected, and so identifying a technique for your specific approach would probably be easier if folks could work with data you are working with.

kilir commented 8 months ago

Hi, in addition to example files, please consider shortening your code to the relevant parts. Cheers, Rüdiger

KIMSseongho commented 8 months ago

I didn't know how to upload the .ctf file, but i just upload now ! thanks a lot guys

zmichels commented 8 months ago

For clarity, what do you mean by this statement?: "inaccurate results are obtained. (result of GOS value: 10~50)"

How do you know what the GOS value should be, such that you believe the results are inaccurate? For example, those GOS values are completely plausible for a post-deformation microstructure with pronounced intragranular distortion.

kilir commented 8 months ago

Maybe I misunderstand a few things, but it seems you want to assign each pixel in the deformed map to a grain corresponding to the initial map, i.e. pixels do not change the grain they were belonging to, right? You can compute grain based on grainId. of course this may result in boundaries which do not fulfill the an angle threshold criterion, however, having both (have boundaries based on an angle threshold AND exactly the same pixel assignment despite pixels changed orientation) is to my option not possible.

% Load the data
ebsd_initial = EBSD.load('50x50_Initial.ctf', 'convertEuler2SpatialReferenceFrame');
ebsd_deformed = EBSD.load('50x50_Deformed.ctf', 'convertEuler2SpatialReferenceFrame');

% Calculate grains with 5 degrees threshold
[grains_initial, ebsd_initial.grainId] = calcGrains(ebsd_initial, 'angle', 5*degree);

% Calculate grains for the deformed dataset based in grainId of the initial grains
[grains_deformed, ebsd_deformed.grainId] = calcGrains(ebsd_deformed, 'custom', ebsd_initial.grainId );

plot(ebsd_initial,ebsd_initial.KAM/degree)
hold on; plot(grains_initial.boundary); hold off
mtexTitle('initial - KAM')

nextAxis(1,2)
plot(grains_initial,grains_initial.GOS/degree)
mtexTitle('initial - GOS')

nextAxis(2,1)
plot(ebsd_deformed,ebsd_deformed.KAM/degree)
hold on; plot(grains_deformed.boundary); hold off
mtexTitle('deformed - KAM')

nextAxis(2,2)
plot(grains_deformed,grains_deformed.GOS/degree)
mtexTitle('deformed - GOS')
mtexColorbar

Hopt this helps. Cheers, Rüdiger

KIMSseongho commented 8 months ago

I was wondering how to calculate GOS (Grain Orientation Spread). Depending on the grain corresponding to each pixel in the initial map, we attempted to assign the same grain to pixels in the deformed map. To achieve this, I thought of a way to calculate GOS, but it was difficult to implement and I had difficulties because I did not properly understand the code.

However, the line below from the code you provided seems to solve this problem.

% Calculate grains for the deformed dataset based in grainId of the initial grains [grains_deformed, ebsd_deformed.grainId] = calcGrains(ebsd_deformed, 'custom', ebsd_initial.grainId );

This line of code assigns the calculated GOS to the transformed map based on the grains (Grain IDs) of the initial map. In the resulting transformed map, GOS is calculated based on the corresponding grain ID.

This line of code allowed me to graduate maybe with the results I wanted, and I am so grateful. really thanks a lot

best regard Seongho Lee

kilir commented 8 months ago

Happy to hear that this works.