%ccly_Patterns_Analysis
%%MATLAB控制CST的思想基础：CST的建模仿真的命令都是VB命令，而要想使用MATLAB来控制CST就需要将应用之间的通信接口作为一个桥梁架接在MATLAB与CST之间，COM组件就是做这样的事情。
%%由于CST程序中的帮助文件关于VB语言的使用非常详细，所以我们需要做的就是将这座桥梁搭好。注：理论上所有手动操作CST的VB命令能在帮助文件里面找到对应代码
%%将VB命令转化为在MATLAB中能够运行的代码是MATLAB自动控制CST进行建模仿真的关键
%%典型的VB命令转化为CST代码如下所示[1]:
% With Brick                                    brick = invoke(mws, 'Brick')
%     .Reset                                    invoke(brick, 'Reset');
%     .Name ("brick1")                          invoke(brick, 'Name', "brick1");
%     .Component ("component1")                 invoke(brick, 'Component', "component1");
%     .Material ("PEC")               ==》      invoke(brick, 'Material', "PEC");
%     .Xrange (0, 2)                            invoke(brick, 'Xrange', 0, 2);
%     .Yrange (0, 3)                            invoke(brick, 'Yrange', 0, 3);
%     .Zrange (0, "a+3")                        invoke(brick, 'Zrange', '0', num2str(a+3));
%     .Create                                   invoke(brick, 'Create');
% End With                                      release(brick);
%基本思路就是找出mws中需要操作的对象，然后对其所有参数进行赋值或者执行命令，然后释放对象

%%参考文献：
%%[1]CST. "Application Note - Calling CST Studio from Matlab"
clc;
clear;
close all;

cst = actxserver('CSTStudio.application');%首先载入CST应用控件
mws = invoke(cst, 'NewMWS');%新建一个MWS项目
app = invoke(mws, 'GetApplicationName');%获取当前应用名称
ver = invoke(mws, 'GetApplicationVersion');%获取当前应用版本号
fullfilename=which('Patch_Array_1x10.cst');%打开一个已经有仿真结果的CST文件,此CST文件要和本m文件在同一文件目录下
invoke(mws, 'OpenFile', fullfilename);%打开一个存在的CST文件

%%模型文件初始化结束
%参数声明
e0=8.85418782e-12;
mu0=1.25663706e-6;
c=1/sqrt(e0*mu0);%光速常量，m/s
M=10;%阵元个数
a=15;%阵元间隔，mm    
%需要用到的关键对象
combineresults = invoke(mws, 'CombineResults');%用于方向图合成

%%生成不多波束指向波束所需要的相位分布，然后输入到CST里面进行方向图分析
for angle=0:20:90   %有源方向图合成，设置理论的波束偏转角度。
    phi=angle*pi/180;%将角度转成弧度
    f0=10;%频点为10GHz
    lambda0=c/f0/10^6;%计算自由空间波长
    p1=(-4.5:1:4.5)';%总共10个单元，只是为了让相位值看上去对称
    dpha=a*sin(phi)/lambda0*360;%相差，单位：°
    pha=a*sin(phi)*p1/lambda0*360;%生成等相差分布，单位：°
    amp=ones(10,1);%幅度相等
    lablename = ['ScanAngle_',num2str(angle)];
    invoke(combineresults, 'Reset');
    invoke(combineresults, 'SetMonitorType', 'frequency');
    invoke(combineresults, 'SetOffsetType', 'phase');
    invoke(combineresults, 'EnableAutomaticLabeling', 'False');
    invoke(combineresults, 'SetLabel', lablename);
    invoke(combineresults, 'SetNone');
    invoke(combineresults, 'AddFilter' ,':farfield:');
    invoke(combineresults, 'OnlyAtFrequency' ,'10');%只对10GHz的频点进行分析，可以设置成对所有的远场观测点进行综合，参照help文档里面VBA部分关于combineresults的说明即可
    for j=1:M
        invoke(combineresults, 'SetExcitationValues' ,'port', j, 1, amp(j), pha(j));
    end
    invoke(combineresults, 'Run')
end
release(combineresults);
release(mws);
release(cst);
%计算完成后可以在CST里面观察合成后的方向图是否有偏转