こんにちは。
いつもお世話になっております。
小生、只今WindowsXPSP3上で、C言語とWin32APIを使用し、BCC5.5.1でコンパイルしながら、Windowsプログラミングを勉強しています。
度々、質問させて頂き、その都度回答を頂戴し、誠に恐縮ではあるのですが、今回も質問させて下さい。
内容はLoadImage関数を利用した、タイトルバーのアイコン表示です。
以下のコードを試しても、タイトルバーにアイコンが表示されません。
かといって、色々なサイトを見、LoadIconを使用しようとして、MSDNを調べると"この関数は、LoadImage 関数に取って代わられました。"と表記されています。
#if 1
/* タイトルバーにアイコン表示 */
#include <windows.h>
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
ATOM InitApp(HINSTANCE, LPCSTR);
BOOL InitInstance(HINSTANCE, int, LPCSTR);
int WINAPI WinMain(
HINSTANCE hCurInst,
HINSTANCE hPrevInst,
LPSTR lpsCmdLine,
int nCmdShow)
{
MSG msg;
BOOL bRet;
LPCSTR szClassName = "TitleBarIcon";
if(!InitApp(hCurInst, szClassName)){
return FALSE;
}
if(!InitInstance(hCurInst, nCmdShow, szClassName)){
return FALSE;
}
while((bRet = GetMessage(&msg, NULL, 0, 0)) != 0){
if(bRet == -1){
MessageBox(NULL, "GetMessage Error", "Error", MB_OK);
break;
}
else{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int)msg.wParam;
}
//ウィンドウクラスの登録
ATOM InitApp(HINSTANCE hInst, LPCSTR szClassName)
{
WNDCLASSEX wc;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInst;
wc.hIcon = (HICON)LoadImage(
NULL,
"Linux.ico",
IMAGE_ICON,
0,
0,
LR_LOADFROMFILE | LR_DEFAULTSIZE | LR_SHARED);
wc.hCursor = (HCURSOR)LoadImage(
NULL,
MAKEINTRESOURCE(IDC_ARROW),
IMAGE_CURSOR,
0,
0,
LR_DEFAULTSIZE | LR_SHARED);
wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = (LPCSTR)szClassName;
wc.hIconSm = (HICON)LoadImage(
NULL,
MAKEINTRESOURCE(IDI_APPLICATION),
IMAGE_ICON,
0,
0,
LR_DEFAULTSIZE | LR_SHARED);
return (RegisterClassEx(&wc));
}
//ウィンドウの生成
BOOL InitInstance(HINSTANCE hInst, int nCmdShow, LPCSTR szClassName)
{
HWND hWnd;
hWnd = CreateWindow(
szClassName,
"TitleBarIcon",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
200,
200,
NULL,
NULL,
hInst,
NULL);
if(!hWnd){
return FALSE;
}
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
return TRUE;
}
//ウィンドウプロシージャ
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
switch(msg){
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return (DefWindowProc(hWnd, msg, wp, lp));
}
return 0;
}
お忙しい中、申し訳ございませんが、
先輩方、アドバイス宜しくお願い致します。
ちなみに読み込んでいるアイコンのサイズは幅、高さとも32ピクセルです。
No.4ベストアンサー
- 回答日時:
>wc.hIcon = (HICON)LoadImage(
>NULL,
>MAKEINTRESOURCE(MYICON),
>IMAGE_ICON,
>0,
>0,
>LR_LOADFROMFILE);
これで読み込みに成功しますか?
なにやらよくわからないファイル名(?)を参照しようとしている…んでしょうか。
//
// Icon resources
//
LANGUAGE LANG_JAPANESE, SUBLANG_JAPANESE_JAPAN
IDI_ICON1 ICON ".\\黒猫01.ico"
# ちなみに、ファイルサイズは766バイト。
WNDCLASSEX wcex = {0};
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style= CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc= WndProc;
wcex.cbClsExtra= 0;
wcex.cbWndExtra= 0;
wcex.hInstance= hInstance;
wcex.hIcon= (HICON)LoadImage(hInstance, MAKEINTRESOURCE(IDI_ICON1), IMAGE_ICON, 0, 0, LR_DEFAULTSIZE | LR_SHARED);
wcex.hCursor= LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground= (HBRUSH)(COLOR_WINDOW+1);
wcex.lpszMenuName= MAKEINTRESOURCE(IDC_QA5728505);
wcex.lpszClassName= szWindowClass;
だけです。
VC++2008 ExpressEditionでWin32プロジェクトを作成。
ResEditでリソースに32x32のアイコンを追加して、上記の変更(wcex.hIconの変更とwcex.hIconSmへの設定の削除、wcexのクリア)だけです。
OSが縮小したアイコンがタイトルバーに設定されました。
ご回答頂いたのに、ご返答遅くなってしまい誠に申し訳ございません。
Wr5さんのLoadImageAPIの使い方を拝見させて頂き、
色々と実験させて頂いたところ、今まで、LoadImageの第2引数にインスタンスハンドルを指定していませんでした。
こちらのソース内で、LoadImageの第2引数にインスタンスハンドルを指定すると、タイトルバー、タスクバー、Alt+Tabキーでの切り替え画面で表示したいアイコンが表示されました。
本当に沢山のアドバイス頂き、誠にありがとうございました。
また、ご返答遅れまして、誠に申し訳ございませんでした。
深く反省いたします。
No.3
- 回答日時:
ちょこっと試してみました。
32x32のみのアイコン、手元で探すのがちょっと面倒でしたのでネットで適当に探して使いました。
で、その前に確認ですが……
「タイトルバーの左上のアイコンに32x32のアイコンを(縮小されていてでも)使いたい」
ということでよいのでしょうか?
>wc.hIconSm = (HICON)LoadImage(
>NULL,
>MAKEINTRESOURCE(IDI_APPLICATION),
>IMAGE_ICON,
>0,
>0,
>LR_DEFAULTSIZE | LR_SHARED);
でも、表題の「LoadImageを使用し、タイトルバーのアイコンを表示」になっていますので…。
で、wc.hIconに設定しているアイコンではなく、
IDI_APPLICATIONのアイコンが表示されているのではないでしょうか?
# Alt+TABで表示される一覧の方では希望したアイコンが表示されているかと。
wc.hIconSmをNULLにするか、wc.hIconと同じモノを設定してみてはどうでしょう?
# 試したのはwc.hIconSmをNULLにする方法でした。
この回答への補足
ご回答頂き誠にありがとうございます。
言及されておられました、ご質問にお答えさせて頂きます。
>で、その前に確認ですが……
>「タイトルバーの左上のアイコンに32x32のアイコンを(縮小されていてでも)使いたい」
>ということでよいのでしょうか?
はい。
おっしゃる通り、タイトルバーの左上のアイコンに任意のアイコンを表示させたいのです。
># Alt+TABで表示される一覧の方では希望したアイコンが表示されているかと。
いいえ、Alt+Tabで表示した際もデフォルトのアイコンが表示されました。
># 試したのはwc.hIconSmをNULLにする方法でした。
私も試させて頂きましたが、以下に記述するように、タイトルバーのアイコンには変化はなく、タスクバーのアイコンが変更されました。
ご指摘のあったように、wc.hIconSmにwc.hIconと同じ値をセットし、コンパイルし、実行してみたところ、タスクバーのアイコンは希望のアイコンに変更されましたが、タイトルバーのアイコンは変更されませんでした。。。
以下にコードを提示します。
※リソースファイル、リソースヘッダーはmaznobuさんの箇所で書いた物と同じなので割愛させて頂きます。すいません。
#include <windows.h>
#include "ResIcon.h"
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
ATOM InitApp(HINSTANCE, LPCSTR);
BOOL InitInstance(HINSTANCE, int, LPCSTR);
int WINAPI WinMain(
HINSTANCE hCurInst,
HINSTANCE hPrevInst,
LPSTR lpsCmdLine,
int nCmdShow)
{
MSG msg;
BOOL bRet;
LPCSTR szClassName = "Window";
if(!InitApp(hCurInst, szClassName)){
return FALSE;
}
if(!InitInstance(hCurInst, nCmdShow, szClassName)){
return FALSE;
}
while((bRet = GetMessage(&msg, NULL, 0, 0)) != 0){
if(bRet == -1){
MessageBox(NULL, "GetMessage Error", "Error", MB_OK);
break;
}
else{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int)msg.wParam;
}
//ウィンドウクラスの登録
ATOM InitApp(HINSTANCE hInst, LPCSTR szClassName)
{
WNDCLASSEX wc;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInst;
wc.hIcon = (HICON)LoadImage(
NULL,
MAKEINTRESOURCE(MYICON),
IMAGE_ICON,
0,
0,
LR_LOADFROMFILE);
wc.hCursor = (HCURSOR)LoadImage(
NULL,
MAKEINTRESOURCE(IDC_ARROW),
IMAGE_CURSOR,
0,
0,
LR_DEFAULTSIZE | LR_SHARED);
wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = (LPCSTR)szClassName;
wc.hIconSm = (HICON)LoadImage(
NULL,
MAKEINTRESOURCE(MYICON),
IMAGE_ICON,
0,
0,
LR_LOADFROMFILE);
return (RegisterClassEx(&wc));
}
//ウィンドウの生成
BOOL InitInstance(HINSTANCE hInst, int nCmdShow, LPCSTR szClassName)
{
HWND hWnd;
hWnd = CreateWindow(
szClassName,
"Window",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
200,
200,
NULL,
NULL,
hInst,
NULL);
if(!hWnd){
return FALSE;
}
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
return TRUE;
}
//ウィンドウプロシージャ
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
switch(msg){
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return (DefWindowProc(hWnd, msg, wp, lp));
}
return 0;
}
以上です。
お忙しい中、申し訳ございませんが、再度アドバイスの方、宜しくお願いします。
No.2
- 回答日時:
こんにちは。
タイトルのアイコンはセオリーとしてはリソースファイル内のアイコンです。
アイコンもリソースですが、そういう意味ではないので直接的なファイルは指定しても意味がありません。
LoadImage(NULL, "Linux.ico" ...
という記述がありますが、それはファイルではなくてリソース上の名前である必要があります。
テキストの.rc ファイル(リソースファイル)を作ってその中で以下のようにファイルを指定します。
1 ICON "Linux.ico"
これをリソースコンパイラ(rc.exe)でresファイルにしつつ、
WinMainでは
LoadImage(NULL, MAKEINTRESOURCE(1), ...
と言うようにします。数字は1である必要は無いです。5でも200でも何でもOKですが、既存のリソースとバッティングしないようにします。
なお、rcファイルで
"LINUX_Ico" ICON "Linux.ico"
として
LoadImage(NULL, _T("LINUX_Ico") ...
でもいいですよ。リソースIDは文字列でもOKなのでパラメータがLPCTSTRなんです。
リソース名の頭は英字で、またピリオドは入れないでくださいね。
_T("...")っていうのは TEXT("...")というマクロのショート形。
BCCで実装されているかどうか分からないけども、Windows SDKとして標準のマクロです。
LPCTSTRのTが、コンパイラがワイド文字なのかバイト文字なのかを判断します。
それにあわせて_T("...")とすると、"..." なのか L"..." なのかをコンパイラが自動で設定します。
LoadImage にどうしてもファイルを指定したいならば、
LoadImage のフラグ指定に LR_LOADFROMFILE というフラグを指定してください。
このファイル指定は全てのWindowsで動くわけではありません。
Windows 98 とかで表示させるには先のリソースである必要があります。
RCファイルはそれなりの構文があるので各自調べてください。
この回答への補足
早速、ご回答頂き誠にありがとうございます。
ご指摘のあったとおり、BCCFormを使いリソースファイル、リソースヘッダーを作成し、コードを修正し、以下の手順でコンパイル、実行してみました。
※ソースファイル名はsource.cpp、リソースファイル名はIcon.rcです。
1.bcc32 -W source.cpp
2.brc32 Icon.rc source.exe
とし、出来上がった実行ファイルを実行してみたところ。。。
タイトルバーのアイコンは何も変化せず、実行ファイルのアイコンがLinux.icoに変更されました。
以下にリソースヘッダ、リソースファイル、ソースコードを記します。
※文字制限がある為、必要ではない部分は省略させて頂きます。
<リソースヘッダ>
#defineMYICON100
<リソースファイル>
#include"ResIcon.h"
//--------------------------
// イメージ(MYICON)
//--------------------------
MYICONICONDISCARDABLE"C:\Documents and Settings\ShuNakagawa\My Documents\C\Linux.ico"
<ソースファイル>
#include <windows.h>
#include "ResIcon.h"
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
ATOM InitApp(HINSTANCE, LPCSTR);
BOOL InitInstance(HINSTANCE, int, LPCSTR);
int WINAPI WinMain(
HINSTANCE hCurInst,
HINSTANCE hPrevInst,
LPSTR lpsCmdLine,
int nCmdShow)
{
MSG msg;
BOOL bRet;
LPCSTR szClassName = "Window";
if(!InitApp(hCurInst, szClassName)){
return FALSE;
}
if(!InitInstance(hCurInst, nCmdShow, szClassName)){
return FALSE;
}
while((bRet = GetMessage(&msg, NULL, 0, 0)) != 0){
if(bRet == -1){
MessageBox(NULL, "GetMessage Error", "Error", MB_OK);
break;
}
else{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int)msg.wParam;
}
//ウィンドウクラスの登録
ATOM InitApp(HINSTANCE hInst, LPCSTR szClassName)
{
WNDCLASSEX wc;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInst;
wc.hIcon = (HICON)LoadImage(
NULL,
MAKEINTRESOURCE(MYICON),
IMAGE_ICON,
0,
0,
LR_LOADFROMFILE);
wc.hCursor = (HCURSOR)LoadImage(
NULL,
MAKEINTRESOURCE(IDC_ARROW),
IMAGE_CURSOR,
0,
0,
LR_DEFAULTSIZE | LR_SHARED);
wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = (LPCSTR)szClassName;
wc.hIconSm = (HICON)LoadImage(
NULL,
MAKEINTRESOURCE(IDI_APPLICATION),
IMAGE_ICON,
0,
0,
LR_DEFAULTSIZE | LR_SHARED;
return (RegisterClassEx(&wc));
}
//ウィンドウの生成
BOOL InitInstance(HINSTANCE hInst, int nCmdShow, LPCSTR szClassName)
{
HWND hWnd;
hWnd = CreateWindow(
szClassName,
"Window",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
200,
200,
NULL,
NULL,
hInst,
NULL);
if(!hWnd){
return FALSE;
}
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
return TRUE;
}
//ウィンドウプロシージャ
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
switch(msg){
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return (DefWindowProc(hWnd, msg, wp, lp));
}
return 0;
}
以上です。
誠に申し訳ございませんが、再度アドバイスの方宜しくお願いします。
No.1
- 回答日時:
LoadImage()の戻り値は有効な値になっていますか?
読み込みに失敗してNULLだったりしませんか?
# タイトルバーのアイコンに32x32って設定したこと無いですが。
# 読み込みに問題なければ、OS側でリサイズ…してくれますかね。
この回答への補足
ご回答頂き、誠にありがとうございます。
ご指摘のあった通り、LoadImageの戻り値がNULLになっていないかを調べる為に以下のコードを書き、コンパイルし、実行してみましたが、LoadImageの戻り値はNULLにはなっていないようです。
#include <windows.h>
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
ATOM InitApp(HINSTANCE, LPCSTR);
BOOL InitInstance(HINSTANCE, int, LPCSTR);
int WINAPI WinMain(
HINSTANCE hCurInst,
HINSTANCE hPrevInst,
LPSTR lpsCmdLine,
int nCmdShow)
{
MSG msg;
BOOL bRet;
LPCSTR szClassName = "TitleBarIcon";
if(!InitApp(hCurInst, szClassName)){
return FALSE;
}
if(!InitInstance(hCurInst, nCmdShow, szClassName)){
return FALSE;
}
while((bRet = GetMessage(&msg, NULL, 0, 0)) != 0){
if(bRet == -1){
MessageBox(NULL, "GetMessage Error", "Error", MB_OK);
break;
}
else{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int)msg.wParam;
}
//ウィンドウクラスの登録
ATOM InitApp(HINSTANCE hInst, LPCSTR szClassName)
{
WNDCLASSEX wc;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInst;
wc.hIcon = (HICON)LoadImage(
NULL,
"Linux.ico",
IMAGE_ICON,
0,
0,
LR_LOADFROMFILE | LR_DEFAULTSIZE | LR_SHARED);
if(wc.hIcon == NULL){
MessageBox(NULL, "アイコンファイル読み込みに失敗",
"エラー", MB_OK);
}
wc.hCursor = (HCURSOR)LoadImage(
NULL,
MAKEINTRESOURCE(IDC_ARROW),
IMAGE_CURSOR,
0,
0,
LR_DEFAULTSIZE | LR_SHARED);
wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = (LPCSTR)szClassName;
wc.hIconSm = (HICON)LoadImage(
NULL,
MAKEINTRESOURCE(IDI_APPLICATION),
IMAGE_ICON,
0,
0,
LR_DEFAULTSIZE | LR_SHARED);
return (RegisterClassEx(&wc));
}
//ウィンドウの生成
BOOL InitInstance(HINSTANCE hInst, int nCmdShow, LPCSTR szClassName)
{
HWND hWnd;
hWnd = CreateWindow(
szClassName,
"TitleBarIcon",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
200,
200,
NULL,
NULL,
hInst,
NULL);
if(!hWnd){
return FALSE;
}
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
return TRUE;
}
//ウィンドウプロシージャ
LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp)
{
switch(msg){
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return (DefWindowProc(hWnd, msg, wp, lp));
}
return 0;
}
以上です。
ご確認の程、宜しくお願いします。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- C言語・C++・C# c言語の問題の説明、各所ごとに 5 2023/07/26 11:03
- C言語・C++・C# c言語の問題です 3 2023/01/10 16:15
- FX・外国為替取引 mql4のコンパイルエラー箇所の修正お願いします。 1 2023/03/15 16:14
- C言語・C++・C# プログラミングの授業の課題です 1 2023/01/17 22:15
- C言語・C++・C# バイナリファイルをコピーするのにかかる時間を測りたいのですが実行するとFatel error:gli 2 2022/11/03 01:10
- 大学・短大 C言語線形リストの問題です 3 2022/12/22 00:45
- C言語・C++・C# leetcode 155 minstack 1 2022/05/07 16:43
- Visual Basic(VBA) Vba LongPtrについて教えてください 2 2022/08/19 11:14
- JavaScript clear機能を失わずにファイルアップロード機能を作成したい 3 2023/06/10 16:12
- PHP php テーブルが作成できない 1 2022/11/17 23:41
このQ&Aを見た人はこんなQ&Aも見ています
関連するカテゴリからQ&Aを探す
おすすめ情報
このQ&Aを見た人がよく見るQ&A
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
エディットボックスの背景の色...
-
この列挙体でsysjanの関数はあ...
-
画像を表示したいのですが……
-
不明なエラー
-
エラー Run-Time Check Failur...
-
COMPORTマルチスレッドで例外発生
-
子ウインドウの作成と破棄について
-
エディットコントロール入力時...
-
音量調節
-
WM_CREATE について
-
プログラミングでエラーが出ま...
-
Enterキーを押されたら次の処理...
-
fgetsなどのときのstdinのバッ...
-
マイナスからプラスへ転じた時...
-
複数桁10進数の*桁目だけを抽出...
-
「指定されたキャストは有効で...
-
「an=(n-1)/(n+1)のときlim[n→∞...
-
c言語で、繰り返し文の中で、0....
-
C言語での引数の省略方法
-
正負を反転させて出力するプロ...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
Win32APIでウィンドウを中央に...
-
オーバーレイみたいな処理がしたい
-
ダイアログプログラムでEnterキ...
-
キャレットの現在位置の表示 (W...
-
PeekMessageについて
-
ウィンドウ非表示に時に表示し...
-
C#のswitch文を簡略化したいの...
-
C言語win32api、エディットボッ...
-
音量調節
-
LoadImageを使用し、タイトルバ...
-
プログラミングでエラーが出ま...
-
エディットコントロール入力時...
-
ウィンドウハンドルがメッセー...
-
ボタンの色(WINAPI)
-
画像を表示したいのですが……
-
WINAPIでキーから文字列を入力...
-
エラー Run-Time Check Failur...
-
エディットボックスの背景の色...
-
Win32APIでアイコンファイルを...
-
WM_KEYDOWNでPrtScを捕まえる方...
おすすめ情報