Note: This discussion is about an older version of the COMSOL Multiphysics® software. The information provided may be out of date.
Discussion Closed This discussion was created more than 6 months ago and has been closed. To start a new discussion with a link back to this one, click here.
determin face numbers associated with a domain
Posted 16.03.2011, 12:44 GMT-4 Geometry Version 3.5a 11 Replies
Please login with a confirmed email address before reporting spam
Thanks for your help,
Everet
This is the code I'm working with:
flclear fem
% Geometry
g1=block3('200e-6','200e-6','200e-6','base','corner','pos',{'-100e-6','-100e-6','230e-6'},'axis',{'0','0','1'},'rot','0');
g2=cone3('7.37039724389e-6','20.25e-6','20','pos',{num2str(tipOffset),'0',num2str(zTip+20.25e-6)},'axis',{'0','0','-1'},'rot','0');
g3=sphere3(num2str(radius),'pos',{num2str(tipOffset),'0',num2str(zTip)},'axis',{'0','0','1'},'rot','0');
g4=geomcomp({g1,g3},'ns',{'substr','sphere'},'sf','substr*sphere+substr','repairtol',1.0E-10,'face','none','edge','all');
g5=block3('1.5e-6','24e-6','100e-9','base','corner','pos',{'-0.75e-6','-12e-6','430e-6'},'axis',{'0','0','1'},'rot','0');
g6=cylinder3(num2str(cylRadius),'100e-9','pos',{num2str(tipOffset),'0','430e-6'},'axis',{'0','0','1'},'rot','0');
g7=geomcomp({g5,g6},'ns',{'sio2','cylinder'},'sf','sio2*cylinder+sio2','repairtol',1.0E-10,'face','none','edge','all');
g8=block3('200e-6','200e-6','200e-6','base','corner','pos',{'-100e-6','-100e-6','430e-6'},'axis',{'0','0','1'},'rot','0');
% Geometry objects
clear s
s.objs={g2,g4,g7,g8};
s.name={'tip','substr','sio2','air'};
s.tags={'g2','g4','g7','g8'};
fem.draw=struct('s',s);
fem.geom=geomcsg(fem);
Please login with a confirmed email address before reporting spam
% determine what faces are associated with which domains
% get info up/down info
upDown=geominfo(fem.geom,'out','ud');
% domain(n) holds the faces associated with domain n-1
% domain 0 is the volume surrounding the model
domain=cell(1,max(upDown(:))+1);
% loop through the faces and add them to the appropriate domains
for i=1:length(upDown)
domain{upDown(1,i)+1}=[domain{upDown(1,i)+1},i];
domain{upDown(2,i)+1}=[domain{upDown(2,i)+1},i];
end
Please login with a confirmed email address before reporting spam
Please login with a confirmed email address before reporting spam
If you liked that then you may also appreciate a few other tid bits...
To set up boundary conditions on faces you can loop through the list of faces associated with a specific domain:
% define boundary conditions
clear bnd
bnd.V0 = {0,0,tipVoltage};
bnd.type = {'V0','cont','V'};
bnd.ind = ones(1,length(upDown))*2; % init all faces to be continuous
% find the faces that are ground
for i=1:length(domainNames)
if (strcmp(domainNames{i}, 'surround'))
bnd.ind(domain{i})=1;
end
end
% find the faces that are v0
for i=1:length(domainNames)
if (strcmp(domainNames{i}, 'tip'))
bnd.ind(domain{i})=3;
end
end
also for doing post processing integrations (or any thing else for that matter) you can find the faces common to two domains by the intersection of two sets. For example, if you want to know what faces bind regions 1 and 2, you can find the intersection:
intersect(domain{1},domain{2})
Just a few happy thoughts
Please login with a confirmed email address before reporting spam
I have the same problem. Will be thankful for help.
I need to add through MATLAB new subdomains and than define them the boundary conditions.
bnd.V0 = {0,0,3000};
bnd.type = {'nJ0','V','V'};
bnd.ind = [1,1,1,1,2,2,2,1,2,2,3,3,3,1,1,3,3,1];
How can I know which are the indexes of the new added domains?
Thanks,
Alex
Attachments:
Please login with a confirmed email address before reporting spam
From looking at your model I believe I understand your question/problem. To summarise (please correct me if I'm wrong) you have a tissue cylinder with several electrodes/cylinders inserted. The first one in the centre is positive and remains constant. The remaining (4 in this case) electrodes are then placed symmetrically around the centre. The problem your having is defining the physics properties for the subdomains and boundaries.
The first problem that I have not really solved is how COMSOL assigns domain numbers. You may need to play around opening your .m file with COMSOL with different number of negative electrodes to be able to associate an electrode with a domain.
In the current case:
domain 0: the surrounding area - out side your model
domain 1: the tissue
domain 2,3,5,6: negative electrodes
domain 4: positive electrode
Assuming that you find a way to identify what domains are associated with what structures then its smooth sailing...
I'll show you how I approached the problem
% determine what faces are associated with which domains
% get the up/down info
upDown=geominfo(fem.geom,'out','ud');
% domain(n) holds the faces associated with domain n-1
% domain 0 is the volume surrounding the model
domain=cell(1,max(upDown(:))+1);
% loop through the faces and add them to the appropriate domains
for i=1:length(upDown)
domain{upDown(1,i)+1}=[domain{upDown(1,i)+1},i];
domain{upDown(2,i)+1}=[domain{upDown(2,i)+1},i];
end
% determine the names associated with the domains
domainNames={'surround','tissue','neg','neg','pos','neg','neg'};
This code creates a cell array that holds arrays of varying length. each array holds the faces that are associated with each domain. For example, domain{1} would return all the faces associated with domain 0, the surrounding area [1,2,3,4,8,14,18,22,23,30,34]. Or for domain 4, domain{4+1}=[15,16,17,18,26,27]
This code works by calling the function geominfo ('help geominfo')
upDown=geominfo(fem.geom,'out','ud');
This function will return a 2xN matrix where N is the number of faces. Each face has two domains associated with it, one on either side. This is what is in the column. To use this data, simply loop through the matrix and add each face to a vector that represents the faces used to enclose a domain.
Again, the domainNames definition is based on this particular case. I hope you can figure a way to define this automatically... I'd love to see it.
The next step is to define the boundary conditions. Here is the code I used to do this:
% define boundary conditions
clear bnd
bnd.V0 = {0,0,3000}; % define negative voltage as 0V and positive voltage as 3000V
bnd.type = {'fp','V','V'}; % was complaining about type nJ0 so I changed it to a floating potential so it would compile
bnd.ind = ones(1,length(upDown)); % init all faces to be of type nJ0. 'length(upDown)' returns the number of faces
% find the faces that are negative
for i=1:length(domainNames)
if (strcmp(domainNames{i}, 'neg'))
bnd.ind(domain{i})=2; % change the initial condition for all faces on all negative electrodes to be 0V
end
end
% find the faces that are positive
for i=1:length(domainNames)
if (strcmp(domainNames{i}, 'tip'))
bnd.ind(domain{i})=3; % change the initial condition for all faces on the positive electrode to be 3000V
end
end
At this point you have created an application mode with initialised boundary conditions. The subdomain settings now need to be set.
% define permitivity
clear equ
equ.sigma = {0.2,5.5e7}; % 5.5*10^7 is better written as 5.5e7
equ.ind = []; % initialise the indices vector. when done, this vector will define which of the two
% options you have defined for each subdomain, sigma=0.2 or sigma=5.5e7
for i=1:length(domainNames)
switch domainNames{i}
case {'neg' 'pos'}
equ.ind=[equ.ind,2];
case {'tissue'}
equ.ind=[equ.ind,1];
end
end
now that we have the boundary conditions and the subdomain settings we need to put them into the app1 structure
% initialise the app1 variable
% Application mode 1
clear appl
appl.mode.class = 'EmConductiveMediaDC';
appl.module = 'ACDC';
appl.sshape = 2;
appl.border = 'on';
appl.assignsuffix = '_emdc';
% boundary conditions
appl.bnd = bnd;
% subdoiman conditions
appl.equ = equ;
I hope this helps you understand what I've done. I also hope I haven't done your home work for you ;) in fact all I did was copy and paste my code with a few very minor modifications... The sum of what I've done is attached below in your model4.m file.
Also, to help with the integration at the end ill show you how I accomplished (sorry, but I didn't bother updating it for your needs :)
Good luck!
% faces associated with the tip
tipFace=domain{ismember(domainNames,'tip')==1};
%%
% we need to know whether the up side or down side of the tip is in
% contact with the air
tipUpFace=[];
tipDownFace=[];
for i=tipFace
% get the upDown entry for the given face
faceUD=upDown(:,i);
% decide wether it should be on the up list or the down list
if (faceUD(1)==3)
tipDownFace=[tipDownFace,i];
else
tipUpFace=[tipUpFace,i];
end
end
dnTEz='-0.5*(down(Dx_es)*down(Ex_es)+down(Dy_es)*down(Ey_es)+down(Dz_es)*down(Ez_es))*unz+(unx*down(Dx_es)+uny*down(Dy_es)+unz*down(Dz_es))*down(Ez_es)';
unTEz='-0.5*(up(Dx_es)*up(Ex_es)+up(Dy_es)*up(Ey_es)+up(Dz_es)*up(Ez_es))*dnz+(dnx*up(Dx_es)+dny*up(Dy_es)+dnz*up(Dz_es))*up(Ez_es)';
% Integrate - tip
I1=postint(fem,unTEz,'unit','N','recover','off','dl',tipUpFace,'edim',2);
I2=postint(fem,dnTEz,'unit','N','recover','off','dl',tipDownFace,'edim',2);
tipForce=I1+I2;
Attachments:
Please login with a confirmed email address before reporting spam
Thanks a lot,
Will update with the progress.
I solved the issue with domane names by just assigning the name for each created electrode.
Please login with a confirmed email address before reporting spam
% determine the names associated with the domains
domainNames={'surround','tissue','neg','neg','pos','neg','neg'};
you don't know what order to put them in. What I mean is that in this case surround is domain 0, tissue is domain 1 ... and the last negative electrode is domain 6. BUT this order will change depending on the number of electrodes that you include.
Please login with a confirmed email address before reporting spam
Number of negative electrodes changes,
I am able to create an array of objects and have an array with all bondaries ( faces)
However, need to identify them. Cannot use the domane names manually since I have a different amount of faces every time.
My idea with the s.name did not work.
How can I know for each domain its s.name?
Attachments:
Please login with a confirmed email address before reporting spam
I'm not sure what your question is either. I think that if you'd like me to look through your code you should spend some time to ask the question a bit more clearly.
The code that I posted before should mostly work for you if you can just figure a way to create a cell array of domain names as I had done here:
% determine the names associated with the domains
domainNames={'surround','tissue','neg','neg','pos','neg','neg'};
this really is the tricky part, but it appears that you at least found a way to identify the tissue domain, the domain with the most faces:
tissueDomain = 0;
maxfaces=0;
for i = 2 : length(faces)
if (length(faces{i})>maxfaces)
tissueDomain = i;
maxfaces = length(faces{i});
end;
end;
after that, you can always assume that the surround is domain zero. You can then assume that all the domains with 6 sides are negative electrodes. That leaves only to determine the domain number of the positive electrode.
After a bit of looking at your model, i found a solution to this specific case. COMSOL always assigns domain 0 to surround, and domain 1 to tissue. After that the rest of the domains belong to the negative electrodes except for one. It just so happens that in your model, COMSOL assigns the domain number to the positive electrode in a predictable way.
If the number of negative electrodes is even, then the number of negative electrodes before and after the positive electrode domain is even.
If the number of negative electrodes is odd then the positive domain can be found be checking whether or not (N+1) is divisible by 4. If it is, then the extra negative electrode will have a domain number lower than the positive electrode's domain number, and if not it will be greater than the positive electrode's domain number.
% determine the names associated with the domains
domainNames=cell(size(domain));
domainNames{1}='surround';
domainNames{2}='tissue';
for i=3:length(domain)
domainNames{i}='neg';
end
% find wich electrodeis positive
% if N is even then the positive electrode is the middle of electrode domains
if mod(N,2)==0
domainNames{(3+length(domain))/2}='pos';
else
% N is odd
if mod(N+1,4)==0
% if N is odd and N+1 is divisible by 4 then we should round up
domainNames{ceil(N/2)+3}='pos';
else
% else we should round down
domainNames{floor(N/2)+3}='pos';
end
end
I attached an updated version of the file I posted the last time
Good Luck
Attachments:
Please login with a confirmed email address before reporting spam
Thanks a lot. Now it is possible to define the boundary conditions in the specific case the positive electrode in the center. Attach the full working code with insulation boundary conditions.
This solves my specific case.
Again thanks a lot->research is moving forward.
However, I think there is still a way to define the domain names in the general case.
In COMSOL it is possible to give names to boundaries (bnd.name)
In addition, once we create a new geometry we git it a name :
g1=cylinder3('0.4','0.1','pos',{'0','0','-0.05'},'axis',{'0','0','1'},'rot','0');
clear s
s.objs={g1};
s.name={'tissue'};
s.tags={'g1'};
My question was if it is possible to connect s.name with what you called domainNames. Because
domainNames(1)=one of the fem.geom. subdomains s.name. I still cannot find this link.
Attachments:
Please login with a confirmed email address before reporting spam
I am at a loss as to correctly predicting the domain numbers from the geometry. The problem is that I've found a way around it for my research (and yours too) and I no longer care too much to do it properly ;) I'd much rather spend the time writing my thesis...
Good Luck with your research
Note that while COMSOL employees may participate in the discussion forum, COMSOL® software users who are on-subscription should submit their questions via the Support Center for a more comprehensive response from the Technical Support team.
Suggested Content
- KNOWLEDGE BASE How does COMSOL Multiphysics handle complex-valued numbers and problems in the frequency domain?
- FORUM Determining which face numbers associated to each object name
- BLOG Characterizing the Flow and Choosing the Right Interface
- KNOWLEDGE BASE Resolving Time-Dependent Waves
- BLOG Automatically Handling Selections in COMSOL Multiphysics®