幻想森林

 找回密码
 立即注册
搜索
热搜: 活动 交友 discuz
查看: 3442|回复: 0

Genie-04-genie,vala,c的胶水

[复制链接]

136

主题

1751

帖子

548

积分

版主

Rank: 7Rank: 7Rank: 7

积分
548
发表于 2010-1-27 11:05:10 | 显示全部楼层 |阅读模式
显然genie和vala的混合是最方便的,都是用同一编译系统翻译成c的,要是不能通用,反倒是怪事了。
###在vala里写一个类,然后在genie里调用
a.vala:
  1. public class Test
  2. {
  3.     public int say(string s)
  4.     {
  5.         print(s);
  6.         return 0;
  7.     }
  8. }
复制代码
b.gs:
  1. init
  2.     var t = new Test()
  3.     t.say("hello")
复制代码
编译
  1. valac -o test.exe a.vala b.gs
复制代码
其实Vala和Genie有相当部分是语意一样,只是书面写法不一样。
像上面的那个a.vala就等同于
  1. class Test
  2.     def say(s:string):int
  3.         print(s)
  4.         return 0
复制代码
当然了,区别还是有的,比如这个例子里,vala里的print要比genie里的print少了个\n号。
反过来,genie里声明,vala调用也是一样的。个人兴趣在Genie上,不说vala。

既然都被翻译成c,也就意味着可以直接用c代码。
Genie里提供了extern关键字来修饰函数或类方法,可以直接调用c文件里的函数。
###方法一:先从c文件开始
a.c:
  1. #include "windows.h"
  2. typedef enum
  3. {
  4.     IntType,
  5.     FloatType
  6. }MyEnum;
  7. typedef struct
  8. {
  9.     const char* s;
  10.     int a;
  11.     float b;
  12.     char t[64];
  13. }mytest;
  14. void msgbox(mytest t, MyEnum me)
  15. {
  16.     switch(me)
  17.     {
  18.         case IntType:
  19.             sprintf(t.t, "%s:%d", t.s, t.a);
  20.             break;
  21.         case FloatType:
  22.             sprintf(t.t, "%s:%f", t.s, t.b);
  23.             break;
  24.         default:
  25.             break;
  26.     }
  27.     
  28.     MessageBoxA(NULL, &t.t[0], "MessageBox", 0);
  29. }
复制代码
b.gs:
  1. enum MyEnum
  2.     IntType
  3.     FloatType
  4. [SimpleType]
  5. struct mytest
  6.     s:string
  7.     a:int
  8.     b:float
  9.     t:char[64]
  10. def extern msgbox(mt:mytest, me:MyEnum)
  11. init
  12.     mt:mytest = {"Value", 1, 1.0f};
  13.     msgbox(mt, MyEnum.IntType);
  14.     msgbox(mt, MyEnum.FloatType);
复制代码
[SimpleType]是可以修饰如何用来编译成c代码的Attributes。
这里是用说明定义的这个struct,使其和c一样的值类型的方式工作。
Genie里的struct其实就是c里的struct的指针,也就是引用类型。
以后写c文件常记得用struct指针,就不再写[SimpleType]了。
用了winapi,自然编译前要先加上mingw32的winapi库。http://sourceforge.net/projects/ ... 20for%20MS-Windows/
  1. valac -X -mwindows -o test.exe a.c b.gs
复制代码
这种作法写了两次数据定义,有点麻烦。
当然了,也可以把b.gs里的数据定义部分移出来,单独写在一个gs文件里,方便管理和修改。
其实,完全可以只写一次定义,不过编译却要2-3次。且可以不用为struct写[SimpleType]了。

###方法二:先从gs文件开始
先编译上面的去掉这个[SimpleType]的b.gs
  1. valac b.gs -C -H b.h
复制代码
加参数用-C -H a.h输出头文件。(-H参数一定要指定头文件的名字)
再在a.c里包含b.h。试着编译一次:
  1. valac b.gs a.c
复制代码
一般来说b.h源文件里会有一些“奇怪的东西”报错,只要不是所需要的类型定义,完全可以注释掉出错的行。另外还有一些定义,像enum里的成员等等,编译器会自动为它改名,所以a.c文件也要相应的改动。
ps.如果不是从上面的例子复制来,而是直接写c文件,那么直接用b.h里改好的名字就行。
新的a.c:
  1. #include "b.h"
  2. #include "windows.h"
  3. void msgbox(mytest* t, MyEnum me)
  4. {
  5.     switch(me)
  6.     {
  7.         case MY_ENUM_IntType:
  8.             sprintf(t->t, "%s:%d", t->s, t->a);
  9.             break;
  10.         case MY_ENUM_FloatType:
  11.             sprintf(t->t, "%s:%f", t->s, t->b);
  12.             break;
  13.         default:
  14.             break;
  15.     }
  16.     
  17.     MessageBoxA(NULL, &t->t[0], "MessageBox", 0);
  18. }
复制代码
再次
  1. valac b.gs a.c
复制代码
搞定,收工。

Gneie的基本内容差不多就这么些了吧。除了Genie自己外,库里还有不少的lgpl的东西。gee被Genie默认使用了,那么下面的目标是gtk+。

ps.简单的试了下GTK+,官方的DEMO在我的Win7下,有两个例子莫名其妙的出错,也查不出来是哪里出的问题。再加上GTK+在Win下不是原生的风格,所以还是放弃使用GTK+的打算,反正游戏也用不了那么多的GUI元件,调用c写个窗口创建和消息处理就差不多了。
え~え~お!!!
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|幻想森林

GMT+8, 2024-3-28 19:34 , Processed in 0.022830 second(s), 20 queries .

Powered by Discuz! X3.4

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表