gvx 发表于 2011-5-19 19:53:10

請問C++高手 main.cpp 如何編譯成DLL

請問C++高手 main.cpp 如何編譯成DLL
這是fallout_font.dll的C++跟 noword 要來的,搞了老半天沒法編譯成DLL

目前繁體化問題主要在提示框文字變亂碼如下圖
對話如果太長會有第二段以上時如果有繁體字時有時會變亂碼
有強者能幫忙修改一下嗎??

main.cpp

#ifdef   __cplusplus
#define EXPORT extern "C" __declspec (dllexport)
#else
#define EXPORT __declspec (dllexport)
#endif
#include <windows.h>

#define BMP_WIDTH 640

struct font_struct
{
HFONT hFont;
char name;
int size;
int weight;
} text_font, button_font;

DWORD *g_pBits;
HDC g_Hdc;
HBITMAP g_hBmp;
LONG g_FontHeight;
LONG g_Adjust;
UINT g_CodePage;

void
GetIni ()
{
char ini_name;
GetModuleFileName (NULL, ini_name, MAX_PATH);
*(strrchr (ini_name, '\\') + 1) = 0;
strcat (ini_name, "fallout_font.ini");

GetPrivateProfileString ("TEXT", "Name", "Tahoma", text_font.name,
                           80, ini_name);
text_font.size = GetPrivateProfileInt ("TEXT", "Size", 11, ini_name);
text_font.weight = GetPrivateProfileInt ("TEXT", "Weight", 400, ini_name);

GetPrivateProfileString ("BUTTON", "Name", "黑體", button_font.name,
                           80, ini_name);
button_font.size = GetPrivateProfileInt ("BUTTON", "Size", 20, ini_name);
button_font.weight =
    GetPrivateProfileInt ("BUTTON", "Weight", 100, ini_name);

g_Adjust = GetPrivateProfileInt ("MISC", "Adjust", 3, ini_name);

g_CodePage = GetPrivateProfileInt ("MISC", "CodePage", 0, ini_name);
if (g_CodePage==0)
{g_CodePage = GetACP();}
}

LONG
TextWidth (const char *string)
{
SIZE size;
GetTextExtentPoint32 (g_Hdc, string, lstrlen (string), &size);
return size.cx;
}

int
RepFrontDot (char *string)
{
int len = lstrlen (string);
if ((unsigned char) *string == 0x95)
    {
      for (int i = len; i >= 1; i--)
      {
          string = string;
      }
      //●
      string = 0xa1;
      string = 0xf1;
      len += 2;
    }
return len;
}

EXPORT void
InitFont ()
{
//create HDC
g_Hdc = CreateCompatibleDC (NULL);

//create font
text_font.hFont =
    CreateFont (-text_font.size, 0, 0, 0, text_font.weight, FALSE,
                FALSE, FALSE,
                DEFAULT_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, ANTIALIASED_QUALITY,
                VARIABLE_PITCH | FF_DONTCARE, text_font.name);
button_font.hFont =
    CreateFont (-button_font.size, 0, 0, 0, button_font.weight, FALSE, FALSE,
                FALSE, DEFAULT_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS,
                ANTIALIASED_QUALITY, VARIABLE_PITCH | FF_DONTCARE, button_font.name);

//create bitmap
BITMAPINFO bmi;
ZeroMemory (&bmi.bmiHeader, sizeof (BITMAPINFOHEADER));
bmi.bmiHeader.biSize = sizeof (BITMAPINFOHEADER);
bmi.bmiHeader.biWidth = BMP_WIDTH;
bmi.bmiHeader.biHeight = -max (button_font.size, text_font.size) * 1.5;
bmi.bmiHeader.biPlanes = 1;
bmi.bmiHeader.biBitCount = 32;
bmi.bmiHeader.biCompression = BI_RGB;
g_hBmp =
    CreateDIBSection (g_Hdc, &bmi, DIB_RGB_COLORS, (void **) &g_pBits, NULL,
                      0);

//set bmp, font, color
SelectObject (g_Hdc, g_hBmp);
SelectObject (g_Hdc, button_font.hFont);
SetTextColor (g_Hdc, RGB (255, 255, 255));
SetBkColor (g_Hdc, 0);
}

EXPORT void
ClearFont ()
{
DeleteObject (g_hBmp);
DeleteObject (text_font.hFont);
DeleteObject (button_font.hFont);
DeleteDC (g_Hdc);
}


EXPORT int
TextOutput (char *string, int string_width, int screen_width, BYTE * dest,
            BYTE color)
{/*
for (int i=0;i<=256;i++)
{
      dest=i;
}
return 0;*/
SIZE size;
BYTE smooth_color = color + 1;
int len = RepFrontDot (string);

while (true)
    {
      GetTextExtentPoint32 (g_Hdc, string, len, &size);
      if (size.cx < string_width * 1.7)
      break;
      len--;
    }

TextOut (g_Hdc, 0, 0, string, len);
bool is_emptyline = true;
for (int i = 0; i < size.cy; i++)
    {
//      bool margin=true;
      for (int j = 0; j < size.cx; j++)
      {
          if (g_pBits != 0)
            {
/*            if (margin && g_pBits!=0 && color>16)
            {
                *dest = color-1;
                margin=false;
            }
            else if(g_pBits != 0 && color>16)
            {
                  *dest=color-1;
                  margin=true;
            }
            else*/
            {*dest=color;}
            is_emptyline = false;
            }
          dest++;
      }
      dest -= size.cx;
      if (!is_emptyline)
      dest += screen_width;
    }
return len;
}

EXPORT LONG
GetTextWidth (char *string)
{
RepFrontDot (string);
return TextWidth (string);
}

EXPORT LONG
GetTextHeight ()
{
DWORD ret_address;
__asm
{
mov eax, dword ptr ss:
mov ret_address, eax
};

switch (ret_address)
    {
    case 0x42bc17:
    case 0x42c0f2:
      return g_FontHeight + g_Adjust - 1;
    case 0x496cd1:
    case 0x44051a:             //對話列表
    case 0x46817a:             //交易價格
    case 0x4874f1:               //pipboy
    case 0x486ca7:               //pipboy初始化
    case 0x48924a:               //pipboy按鈕
    case 0x487534:               //pipboy橫線
    case 0x48754c:               //pipboy橫線
      return g_FontHeight + g_Adjust;
    default:
      return g_FontHeight;
    }
}

EXPORT void
SelectFont (int font)
{
if (font < 0x66)
    SelectObject (g_Hdc, text_font.hFont);
else
    SelectObject (g_Hdc, button_font.hFont);

SIZE size;
GetTextExtentPoint32 (g_Hdc, "啊g", 3, &size);
g_FontHeight = size.cy;
if (font == 0x65)
    g_FontHeight -= g_Adjust;
}

EXPORT int
SplitText (const char *string, WORD * split_pos, WORD * split_count,
         LONG width)
{
int len = lstrlen (string);

split_pos = 0;
width-=text_font.size;

if (TextWidth (string) <= width)
    {
      *split_count = 2;
      split_pos = len;
    }
else
    {
      *split_count = 1;
      WCHAR *wstring = new WCHAR;
      int lenW = MultiByteToWideChar (g_CodePage, 0, string, -1, wstring, len + 1);
      int linewidth = 0;
      int j = 0;
      for (int i = 0; i < lenW; i++)
      {
          if (wstring > 0x80)
            {
            linewidth += text_font.size;
            j += 2;
            }
          else
            {
            SIZE size;
            GetTextExtentPoint32W (g_Hdc, wstring + i, 1, &size);
            linewidth += size.cx;
            j++;
            }
          if (linewidth > width)
            {
            //roll back
            do
                {
                  j--;
                  if (wstring > 0x80)
                  {
                      j--;
                  }
                  i--;
                  if (i == 0)
                  return 1;
                }
            while (wstring <= 0x80 && wstring != 0x20);
            split_pos[*split_count] = j;
            (*split_count)++;
            linewidth = 0;
            }
      }
      split_pos[*split_count] = len;
      (*split_count)++;

      delete[]wstring;
    }
return 0;
}

EXPORT void
TextOutputL (char *string, int string_width, int screen_width, int *line,
             BYTE * dest, BYTE color)
{
RepFrontDot (string);
if (string_width - text_font.size * 2 > 0)
    {
      string_width -= text_font.size * 2;
    }
if (TextWidth (string) <= string_width)
    {
      BYTE *dest_tmp =
      dest + (*line) * screen_width * (GetTextHeight () + g_Adjust - 1);
      TextOutput (string, string_width, screen_width, dest_tmp, color);
      (*line)++;
    }
else
    {
      int len = strlen (string);
      WCHAR *wstring = new WCHAR;
      int lenW = MultiByteToWideChar (g_CodePage, 0, string, -1, wstring, len + 1);
      int linewidth = 0;
      int head = 0, tail = 0;
      for (int i = 0; i < lenW; i++)
      {
          if (wstring > 0x80)
            {
            linewidth += text_font.size;
            tail += 2;
            }
          else
            {
            SIZE size;
            GetTextExtentPoint32W (g_Hdc, wstring + i, 1, &size);
            linewidth += size.cx;
            tail++;
            }
          if (linewidth > string_width)
            {
            //roll back
            do
                {
                  tail--;
                  if (wstring > 0x80)
                  {
                      tail--;
                  }
                  i--;
                  if (i == 0)
                  break;
                }
            while (wstring <= 0x80 && wstring != 0x20);
            BYTE *dest_tmp =
                dest + (*line) * screen_width * (GetTextHeight () + g_Adjust -
                                                 1);
            (*line)++;
            char tmp = string;
            string = 0;
            TextOutput (string + head, string_width, screen_width, dest_tmp,
                        color);
            string = tmp;
            head = tail;
            linewidth = 0;
            }
      }
      BYTE *dest_tmp =
      dest + (*line) * screen_width * (GetTextHeight () + g_Adjust - 1);
      TextOutput (string + head, string_width, screen_width, dest_tmp, color);
      (*line)++;
      delete[]wstring;
    }
}


EXPORT int
TextOutputX (char *string, int *string_offset, RECT * rect, int screen_width,
             BYTE * dest, BYTE color)
{
RepFrontDot (string);
int string_width = rect->right - rect->left;
if (string_width - text_font.size * 2 > 0)
    {
      string_width -= text_font.size * 2;
    }
dest += screen_width * rect->top;
if (string_offset != NULL)
    string += *string_offset;

if (TextWidth (string) <= string_width)
    {
      TextOutput (string, string_width, screen_width, dest, color);
      if (string_offset != NULL)
      *string_offset = 0;
      rect->top += GetTextHeight () + g_Adjust - 1;
    }
else
    {
      int len = strlen (string);
      WCHAR *wstring = new WCHAR;
      int lenW = MultiByteToWideChar (g_CodePage, 0, string, -1, wstring, len + 1);
      int linewidth = 0;
      int head = 0, tail = 0;
      for (int i = 0; i < lenW; i++)
      {
          if (wstring > 0x80)
            {
            linewidth += text_font.size;
            tail += 2;
            }
          else
            {
            SIZE size;
            GetTextExtentPoint32W (g_Hdc, wstring + i, 1, &size);
            linewidth += size.cx;
            tail++;
            }
          if (linewidth > string_width)
            {
            //roll back
            do
                {
                  tail--;
                  if (wstring > 0x80)
                  {
                      tail--;
                  }
                  i--;
                  if (i == 0)
                  break;
                }
            while (wstring <= 0x80 && wstring != 0x20);
            //output one line
            //backup tail
            char tmp = string;
            string = 0;
            //output
            TextOutput (string + head, string_width, screen_width, dest,
                        color);
            //restore tail
            string = tmp;

            dest += screen_width * (GetTextHeight () + g_Adjust - 1);
            rect->top += GetTextHeight () + g_Adjust - 1;
            if (string_offset != NULL)
                *string_offset += tail - head;
            head = tail;
            linewidth = 0;
            if (rect->top + GetTextHeight () + g_Adjust - 1 > rect->bottom)
                break;
            } //end if (linewidth > string_width)
      } //end for
      if (rect->top + GetTextHeight () + g_Adjust - 1 < rect->bottom)
      {
          TextOutput (string + head, string_width, screen_width, dest, color);
          rect->top += GetTextHeight () + g_Adjust - 1;
          if (string_offset != NULL)
            *string_offset = 0;
      }
      delete[]wstring;
    }
    return rect->top;
}

BOOL APIENTRY
DllMain (HANDLE hModule, DWORD ul_reason_for_call, LPVOID lpReserved)
{
switch (ul_reason_for_call)
    {
    case DLL_PROCESS_ATTACH:
      GetIni ();
      break;
    case DLL_THREAD_ATTACH:
      break;
    case DLL_THREAD_DETACH:
      break;
    case DLL_PROCESS_DETACH:
      break;
    }
return TRUE;
}





小老鼠 发表于 2011-5-20 09:45:56

太深奥,一起帮你等

xfl00 发表于 2011-6-21 11:32:39

噢买噶全是英文{:3_157:}
页: [1]
查看完整版本: 請問C++高手 main.cpp 如何編譯成DLL