2011-07-16 14 views
4

Visual C++で基本的な文字列テーブルリソースを作成しました。私はそのリソースにアクセスしようとしています。しかし、私のプログラムはリソースを見つけることができません。ここでは:Visual C++ 2010でリソース文字列を開く方法は?

int main(int argc, char* argv[]) 
{ 
    HRSRC hRsrc; 
    hRsrc = FindResource(NULL, MAKEINTRESOURCE(IDS_STRING102), RT_STRING); 
    if (hRsrc == NULL) { 
     printf("Not found\n"); 
    } else { 
     printf("Found\n"); 
    } 
} 

このプログラムはリソースを見つけることができず、常にnullを返します。

私は単純なビットマップリソースを作成しましたが、この新しいプログラムはちょうど良いことを識別します。ここで:

int main(int argc, char* argv[]) 
{ 
    HRSRC hRsrc; 
    hRsrc = FindResource(NULL, MAKEINTRESOURCE(IDB_BITMAP1), RT_BITMAP); 
    if (hRsrc == NULL) { 
     printf("Not found\n"); 
    } else { 
     printf("Found\n"); 
    } 
} 

これはビットマップを検索します。

文字列型リソースは何らかの形で処理されますか?

答えて

2

代わりにLoadStringを直接使用できます。ここでは、MSDN FindResourceドキュメントからいくつかのテキストは、アプリケーションがリソースのいずれかのタイプを見つけることにfindResourceを使用することができますが、アプリケーションは後続の呼び出しにすることによって、バイナリリソースデータにアクセスする必要がある場合にのみ、この機能を使用する必要があります...

ですLoadResourceに、次にLockResourceに渡します。

... loadStringはを使用して...すぐにリソースを使用するには! findResource()とFindResourceExを使用している場合

文字列と文字列のテーブルが実際に異なる方法で処理され

+2

' MAKEINTRESOURCE((IDS_STRING102> > 4)+1) 'となる。 'LoadString'を使うのがずっと簡単です...'FindResource'は直感的な文字列読み込みのために作られたものではありません。 :( – Ben

5

あなたはこれが役立つはずです)(loadStringはを使用したくないと仮定すると...()。 this KB記事:

文字列リソースは文字列のブロックとして格納されます。各ブロックは までの16個の文字列を持つことができ、ロード/更新できる文字列リソースの最小単位は です。各ブロックは、識別子(ID)によって1つ(1)で始まり、 と識別されます。 FindResource、LoadResource、およびUpdateResource関数を呼び出す場合は、 というIDを使用します。

IDを持つ文字列、nStringIDは、次式で与え nBlockID、IDとブロック内に配置されている:

nBlockID =(nStringID/16)+ 1。 //整数の除算を書き留めます。

nStringIDの下位4ビットは、ブロック内のどのエントリに実際の文字列が含まれているかを示します。 FindResource()に渡すブロックIDと、文字列が存在するブロックのインデックスを計算したら、その文字列をスキャンして、探している文字列を見つけなければなりません。

次のコードを使用してください。

const WCHAR *stringPtr; 
WCHAR stringLen; 

// Get the id of the string table block containing the target string 
const DWORD blockID = (nID >> 4) + 1; 

// Get the offset of teh target string in the block 
const DWORD itemID = nID % 0x10; 

// Find the resource 
HRSRC hRes = FindResourceEx(
    hInst, 
    RT_STRING, 
    MAKEINTRESOURCE(blockID), 
    wLanguage); 
if (hRes) 
{ 
    HGLOBAL hBlock = LoadResource(hInst, hRes); 
    const WCHAR *tableDataBlock = reinterpret_cast<LPCWSTR>(LockResource(hBlock)); 
    const DWORD tableBlockSize = SizeofResource(hInst, hRes); 
    DWORD searchOffset = 0; 
    DWORD stringIndex = 0; 

    // Search through the section for the appropriate entry. 
    // The first two bytes of each entry is the length of the string 
    // followed by the Unicode string itself. All strings entries 
    // are stored one after another with no padding. 
    while(searchOffset < tableBlockSize) 
    { 
     if (stringIndex == itemID) 
     { 
      // If the string has size. use it! 
      if (tableDataBlock[searchOffset] != 0x0000) 
      { 
       stringPtr = &tableDataBlock[searchOffset + 1]; 
       stringLen = tableDataBlock[searchOffset]; 
      } 
      // Nothing there - 
      else 
      { 
       stringPtr = NULL; 
       stringLen = 0; 
      } 

      // Done 
      break; 
     } 

     // Go to the next string in the table 
     searchOffset += tableDataBlock[searchOffset] + 1; 

     // Bump the index 
     stringIndex++; 
    } 
} 
0

研究の2日間は、私は(それが動作!)これを見つけた後:あなたは、あなたがIDを渡す必要がある文字列に `FindResource`を使用する必要がある場合

#include <atlstr.h> 

...... 

ATL::CString str; 
WORD LangID = MAKELANGID(LANG_ENGLISH,SUBLANG_DEFAULT); 
str.LoadString(NULL,IDS_STRING101, LangID); 
関連する問題