在ZEMAX和MATLAB之间通信

来源:互联网 发布:java用for循环打印菱形 编辑:程序博客网 时间:2024/05/22 08:28

如何在ZEMAX和MATLAB之间通信

原作:DerekGriffith

本文内容:

1如何在MATLABZEMAX中设置通信链接

2如何为MATLAB设置ZEMAX DDE 工具箱

3常见问题及解答

Zemax and Matlab : 强大的配对

Zemax具有内置的DDE(动态数据交换)服务器,因而允许其他的windows程序和zemax函数之间建立链接。如果你用譬如C++之类的编程语言来编写一个zemax DDE应用,那将是一件非常复杂的事情。另一种选择是选择一种脚本语言,比如说tcl,python和matlab。Matlab是不错的选择,因为它有大量的处理和可视化科学与工程数据的函数。Matlab也有工具箱在一些更加专业和学科性的领域来扩展它的能力。

那么,什么是DDE?

DDE是windows的一种协议来允许不同应用之间的通信。

DDE通信有一些模式,最简单的就是数据串之间的交换。两个应用中的一个必须把自己设置为服务器。Zemax此时就是服务器,所以你要做的事情就是打开zemax。你一旦启动了zemax,dde服务器就已经就绪并等待客户机来连接和请求服务。此时的客户机就是matlab。


从matlab连接到zemax

如果你查阅zemax手册中的“Zemax Extensions”章中的The Data Items部分,你会看到许多不同的你可以用matlab(或者其他的客户机)发送到zemax的请求命令。手册里还记录了zemax会返回给客户机的回复信息。这些请求可能是为了让zemax运行一个特别的函数或者计算,挥着仅仅是为了发送当前存储在zemaxDDE服务器上的透镜数据。

有一点需要注明。Zemax总会将存在DDE服务器中的透镜数据复制一份给zemax的LDE用户。这个方法很不错,因为你不会希望一些DDE客户机未经预料的进入zemax并改变了你的透镜数据。有一些函数能直接把LDE中的透镜数据复制到DDE服务器中或者反过来也可。PushLens项指导zemax来把DDE服务器中的透镜数据复制给LDE,GetRefresh项会把LDE中的数据复制到DDE服务器中。当你在matlab中开发你的应用时,追踪你的数据并注意如何运用PushLens 和 GetRefresh是非常重要的。

从zemax的preferences对话框中,你能控制哪个扩展程序(此时是matlab)能让zemax把透镜数据从DDE服务器中发送到LDE中去。选择EDITORS标签,找到Allow Extensions to Push Lenses复选框。见下图:

Matlab有一些基础函数来执行DDE客户机操作。他们包括:

ddeinit -这个函数用来初始化DDE对话

 

ddereq -用来从DDE服务器中请求数据

 

ddeterm -结束DDE链接

基本的从matlab连接到zemax的顺序是:

1启动zemax和matlab

2使用ddeinit函数初始化DDE链接

3使用ddereq函数发送给zemax请求和接受其回复

4用ddeterm函数结束链接

Ddereq函数是以文本模式使用的,也就是说,你发送给zemax数据和接收到的回复都是字符串。为了把字符串变成更有用的类型(浮点型,双精度型,整型等),你要用到sscanf或其他函数来进行字符串变换,比如str2num函数。

你可以通过下载zemax dde toolbox来减少一些努力。这个工具箱是GPL下的开放资源,并且实现了zemax手册中zemax extensions记录的每一个数据项条目的功能。工具箱中相应的matlab函数有和数据项一样的名字,但是前缀是z。下面是开始的步骤:

1下载工具箱文件(zip文件)

2解压,并将解压后的文件放在磁盘上的任何位置,命名为MZDDE。

3启动zemax和matlab

4把MZDDE目录加入到matlab路径中以使matlab找到新函数(文件菜单>选择set path)

5如果你在matlab中键入help medde,你会得到一列关于所有工具箱中的函数和简短的描述的清单。如果是这样,那么你就可以使用工具箱 了。

6使用zDDEInit函数打开到zemax的DDE连接。这一步很重要,如果你在试图执行其他调用前不这么做,matlab会发布一个冗长的错误信息以表示一些麻烦已经发生了。你应该联系你的数学技术支持人员。如果有这样的提示的话,直接忽略,然后调用zDDEInit。

7需要的话可以调用工具箱中其他的函数。如果你要和zemax用户接口直接联系的话,使用zPushLens和 zGetRefresh是非常明智的。当然,你也可以从matlab命令行来调用这些函数,或者把它们编入你的matlab函数和脚本里。

8调用zDDEClose来结束。在大多数情况下这一步并不重要,你也可以直接结束matlab和zemax。

注意到为了增加可读性,工具箱函数名是大写的。Matlab函数名在windows下对大小写不敏感,也就是说,zddeinit和zDDEInit效果是一样的。在matlab命令行中这是很方便的。但是大写可以提高函数和脚本的可读性。所有函数的源码都是可以修改和重复使用的,你也可以检查源码来观察基础的matlab DDE调用是如何工作的。

超时(TIMEOUTS)

Matlab的每一个到zemax的DDE调用都可能会超时。zDDEInit函数的默认设置超时时间是3秒钟。也就是说,如果zemax在3秒内不响应DDE请求,matlab调用会空手而归。你需要增加时间限制如果你调用zemax来做一些费时间的计算的话。可以用zSetTimeout函数调用来做到。

举例:

这是一个zemax和matlab交互的简单例子。此时已经启动了zemax。在matlab中键入以下命令:

>> zddeinit

 

ans =

 

    0

 

>>zLoadFile('C:/Zemax/Samples/Sequential/Objectives/Cooke 40 degree field.zmx')

 

ans =

 

    0

 

>> zpushlens(1)

 

ans =

 

    0

 

>> [x, y] = SpiralSpot(0.4, 0, 1, 10,10000);

 

>> plot(x,y)

你会得到下面的图:

首先,初始化DDE连接,结果是0表示连接成功。然后zLoadFile函数要求zemax把透镜数据装入DDE服务器。现在,把点列图画出来的一种漂亮的方法是追踪通过透镜入瞳的螺旋光线然后把像平面的光线截面画出来。这通过工具箱函数SpiralSpot来实现。键入help spiralspot来获取该函数的帮助。因为SpiralSpot首先使用zGetRefresh来开始对LDE中的透镜数据作用,所以在调用SpiralSpot之前必须先调用zPushLens。zPushLens的超时时间是1秒。

注意到本例中,如果你如果在zemax文件菜单中载入相同的透镜那么会和调用zLoadFile相同的效果。

追踪大量光线

标准的DDE调用文本模式很多情况下是足够使用的,但是当客户机和服务器之间大量数据需要交换时就力不从心了。当你想追踪大量光线时,这个问题就来了。

并不是一次追踪一条光线,而是先创建一个包含所有光线的数组,然后一次性把这个数组传递给zemax。Zemax然后追踪所有的光线,然后把整个数组还给客户机。注意在DDE中传输的并不是所有数据,而仅仅是数组所在内存的指针。这样便消除了大量光线追迹时DDE通信的瓶颈。

不幸的是,当初在写工具箱时,matlab就不允许除了文本模式以外的DDE模式。为了避免这个问题,需要用mex(matlab可执行)格式写一些C代码。生成的.dll文件命名为zArrayTrace。键入help zArrayTrace以获得关于大量光线追迹的更多信息。查阅zemax手册中的相应部分也同样有用。为了设置zArrayTrace模式0的光线输入数据,函数genRayDataMode0很有用。

编译matlab编写的单机zemax扩展

如果你有matlab编译器,那么你可以把用工具箱编写的matlab脚本编译到单机扩展,以便zemax扩展菜单可以运行。这样做的时候有一些陷进需要避免。

首先,有一些matlab函数不能被编译,你需要为这些函数(还好不是很多)想一些其他办法。

第二,当你的单机扩展本应该在装有matlab的电脑上运行良好时,事实上却并没有运行,这主要是因为这台电脑没有matlab运行时间库(Matlabruntime libraries)。因此你需要把你的扩展和运行时间库一起打包来确保完全可移植性。Matlab的自解压文件mglinstaller.exe会使打包大多数运行时间库更容易一点,文件目录是C:/MATLAB/extern/lib/win32或者附近。

最后一个是常规的matlab运行时间库不包含上面提到的DDE函数代码。通过你的matlab安装文件中搜索匹配dde*.dll的文件就能找到这些.dll文件。一般在C:/MATLAB/Toolbox/matlab/winfun或附近。运行时间库包括DDE库,都必须安装在WINDOWS搜索路径下。

使用工具箱时需谨记:

1你的第一个调用必须是zDDEInit。

2超时可能是个问题。必要时用zSetTimeout增加DDE超时限。

3zemax有两份透镜数据,一个在LDE中表示,一个存在DDE服务器里。你可以用zPushLens 和 zGetRefresh把一个数据复制到另一个。zPushLens总是需要一个参数作为超时限。

4你只有在EDITORS标签中选中了复选框以后才可以用zPushLens。

1 0
原创粉丝点击