C++ Language Binding

From Apache OpenOffice Wiki
< Zh‎ | Documentation
Revision as of 02:47, 14 May 2009 by Jirong (Talk | contribs)

Jump to: navigation, search




本节介绍 UNO C++ 语言绑定。它为有经验的 C++ 程序员提供使用 UNO 的最初步骤:建立与远程 OpenOffice.org 的 UNO 进程间连接以及使用远程 StarSuite 的 UNO 对象。


程序库概述

此插图给出了 UNO 组件模型的核心程序库的概述。

C++ UNO 的共享库


可以在安装 {PRODUCTNAME}} 的 <officedir>/program 文件夹中找到这些共享库。上面插图中的标签 (C) 表示 C 链接,而 (C++) 表示 C++ 链接。所有程序库都需要一个 C++ 编译器来进行编译。


所有 UNO 程序库的基础是 sal 程序库。sal 程序库包含系统抽象层 (sal) 和附加的运行时库功能,但不包含任何 UNO 特有的信息。可以通过 C++ 内联包装类访问 sal 程序库中的常用 C 函数。这样,就可以从任何其他编程语言调用函数,因为多数编程语言都具有某种调用 C 函数的机制。


salhelper 程序库是一个小型 C++ 程序库,提供无法通过内联方式实现的附加运行时库功能。


cppu (C++ UNO) 程序库是核心 UNO 程序库。它提供访问 UNO 类型库的方法,并允许以普通方式建立、复制和比较 UNO 数据类型的值。另外,还在此库中管理所有 UNO 桥(= 映射 + 环境)。


示例 msci_uno.dlllibsunpro5_uno.solibgcc2_uno.so 只是某些 C++ 编译器语言绑定库的示例。cppuhelper 程序库是一个 C++ 程序库,包含 UNO 对象的重要基类以及用于引导 UNO 核心的函数。C++ 组件和 UNO 程序必须链接 cppuhelper 程序库。


在 UNO 的所有未来版本中,将保持与上面显示的所有程序库的兼容。您将能够一次构建并链接应用程序和组件,并能够使用 {PRODUCTNAME}} 的当前和以后版本进行运行。


系统抽象层

C++ UNO 客户机程序和 C++ UNO 组件在类型、文件、线程、进程间通信和字符串处理中使用系统抽象层 (sal)。sal 程序库将与操作系统相关的功能作为 C 函数进行提供。目的是最大限度地减少或消除 sal 上面的程序库中与操作系统相关的 #ifdef。sal 提供高性能访问,因为 sal 是每个操作系统提供的位于 API 之上的一个薄层。 Template:Documentation/Note

Sal exports only C symbols. The inline C++ wrapper exists for convenience. Refer to the UNO C++ reference that is part of the OpenOffice.org SDK or in the References section of udk.openoffice.org to gain a full overview of the features provided by the sal library. In the following sections, the C++ wrapper classes will be discussed. The sal types used for UNO types are discussed in section Type Mappings. If you want to use them, look up the names of the appropriate include files in the C++ reference.

sal 仅导出 C 图标。为了方便起见,提供了内联 C++ 包装。如果需要全面了解 sal 程序库提供的功能,请参阅 StarSuite SDK 中的 UNO C++ 引用或 udk.openoffice.org 上的“引用”部分。下面几节将讨论 C++ 包装类。专业 UNO - UNO 语言绑定 - C++ 语言绑定 - 类型映射 中讨论了用于 UNO 类型的 sal 类型。如果要使用它们,请在 C++ 引用中查找相应的包含文件的名称。


文件访问

下面列出的类管理与平台无关的文件访问。它们属于内部调用相应 C 函数的 C++ 类。

  • osl::FileBase
  • osl::VolumeInfo
  • osl::FileStatus
  • osl::File
  • osl::DirectoryItem
  • osl::Directory

一个不熟悉的概念是在整个 API 内使用绝对文件名。在一个多线程程序中,不能依赖于当前工作目录,因此,必须由调用程序明确地将相对路径变成绝对路径。


T线程安全的引用计数

全局 C++ 命名空间中的函数 osl_incrementInterlockedCount()osl_decrementInterlockedCount() 以线程安全方式增加和减少一个 4 字节计数器。引用计数的对象需要此计数器。许多 UNO API 通过引用计数控制对象的生存期。由于并行递增的同一计数器不会可靠地增加引用计数,因此应该使用这些函数。对于大多数平台来说,这比使用互斥体快。


线程和线程同步

类 osl::Thread 可用作您自己线程的基类。改写 run() 方法。

下面的类是常用的同步基元:

  • osl::Mutex
  • osl::Condition
  • osl::Semaphore


套接字和管道

下面的类使您可通过一种与平台无关的方式使用进程间通信:

  • osl::Socket
  • osl::Pipe


字符串

类 rtl::Ostring(8 位,已编码)和 rtl::OUString(16 位,UTF-16)是 UNO 程序的字符串基类。字符串将其数据存储在一个堆内存块中。字符串执行引用计数,而且不能更改,因而使复制更快,而且创建是一项昂贵的操作。可以使用静态函数 OUString::createFromASCII() 创建一个 OUString,也可以从使用以下构造函数进行编码的 8 位字符串进行构造:

 OUString( const sal_Char * value, 
          sal_Int32 length, 
          rtl_TextEncoding encoding, 
          sal_uInt32 convertFlags = OSTRING_TO_OUSTRING_CVTFLAGS ); 


可以将 OUString 转换为一个 8 位字符串,例如,对于 printf(),使用 rtl::OUStringToOString() 函数,它采用某种编码,如 RTL_TEXTENCODING_ASCII_US。


为了进行快速字符串连接,应该使用 'rtl::OStringBuffer 和 rtl::OUStringBuffer,因为它们提供了连接字符串和数字的方法。准备好新字符串缓冲区之后,请使用 makeStringAndClear() 方法建立新的 OUString OString。以下示例对此进行了说明:

 sal_Int32 n = 42;
 double pi = 3.14159;
 
 // create a buffer with a suitable size, rough guess is sufficient
 // stringbuffer extends if necessary
 OUStringBuffer buf( 128 );
 
 // append an ascii string
 buf.appendAscii( "pi ( here " );
 
 // numbers can be simply appended 
 buf.append( pi );
 // RTL_CONSTASCII_STRINGPARAM()
 // lets the compiler count the stringlength, so this is more efficient than
 // the above appendAscii call, where the length of the string must be calculated at
 // runtime
 buf.appendAscii( RTL_CONSTASCII_STRINGPARAM(" ) multiplied with " ) );
 buf.append( n );
 buf.appendAscii( RTL_CONSTASCII_STRINGPARAM(" gives ") );
 buf.append( (double)( n * pi ) );
 buf.appendAscii( RTL_CONSTASCII_STRINGPARAM( "." ) );
 
 // now transfer the buffer into the string.
 // afterwards buffer is empty and may be reused again !
 OUString string = buf.makeStringAndClear();
 
 // You could of course use the OStringBuffer directly to get an OString
 OString oString = rtl::OUStringToOString( string , RTL_TEXTENCODING_ASCII_US );
 
 // just to print something 
 printf( "%s\n" ,oString.getStr() );


Content on this page is licensed under the Public Documentation License (PDL).
Personal tools
In other languages