見出し画像

Notes C API探訪: ITEM_TABLEラップクラス

「サマリーバッファ」は、ビューの行や、検索結果のような、文書をオープンせずにデータを取得できるデータの集まりで、そのサマリーバッファを操作するための起点が「ITEM_TABLE構造体」です。ITEM_TABLE構造体についてはこちらの記事こちらの記事で説明しています。

同じサマリーバッファでも、API関数によって「名前付きサマリーバッファ」を返すか、「名前なしサマリーバッファ」を返すかが変わってきます。「名前付きサマリーバッファ」はstd::mapのようなキーバリュー型、「名前なしサマリーバッファ」はstd::vectorのようなリスト型のコンテナと言えます。

今回は、ITEM_TABLE構造体ポインタを元に生成するnxpp::NamedItemTableクラスを紹介します。

nxpp::NamedItemTable

NamedItemTableクラスは、ITEM_TABLE構造体ポインタを使って生成し、サマリーバッファが持つ「名前」をあらかじめ取得しておくことで、名前に紐付くデータにアクセスしやすくします。

// nxpp/include/nxpp_itemtable.hpp

#ifndef NXPP_ITEMTABLE_HPP
#define NXPP_ITEMTABLE_HPP

#include "./nxpp_variant.hpp"
#include <vector>

#ifdef NT
#pragma pack(push, 1)
#endif

#include <global.h>
#include <nsfnote.h>

#ifdef NT
#pragma pack(pop)
#endif

namespace nxpp {

/**
* @brief 名前付きサマリーバッファクラス
*/
class NamedItemTable
{
 ITEM_TABLE *pTable_; ///< テーブルポインタ
 std::vector<Lmbcs> names_; ///< 名前リスト

public:
 /**
  * @brief コンストラクタ
  * @param pTable ITEM_TABLE構造体ポインタ
  */
 NamedItemTable(ITEM_TABLE *pTable)
   : pTable_(pTable)
   , names_()
 {
   // 先頭のITEMポインタを取得
   ITEM *pItem = reinterpret_cast<ITEM*>(pTable_ + 1);

   // 先頭の名前ポインタを取得
   char *pName = reinterpret_cast<char*>(pItem + pTable_->Items);

   // アイテム数分の巡回
   for (USHORT i = 0; i < pTable_->Items; ++i) {

     // 現在のアイテム名を取得
     auto name = Lmbcs(pName, pItem->NameLength);

     // 名前リストに追加
     names_.push_back(name);

     // 名前ポインタを次にアイテム名に移動
     pName += pItem->NameLength + pItem->ValueLength;

     // 次のITEMポインタに移動
     pItem += 1;
   }
 }

 /**
  * @brief 名前リストを取得
  * @return
  */
 const std::vector<Lmbcs> &names() const { return names_; }

 /**
  * @brief 名前に対応した値をVariantで取得
  * @param name アイテム名
  * @return アイテム値
  */
 Variant value(const Lmbcs &name) const {
   return value(pTable_, name);
 }

 /**
  * @brief 名前に対応した値をVariantで取得
  * @param pTable テーブルポインタ
  * @param name アイテム名
  * @return アイテム値
  */
 static Variant value(ITEM_TABLE *pTable, const Lmbcs &name) {
   char *pValue = nullptr;
   WORD len = 0, type = 0;
   if (NSFLocateSummaryValue(
         pTable,
         name.c_str(),
         &pValue,
         &len,
         &type
         )) {
     return Variant(type, pValue, len);
   }
   return Variant();
 }
};

} // namespace nxpp

#endif // NXPP_ITEMTABLE_HPP

このクラスは、ITEM_TABLE構造体ポインタを取得しますが、ポインタが指すメモリを解放する責務は負いません。ゆくゆくは実装するかもしれませんが、その時はアップデートします。
名前のリストはnamesメソッドで取得します。
値を取得する時はvalueメソッドを使います。インスタンスメソッドでは保持するポインタを使い、クラスメソッドでは直接ポインタを指定することができます。名前がわかっている場合はインスタンスを作らずにこちらを使用した方がいいでしょう。値の取得にはNSFLocateSummaryValue API関数を使用します。取得した値は、前回紹介したnxpp::Variantとして返します。

まとめ

前回のVariantと、今回のNamedItemTableは、次回紹介予定のNSFSearch関数ラップクラスの布石になります。

この記事が気に入ったらサポートをしてみませんか?