CImageList 和 CComboBoxEx 限制为 16 个透明图标

Posted

技术标签:

【中文标题】CImageList 和 CComboBoxEx 限制为 16 个透明图标【英文标题】:CImageList and CComboBoxEx limited to 16 transparent icons 【发布时间】:2017-01-11 15:02:34 【问题描述】:

在 CComboBoxEx 中可以使用的透明图标似乎有 16 个限制。我有以下伪代码:

m_ImageList.Create(16,16,ILC_COLOR32,TF_COUNT,1);

for (int nImage = 0; nImage < TF_COUNT; nImage++)

    m_ImageList.Add(phIcons[nImage]);
    DestroyIcon(phIcons[nImage]);

m_cmbAction.SetImageList(&m_ImageList);

前 16 个图标是可以的 - 以下都是黑色背景而不是透明的。与 CTreeCtrl 或 CListCtrl 关联的相同代码和图像列表效果很好。有什么想法吗?

编辑:我正在使用 Visual Studio 2013

【问题讨论】:

TF_COUNT 是多少?您是否尝试改为致电m_ImageList.Create(16,16,ILC_COLOR32,1,TF_COUNT); 为什么是DestroyIcon(phIcons[nImage]); @sergiol 我已经使用 CreateIconIndirect 创建了图标 - 我需要根据 msdn.microsoft.com/en-us/library/windows/desktop/… 销毁它 TF_COUNT 在我的代码中为 25 - 至于切换参数,我正在尝试任何方法,但这是遥不可及的(注意:出于理智的原因,我还是尝试了它,但它不起作用,我感觉很好:) ) 【参考方案1】:

作者在 ZIP 文件中发布了他的代码:

m_ImageList.Create(16, 16, ILC_COLOR32, TF_COUNT, 1);

for (int nIcon=0; nIcon < TF_COUNT; nIcon++)

    m_ImageList.Add(m_hIcon);

m_ComboBox.SetImageList(&m_ImageList);

COMBOBOXEXITEM cbi;
cbi.mask = CBEIF_IMAGE | CBEIF_INDENT | CBEIF_OVERLAY |
    CBEIF_SELECTEDIMAGE | CBEIF_TEXT | CBEIF_LPARAM;
int nItemCount = 0;


for (int nText = 0; nText < TF_COUNT; nText++)

    CString strItem;
    strItem.Format(_T("Item %d"),nText);
    cbi.iItem = nItemCount;
    cbi.pszText = (LPTSTR)(LPCTSTR)strItem;
    cbi.cchTextMax = strItem.GetLength();
    cbi.iImage = nText;
    cbi.iSelectedImage = nText;
    cbi.iOverlay = nText;
    cbi.iIndent = 0;
    cbi.lParam = nText;
    m_ComboBox.InsertItem(&cbi);
    nItemCount++;

在这段代码中,错误是CBEIF_OVERLAYcbi.iOverlay = nText。叠加图像是在另一个图像上透明绘制的图像(这样,您可以组合两个图标)。在作者的代码中,显然不是这个意图。

最后,图片列表允许only up to 15 overlay icons。这就解释了魔法 16。

【讨论】:

你给你加星!我真的很感谢你的彻底和毅力!【参考方案2】:

解决方案 1

如果要使用透明度,则需要创建带有蒙版的图像列表:

m_ImageList.Create(16, 16, ILC_COLOR32 | ILC_MASK, TF_COUNT, 1)

解决方案 2

另一种(更糟糕的)方法是设置所需的背景颜色(在创建图像列表之后,但在添加图标之前):

m_ImageList.SetBkColor(RGB(0xFF, 0xFF, 0xFF))

关于背景颜色的问题是您必须弄清楚要使用哪种背景颜色。

16的幻数

我不认为你的问题是关于 CComboBoxEx 以某种方式与号码 16 有问题。相反,我认为您的图标有点不同,例如一些真​​正的 32 位,还有一些其他格式。你可以这样测试它:

m_ImageList.Create(16,16,ILC_COLOR32,TF_COUNT,1);

for (int nImage = 0; nImage < TF_COUNT; nImage++)

    m_ImageList.Add(phIcons[0]);


m_cmbAction.SetImageList(&m_ImageList);

此代码多次添加相同的图标。我打赌你不会有任何问题。现在,你也可以试试这个:

m_ImageList.Create(16,16,ILC_COLOR32,TF_COUNT,1);

for (int nImage = 0; nImage < TF_COUNT; nImage++)

    m_ImageList.Add(phIcons[16]);


m_cmbAction.SetImageList(&m_ImageList);

而且你很可能把所有图标都弄错了。

更新 1

我的 Win8.1 上的 16+ 个透明图标没有任何问题,因此是时候怀疑第三方软件或您自己的代码是问题的根源。您需要准备一个仍然包含问题的代码的最小示例,然后在另一台计算机上尝试。最好在虚拟机上尝试(您可以下载预建的here),以降低您在多台机器上同时安装的任何软件的所有可能风险。如果您的最小示例仍然显示虚拟机上的问题,请将其压缩并与我们分享。

【讨论】:

感谢您的提示 - 我确实喜欢您很周到的事实。解决方案 1 不正确 - 您不应该一起使用 ILC_COLOR32 ILC_MASK ... 并且 ILC_COLOR32 在列表控件上工作得很好 解决方案 2:我添加了 20 次相同的图标:前 16 个是可以的 - 第 17 个是不是 - CombBoxEx 有一个神奇的数字 16 :) 难以置信我知道 不知道为什么你认为ILC_COLOR32 ILC_MASK 不能一起使用。 MSDN 对此只字未提,在我自己的示例中,我加载 24 位图标 ILC_MASK 解决了黑色背景。另外,我的 Windows 8.1 上的 16 没有问题。查看更新。 你就像 St Thomas ;) 我已经按照你的建议做了,小样本,带有 hyper-g 的虚拟机,我只得到 16 个透明图标...检查代码:db.tt/ewe3wsQ7gQ 我决定发布另一个答案以使其干净。 PS:你应该先给我们一个最小的例子。

以上是关于CImageList 和 CComboBoxEx 限制为 16 个透明图标的主要内容,如果未能解决你的问题,请参考以下文章

MFC-CImagelist图像列表控件

在 CComboBoxEx 和 ReleaseBuffer 中插入和项目

MFC CComboBoxEx 图标更新问题

CListCtrl 和 CImageList 访问 HBITMAP 进行修改

Mfc CComboBoxEx - 如何更改背景颜色

用图标计算 CComboBoxEx 的最大下拉宽度