ESTUDO COMPARATIVO DE BIBLIOTECAS GRÁFICAS ITEGRADAS COM OPEGL Francisco Tiago Avelar, Vitor Conrado F. Gomes, Cesar Tadeu Pozzer Universidade Federal de Santa Maria – UFSM Curso de Ciência da Computação – Santa Maria - RS [email protected], [email protected], [email protected] Resumo. Este trabalho envolve um estudo de bibliotecas gráficas para o desenvolvimento de aplicações baseadas em janelas incorporados com OpenGL. Em função disso, será feito um panorama e um comparativo das principais APIs escritas em C/C++. Da mesma forma, serão utilizados alguns critérios, como o suporte a sistemas operacionais Windows e Linux, disponibilidade de documentação e facilidade de uso. Outros fatores levados em conta incluem simplicidade quanto à compilação e as dependências de pacotes, além de outros aspectos. Ao final será realizada uma conclusão de quais bibliotecas gráficas apresentam as melhores características para criação de programas gráficos. Palavras-chave: API, OpenGL, C++. 1. ITRODUÇÃO A evolução das interfaces das aplicações acompanha de perto a evolução da computação. Interfaces textuais, como as existentes em sistemas operacionais, como o MS-DOS e UNIX, deram lugar a interfaces gráficas orientadas a janelas. Cada sistema possui peculiaridades que são nativas, tornando específica a programação para cada plataforma. Neste aspecto, a linguagem Java surgiu como unificação entre aplicações gráficas independentes de plataforma de execução, permitindo que o código possa ser executado em qualquer ambiente sem que sejam realizadas alterações. São exemplos os pacotes gráficos Java AWT e Java Swing. Por meio desses, pode-se criar interfaces gráficas que oferecem recursos de interação com eventos e componentes gráficos. Apesar da grande utilização, a linguagem Java possui limitações de desempenho pelo fato de ser interpretada, pois não oferece acesso direto aos recursos nativos, apontando o uso de linguagens compiladas, como C++. Em função dessa tendência, a portabilidade de aplicativos passa a ser prejudicada, pois exige o conhecimento de complexas APIs de sistemas operacionais. Este artigo apresenta um estudo de caso envolvendo a escolha de APIs gráficas que utilizam a linguagem C++ de programação para geração de interfaces em ambiente multiplataforma. A organização do trabalho foi feita expondo o problema definido como foco da pesquisa. A seguir, um levantamento das principais APIs gráficas foi estabelecido ressaltando as funcionalidades de cada uma separadamente. A partir de então, uma comparação entre as APIs envolvendo aspectos positivos e negativos passou a ser determinado para que, ao final, fosse possível concluir quais bibliotecas gráficas possuem as melhores funcionalidades para o desenvolvimento de aplicações gráficas baseadas em janelas. 2. DESCRIÇÃO DO PROBLEMA Em se tratando de aplicações em Computação Gráfica para criação de rotinas gráficas de modelagem, manipulação de objetos e exibição tridimensional, a biblioteca OpenGL tornou padrão para linguagens de programação como C/C++. Além disso, foi projetada para ser independente do sistema de janelas e sistema operacional. Deste modo, não possui comandos para abertura de janelas e leitura de eventos do teclado e mouse. Para associar uma aplicação gráfica em OpenGL com eventos e sistema de janelas do sistema operacional, existe outra API, chamada GLUT (GL Utility Toolkit) cuja função é realizar a integração com o sistema local, além oferecer algumas primitivas gráficas 3D, proporcionando noções simples para criação de aplicativos gráficos. Apesar dessas funcionalidades, a GLUT é limitada em comparação com outras APIs envolvendo aplicações modernas que utilizam botões, barra de tarefas, deslizadores, menus, etc. A partir da simplicidade da GLUT, uma pesquisa envolvendo o levantamento de características das principais APIs gráficas passou a ser definido. O propósito é integrar aplicações em OpenGL com janelas gráficas aprimoradas envolvendo componentes GUI modernamente empregados nos sistemas operacionais amplamente utilizados, como Windows e Linux, e que as APIs sejam bem documentadas de modo a facilitar a compreensão no nível de hierarquia de classes e reutilização de componentes. Seguindo esses itens, quatro nomes foram identificados como sendo as principais: wxWidgets, Qt, Fox e Gtk+. Após esse levantamento primário, demais critérios passaram a ser estabelecidos no intuito de realizar uma escolha de duas APIs que melhor se enquadram para implementação de aplicativos aprimorados com OpenGL. Em se tratando do âmbito em nível de aprendizado acadêmico, mais especificamente relacionado ao curso de Computação Gráfica, fatores decisivos levaram a uma análise mais detalhada das quatro APIs identificadas, focando mais especificamente no nível de compreensão do código-fonte e nas diretivas de compilação utilizando o compilador padrão g++. No que compete ao sistema operacional, foi necessário avaliar a viabilidade mínima de requisitos envolvendo pacotes necessários como dependências de sistema para compilação e execução de programas utilizando componentes das APIs gráficas. Além disso, diretamente relacionado à documentação e a legibilidade de código, foi verificado a confiabilidade de forma a representar o tempo de desenvolvimento do programador, assim como a utilização das bibliotecas gráficas em aplicações com maior impacto a nível industrial no desenvolvimento de soluções em computação. 3. ASPECTOS DAS BIBLIOTECAS GRÁFICAS Através do levantamento realizado sobre as APIs gráficas e a escolha de quatro com as melhores características, uma descrição envolvendo funcionalidades passa a ser estabelecida de forma a explorar o aspecto do desenvolvimento de aplicativos integrados com OpenGL. O panorama remete as principais características envolvendo o diferencial de cada biblioteca gráfica, de modo a ressaltar as potencialidades na criação de programas principalmente voltado à criação de componentes gráficos e ao tratamento de eventos de usuário. 3.1 Gtk+ A API GTK+ [1] foi criada para ser usada pelo GIMP e por isso é chamado de GIMP Toolkit. Essa API integra o projeto GNU, sendo escrita em C com design orientado a objetos. Para este trabalho foi utilizada a GTKMM que é sua interface para C++. Nessa API, o tratamento de eventos é realizado através da emissão de sinais pelo componente que sofreu interação. O tratador de sinais é responsável por chamar a função apropriada. A conexão dos tratadores de sinais com os componentes é feita através de métodos específicos, por exemplo, no caso dos botões pelos métodos signal_pressed, signal_released, entre outros. É organizada através da utilização de namespaces, que fazem o agrupamento lógico dos componentes por categoria. Apesar de Gtk ser multiplataforma, as aplicações não possuem a aparência nativa de cada sistema, sendo única para todos. É importante observar que esta API não possui suporte a OpenGL, sendo esse suprido pela utilização da biblioteca gtkglextmm que se integra perfeitamente ao GTKMM. 3.2 WxWidgets A wxWidgets [2] possui como importante característica o seu funcionamento como uma abstração para o código nativo de manipulação de janelas para cada sistema operacional. Isso permite, com um único código fonte, obter-se versões do programa para sistemas diferentes e com a própria aparência do ambiente. A API faz notavelmente o uso do recurso de macros C++ para facilitar a codificação dos programas. Um exemplo é a ausência explícita da função main em programas que utilizam a wxWidgets, explicado pelo uso da macro IMPLEMENT_APP, a qual indica à API como criar uma instância da aplicação. Além disso, para a vinculação de eventos aos componentes gráficos são criadas tabelas de associações de funções e identificadores totalmente implementadas através do uso de macros. A simplificação para a criação dos componentes gráficos, que pode ser feito através da definição de uma instância da classe correspondente, permite que programas que utilizem esta API possam ter um código legível e de fácil implementação. Essa API é desenvolvida sobre a GTK+ para a sua utilização em sistemas Linux, caracterizando ainda mais sua característica de camada sobre a interface gráfica. 3.3 Qt A API gráfica Qt [3] apresenta uma vasta coleção de classes e suporte a OpenGL. Para fazer emprego mínimo de macros em C++, Qt faz uso de uma extensão que vincula uma classe com eventos de usuário. Em função disso, o cabeçalho de cada classe, além de possuir o protótipo para os eventos da classe, deve incluir obrigatoriamente a macro Q_OBJECT especificada por Qt. Através do utilitário MOC [4], cada cabeçalho contendo a macro é lida com o propósito de gerar um metacódigo em C++ contendo componentes específicos de Qt para mapear as classes com seus eventos. A partir disso, a fonte criada por MOC passa a ser compilada e ligada com o restante da implementação usual de classe. Apesar do mecanismo interno de templates em C++, a justificativa [5] de Qt em utilizar esse programa intermediário para mapeamento das classes com seus eventos está voltada a oferecer ao desenvolvedor uma maneira simplificada de programar através de uma sintaxe clara para criação e manutenção de código. Além disso, muitos compiladores da linguagem C++ apresentam problemas com templates avançados para ambientes multiplataforma e nem todas as questões pertinentes envolvendo interfaces gráficas podem ser resolvidas. Um vetor genérico é facilmente expressível mesmo com a especialização parcial de tipos ponteiros. Por outro lado, uma funçãomembro que constrói uma interface gráfica baseada num descritor XML dado como uma cadeia de caracteres não é simplesmente tratada utilizando templates. 3.4 Fox A API Fox [6] foi inicialmente desenvolvida para Linux, mas as versões mais recentes estão voltadas para executar em modo multiplataforma. Possui uma grande quantidade de componentes gráficos e apresenta uma forma simplificada de associação de classes com seus eventos através de identificadores por enumeração. Uma das características principais é a abordagem simplificada para construção de interfaces gráficas através da forma concisa na criação de componentes. Através de uma única linha de código na instância de uma classe, Fox auxilia na criação de muitos componentes gráficos. Para que essa característica seja possível, a funcionalidade da atribuição padrão de parâmetros para argumentos em C++ é extensivamente utilizada, resultando na redução no emprego de vários métodos que manipulam um único componente, evitando a presença de várias linhas de código no cumprimento de uma mesma especificação. 4. AÁLISE ETRE AS BIBLIOTECAS GRÁFICAS A partir da descrição envolvendo as características e recursos relativos a cada biblioteca gráfica, o próximo passo foi realizar um confronto ressaltando as propriedades relacionadas aos critérios adotados na pesquisa de acordo com os fatores decisivos especificados na descrição do problema. Através da criação de aplicações demonstrativas utilizando cada API gráfica, um maior contato com o desenvolvimento de programas gráficos com cada biblioteca gráfica foi possível de modo a trazer mais próximo do uso prático. Uma das grandes vantagens de Qt é a excelente documentação contendo exemplos na utilização de diversas classes. A API wxWidgets compartilha dessa característica facilitando a criação de componentes e eventos de forma rápida e simplificada. Em contrapartida, o núcleo de Qt ocupa maior espaço em disco devido à grande hierarquia de classes. Em se tratando de chamadas para compilação, o utilitário Qmake é incluído como componente de Qt para automatizar a criação de Makefile. Embora esse encapsulamento na criação das diretivas de compilação possa oferecer uma comodidade ao programador, a dependência passa a ser maior na compilação de aplicativos gráficos. Esse aspecto contraria o ideal de aplicar diretivas simples de compilação através do entendimento claro do uso das bibliotecas de Qt com as dependências do sistema operacional, pois o Makefile criado de forma automática por Qmake é complexo, principalmente devido à organização interna de Qt e a integração do meta-código gerado pelo utilitário MOC para vinculação de classes com tratamento de eventos. Nesse aspecto, Qt é classificado como uma exceção de complexidade, pois as demais bibliotecas gráficas apresentam comportamento satisfatório para criação de Makefile simplificados. A wxWidgets possui uma notável vantagem em relação à GTK+ devido à simplicidade na criação dos componentes gráficos, permitindo, através da instância da classe, tenha-se um componente já funcional. Essa propriedade também é explorada extensivamente em Fox e Qt, assim o caso de utilizar atribuições padrão no construtor de classe para criação de componentes gráficos facilita o emprego de menos linhas para criação de um código mais condensado. Para a implementação de alguns recursos, como a vinculação de eventos a componentes, wxWidgets faz o uso intensivo de macros do C++, acarretando em simplicidade na codificação. Apesar desse emprego reunindo rotinas em forma de macros, a legibilidade de código passa a ser comprometida de forma a não oferecer uma forma mais transparente para o programador. Em contrapartida, o aspecto positivo é a inexistência de um utilitário próprio para associar uma classe com tratamento de eventos, fato que não ocorre em Qt, oferecendo maior entendimento na compilação de programas. Pelo fato de Gtk+ ser mais difundida em ambiente Linux, principalmente através do propósito de ter sido criada inicialmente para o aplicativo GIMP de edição de imagens; e Fox ter sido desenvolvida inicialmente para esse sistema, as dependências são menores, contribuindo na redução de espaço adicional em memória secundária, diferentemente de wxWidgets, cujo espaço passa a ser maior devido a incluir uma biblioteca própria de abstração para acesso de rotinas utilizando componentes Gtk+. Entretanto, em se tratando execução em ambiente Windows, GTK+ exige, além de maior espaço de armazenamento em disco, uma camada de execução adicional responsável pela renderização de janelas de modo a desempenhar um papel de simular um ambiente próprio de forma a ser compatível com o sistema gráfico nativo. Esta característica singular dentre as APIs analisadas faz com que os programas que utilizam Gtk+ tenham o mesmo visual em todas as plataformas, apresentando comportamento diferenciado das demais APIs, nas quais a aparência é nativa do sistema operacional. 5. COSIDERAÇÕES FIAIS Tendo em posse a descrição e comparação das quatro bibliotecas gráficas, a escolha de duas que apresentaram as melhores características para criação de aplicativos gráficos integrados com OpenGL fica melhor constatado, em se tratando do domínio do curso de Computação Gráfica. Dessa forma, as bibliotecas gráficas que melhor apontam características positivas são wxWidgets e Qt. Apesar dos aspectos observados sobre as características das duas APIs escolhidas, é possível afirmar que ambas possuem vantagens no ponto de vista da existência de uma documentação bastante completa e explicativa, facilitando o desenvolvimento de programas. Embora a dificuldade existente em Qt para criar chamadas simples para compilação, a estratégia foi isolar os pacotes de núcleo em Qt de modo a compor uma forma explícita de chamada de Makefile, desvinculando o uso de Qmake pelo programador. Seguindo o mesmo propósito, wxWidgets é mais simplificado para desenvolvimento de programas, pois possui pacotes de núcleo com menor tamanho de armazenamento em disco, além de oferecer maior autonomia para criação em chamadas de compilação. O ideal estabelecido foi trabalhar em dois alicerces, ou seja, fazer uso de Qt que emprega menor quantidade de macros, muito embora utilize um utilitário externo MOC não padrão de C++ para vincular classes com tratamento de eventos, ao passo da adoção de wxWidgets como abordagem mais independente de utilitários incorporados por API, mesmo existindo maior emprego de macros no desenvolvimento de aplicação gráfica. A partir deste trabalho, o próximo passo será disponibilizar, através da Internet, tutoriais explicativos envolvendo a utilização das APIs gráficas escolhidas contendo exemplos demonstrativos práticos. Dessa forma, passa a ser melhor aplicável no âmbito do curso de Computação Gráfica no desenvolvimento mais facilitado de aplicações gráficas integradas com OpenGL. REFERÊCIAS [1] GTK+ - the GIMP Toolkit, Disponível em: <http://www.gtk.org>. Acesso em 14 ago. 2007. [2] wxWidgets, Disponível em: <http://www.wxwidgets.org>. Acesso em 16 ago. 2007. [3] Website biblioteca gráfica Qt. Disponível em <http://trolltech.com/products/qt>. Acesso em 15 ago. 2007. [4] Utilizando o Meta-object Compiler (MOC). Disponível em <http://doc.trolltech.com/4.0/moc.html>. Acesso em 15 ago. 2007. [5] Aspectos de Qt para tratar classes com eventos. Disponível em <http://doc.trolltech.com/4.0/templates.html >. Acesso em 15 ago. 2007. [6] Website biblioteca gráfica Fox. Disponível em <http://www.foxtoolkit.org/>. Acesso em 16 ago. 2007.