带有DOM交互的C ++中的整个Web应用程序

时间:2013-07-12 17:39:10

标签: asm.js

我最近听说过使用emscripten将c ++代码编译为javascript,以及如果asmjs优化完成,它有可能真正快速地运行应用程序。

我已经阅读了几篇文章,教程甚至听过一些非常有趣的youtube videos。我也成功运行了hello world示例。

但是,我不知道这种方法的全部功能,特别是如果整个 webapp可以/应该用C ++编写,而不需要胶水代码。

更具体地说,我想写一些类似于以下C ++的东西(作为参考而不是工作代码)。

#include <window>
class ApplicationLogic : public DOMListener{
private:
    int num;
public:
    ApplicationLogic():num(0);
    virtual void onClickEvent(DOMEventData event){
        num++;
    }
    virtual ~ApplicationLogic(){}
}

int main(){
    DOMElement but = Window.getElementById("foo");
    ApplicationLogic app();
    but.setOnclick(app);
}

我希望它能说清楚这个想法,但目标是实现类似的目标:

  • 一个静态函数,用于在窗口准备就绪时初始化模块(与jquery.ready()相同的行为)。因此可以将侦听器添加到DOM元素中。

  • 直接从C / C ++与DOM交互的方式,因此#include <window>基本上可以访问DOM和其他元素,如JSON,Navigator等。

我一直在想Lua以及当lua脚本包含一个共享对象(动态链接库)时,它在该.so文件中搜索初始化函数,并且会在模块外部注册可用的函数如何在asmjs中创建的函数模块的返回行为。但我无法弄清楚如何使用C ++直接模拟jquery.ready。

正如你所看到的,我对asmjs知之甚少,但是我没有找到教程或类似的东西,我已经阅读了stdlibc,stdlibc ++和SDL在编译时包含的标准库的引用,但是没有关于如何从C ++源操作DOM的参考。

2 个答案:

答案 0 :(得分:2)

怎么了。我知道这是一个古老的话题,但是我发帖在这里以防其他人来这里寻找这个问题的答案(就像我一样)。

从技术上讲,是的,可能 - 但是你用“胶水代码”的 ton ,还有一点点JavaScript(哪种类型的失败了目的IMO)。例如:

#include <emscripten.h>
#include <string>

#define DIV 0
#define SPAN 1
#define INPUT 2
// etc. etc. etc. for every element you want to use

// Creates an element of the given type (see #defines above)
// and returns the element's ID
int RegisterElement(int type)
{
    return EM_ASM_INT({
        var i = 0;
        while (document.getElementById(i))
            i++;
        var t;
        if ($0 == 0) t = "div";
        else if ($0 == 1) t = "span";
        else if ($0 == 2) t = "input";
        else
            t = "span";
        var test = document.createElement(t);
        test.id = i;
        document.body.appendChild(test);
        return i;
    }, type);
}

// Calls document.getElementById(ID).innerHTML = text
void SetText(int ID, const char * text)
{
    char str[500];
    strcpy(str, "document.getElementById('");
    char id[1];
    sprintf(id, "%d", ID);
    strcat(str, id);
    strcat(str, "').innerHTML = '");
    strcat(str, text);
    strcat(str, "';");
    emscripten_run_script(str);
}

// And finally we get to our main entry point...
int main()
{
    RegisterElement(DIV);    // Creates an empty div, just as an example
    int test = RegisterElement(SPAN);    Creates an empty SPAN, test = its ID
    SetText(test, "Testing, 1-2-3");    Set the span's inner HTML
    return 0;    And we're done
}

我有同样的问题并提出了这个解决方案,它按预期编译和工作。但我们基本上是在构建一个C / C ++ API,只是为了做“开箱即用”的JavaScript。不要误解我的意思 - 从语言的角度来看,我每天都会使用C ++而不是JavaScript - 但我不禁认为这样的设置中涉及的开发时间和可能的性能问题是不值得的。如果我打算用C ++做一个Web应用程序,我肯定会使用Cheerp(Duetto的新名称)。

答案 1 :(得分:0)

正如有人已经指出的那样,如果你开始专门为网络提供新的代码库,那么duetto可能是一个解决方案。但在我看来,duetto有很多缺点,比如没有C分配器,如果你想使用第三方库,可能会很难。

如果您使用的是emscripten,它会为各种DOM事件提供API,这几乎完全符合您的要求。

emscripten_set_click_callback(const char *target, void *userData, int useCapture, int (*func)(int eventType, const EmscriptenMouseEvent *mouseEvent, void *userData));

希望这会有所帮助