当前位置: 首页 > news >正文

CredentialProvider提供的UI控件与使用方法

前言:在上一篇博客中对CredentialProvider基本概念、个人理解等做了阐述,其中提到CredentialProvider提供了一定的UI控件可供开发者调用,且开发者只可以使用CredentialProvider接口所提供的控件,不可自定义控件或者美化CredentialProvider接口所提供的控件,本文则结合具体的UI控件图例对CredentialProvider所提供的UI控件进行介绍。

CredentialProvider UI控件简介:如图所示,CredentialProvider提供的UI控件共有9种,开发者可以根据需要自行选择组合使用。该图例对应的代码来自开源的样例代码编译部署所得的截图,样例代码地址为:CredentialProviders/V2 Credential Provider Sample at master · alexyack/CredentialProviders

UI控件的定义为CREDENTIAL_PROVIDER_FIELD_TYPE枚举,开发在使用时只需指定需要的控件枚举即可,CREDENTIAL_PROVIDER_FIELD_TYPE的具体定义如下:

// credentialprovider.h:359typedef /* [v1_enum] */ 
enum _CREDENTIAL_PROVIDER_FIELD_TYPE
{CPFT_INVALID	= 0,CPFT_LARGE_TEXT	= ( CPFT_INVALID + 1 ) ,CPFT_SMALL_TEXT	= ( CPFT_LARGE_TEXT + 1 ) ,CPFT_COMMAND_LINK	= ( CPFT_SMALL_TEXT + 1 ) ,CPFT_EDIT_TEXT	= ( CPFT_COMMAND_LINK + 1 ) ,CPFT_PASSWORD_TEXT	= ( CPFT_EDIT_TEXT + 1 ) ,CPFT_TILE_IMAGE	= ( CPFT_PASSWORD_TEXT + 1 ) ,CPFT_CHECKBOX	= ( CPFT_TILE_IMAGE + 1 ) ,CPFT_COMBOBOX	= ( CPFT_CHECKBOX + 1 ) ,CPFT_SUBMIT_BUTTON	= ( CPFT_COMBOBOX + 1 ) 
} 	CREDENTIAL_PROVIDER_FIELD_TYPE;

CredentialProvider UI控件的使用:UI控件的使用可以参考上面样例中的common.h,根据个人开发需要添加或者删除对应的控件即可,其中SAMPLE_FIELD_ID中的SFI_NUM_FIELDS必须保留,且只能放在最后一个,其表明自定义凭据所包含的UI字段数量。common.h源码如下所示:

// common.h
// https://github.com/alexyack/CredentialProviders/blob/master/V2%20Credential%20Provider%20Sample/C%2B%2B/common.h#pragma once
#include "helpers.h"// The indexes of each of the fields in our credential provider's tiles. Note that we're
// using each of the nine available field types here.
enum SAMPLE_FIELD_ID
{SFI_TILEIMAGE         = 0,SFI_LABEL             = 1,SFI_LARGE_TEXT        = 2,SFI_PASSWORD          = 3,SFI_SUBMIT_BUTTON     = 4,SFI_LAUNCHWINDOW_LINK = 5,SFI_HIDECONTROLS_LINK = 6,SFI_FULLNAME_TEXT     = 7,SFI_DISPLAYNAME_TEXT  = 8,SFI_LOGONSTATUS_TEXT  = 9,SFI_CHECKBOX          = 10,SFI_EDIT_TEXT         = 11,SFI_COMBOBOX          = 12,SFI_NUM_FIELDS        = 13,  // Note: if new fields are added, keep NUM_FIELDS last.  This is used as a count of the number of fields
};// The first value indicates when the tile is displayed (selected, not selected)
// the second indicates things like whether the field is enabled, whether it has key focus, etc.
struct FIELD_STATE_PAIR
{CREDENTIAL_PROVIDER_FIELD_STATE cpfs;CREDENTIAL_PROVIDER_FIELD_INTERACTIVE_STATE cpfis;
};// These two arrays are seperate because a credential provider might
// want to set up a credential with various combinations of field state pairs
// and field descriptors.// The field state value indicates whether the field is displayed
// in the selected tile, the deselected tile, or both.
// The Field interactive state indicates when
static const FIELD_STATE_PAIR s_rgFieldStatePairs[] =
{{ CPFS_DISPLAY_IN_BOTH,            CPFIS_NONE    },    // SFI_TILEIMAGE{ CPFS_HIDDEN,                     CPFIS_NONE    },    // SFI_LABEL{ CPFS_DISPLAY_IN_BOTH,            CPFIS_NONE    },    // SFI_LARGE_TEXT{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_FOCUSED },    // SFI_PASSWORD{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_SUBMIT_BUTTON{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_LAUNCHWINDOW_LINK{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_HIDECONTROLS_LINK{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_FULLNAME_TEXT{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_DISPLAYNAME_TEXT{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_LOGONSTATUS_TEXT{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_CHECKBOX{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_EDIT_TEXT{ CPFS_DISPLAY_IN_SELECTED_TILE,   CPFIS_NONE    },    // SFI_COMBOBOX
};// Field descriptors for unlock and logon.
// The first field is the index of the field.
// The second is the type of the field.
// The third is the name of the field, NOT the value which will appear in the field.
static const CREDENTIAL_PROVIDER_FIELD_DESCRIPTOR s_rgCredProvFieldDescriptors[] =
{{ SFI_TILEIMAGE,         CPFT_TILE_IMAGE,    L"Image",                      CPFG_CREDENTIAL_PROVIDER_LOGO  },{ SFI_LABEL,             CPFT_SMALL_TEXT,    L"Tooltip",                    CPFG_CREDENTIAL_PROVIDER_LABEL },{ SFI_LARGE_TEXT,        CPFT_LARGE_TEXT,    L"Sample Credential Provider"                                 },{ SFI_PASSWORD,          CPFT_PASSWORD_TEXT, L"Password text"                                              },{ SFI_SUBMIT_BUTTON,     CPFT_SUBMIT_BUTTON, L"Submit"                                                     },{ SFI_LAUNCHWINDOW_LINK, CPFT_COMMAND_LINK,  L"Launch helper window"                                       },{ SFI_HIDECONTROLS_LINK, CPFT_COMMAND_LINK,  L"Hide additional controls"                                   },{ SFI_FULLNAME_TEXT,     CPFT_SMALL_TEXT,    L"Full name: "                                                },{ SFI_DISPLAYNAME_TEXT,  CPFT_SMALL_TEXT,    L"Display name: "                                             },{ SFI_LOGONSTATUS_TEXT,  CPFT_SMALL_TEXT,    L"Logon status: "                                             },{ SFI_CHECKBOX,          CPFT_CHECKBOX,      L"Checkbox"                                                   },{ SFI_EDIT_TEXT,         CPFT_EDIT_TEXT,     L"Edit text"                                                  },{ SFI_COMBOBOX,          CPFT_COMBOBOX,      L"Combobox"                                                   },
};static const PWSTR s_rgComboBoxStrings[] =
{L"First",L"Second",L"Third",
};

其中,CredentialProvider所提供的部分UI控件样式与展示形式并非完全一成不变,如图中所示的CPFT_SUBMIT_BUTTON按钮可以像图中那样附属于CPFT_PASSWORD_TEXT控件右侧以向右的箭头形式显示,也可以以独立形式的按钮显示。若以独立的按钮形式显示,则只可在自定义凭据类中对GetSubmitButtonValue方法中的*pdwAdjacentTo参数赋值为按钮自身所对应的ID值,并将common.h中CREDENTIAL_PROVIDER_FIELD_DESCRIPTOR中的按钮字段所对应的第四个参数指定为CPFG_STANDALONE_SUBMIT_BUTTON即可,具体代码如下:

// TestCredential.cppHRESULT TestCredential::GetSubmitButtonValue(DWORD dwFieldID, _Out_ DWORD *pdwAdjacentTo)
{OutputDebugStringA(__FUNCTION__);HRESULT hr;if (SFI_SUBMIT_BUTTON == dwFieldID){// #########################################################################// 附属于CPFT_PASSWORD_TEXT密码文本控件,密码文本控件对应的字段ID为SFI_PASSWORD//*pdwAdjacentTo = SFI_PASSWORD;// #########################################################################// #########################################################################// 按钮独立显示,则赋值为SFI_SUBMIT_BUTTON*pdwAdjacentTo = SFI_SUBMIT_BUTTON;// #########################################################################hr = S_OK;}else{hr = E_INVALIDARG;}return hr;
}

指定第四个参数为CPFG_STANDALONE_SUBMIT_BUTTON,意思为以标准按钮形式显示,具体如下:

static const CREDENTIAL_PROVIDER_FIELD_DESCRIPTOR s_rgCredProvFieldDescriptors[] =
{// 指定第四个参数为CPFG_STANDALONE_SUBMIT_BUTTON,意思为以标准按钮形式显示{ SFI_SUBMIT_BUTTON, CPFT_SUBMIT_BUTTON, L"Submit", CPFG_STANDALONE_SUBMIT_BUTTON},
};

类似的CPFT_COMMAND_LINK链接文本控件,其可以通过指定第四个参数为CPFG_STYLE_LINK_AS_BUTTON而以标准按钮形式显示,具体代码如下:

static const CREDENTIAL_PROVIDER_FIELD_DESCRIPTOR s_rgCredProvFieldDescriptors[] =
{{ SFI_HIDECONTROLS_LINK, CPFT_COMMAND_LINK, L"Hide additional controls", PFG_STYLE_LINK_AS_BUTTON},
};

更多的UI可选性显示形式定义见如下GUID定义,开发者可以根据研发需要指定部分UI的显示形式

// ShlGuid.h:669//
// These GUIDs may be assigned to the CREDENTIAL_PROVIDER_FIELD_DESCRIPTOR::guidFieldType
// member by Microsoft ICredentialProvider implementations.
//// {da15bbe8-954sd-4fd3-b0f4-1fb5b90b174b}
DEFINE_GUID(CPFG_LOGON_USERNAME, 0xda15bbe8, 0x954d, 0x4fd3, 0xb0, 0xf4, 0x1f, 0xb5, 0xb9, 0x0b, 0x17, 0x4b);// {60624cfa-a477-47b1-8a8e-3a4a19981827}
DEFINE_GUID(CPFG_LOGON_PASSWORD, 0x60624cfa, 0xa477, 0x47b1, 0x8a, 0x8e, 0x3a, 0x4a, 0x19, 0x98, 0x18, 0x27);// {3e1ecf69-568c-4d96-9d59-46444174e2d6}
DEFINE_GUID(CPFG_SMARTCARD_USERNAME, 0x3e1ecf69, 0x568c, 0x4d96, 0x9d, 0x59, 0x46, 0x44, 0x41, 0x74, 0xe2, 0xd6);// {4fe5263b-9181-46c1-b0a4-9dedd4db7dea}
DEFINE_GUID(CPFG_SMARTCARD_PIN, 0x4fe5263b, 0x9181, 0x46c1, 0xb0, 0xa4, 0x9d, 0xed, 0xd4, 0xdb, 0x7d, 0xea);// {2d837775-f6cd-464e-a745-482fd0b47493}
DEFINE_GUID(CPFG_CREDENTIAL_PROVIDER_LOGO, 0x2d837775, 0xf6cd, 0x464e, 0xa7, 0x45, 0x48, 0x2f, 0xd0, 0xb4, 0x74, 0x93);// {286BBFF3-BAD4-438F-B007-79B7267C3D48}
DEFINE_GUID(CPFG_CREDENTIAL_PROVIDER_LABEL, 0x286bbff3, 0xbad4, 0x438f, 0xb0, 0x7, 0x79, 0xb7, 0x26, 0x7c, 0x3d, 0x48);// {0b7b0ad8-cc36-4d59-802b-82f714fa7022}
DEFINE_GUID(CPFG_STANDALONE_SUBMIT_BUTTON, 0x0b7b0ad8, 0xcc36, 0x4d59, 0x80, 0x2b, 0x82, 0xf7, 0x14, 0xfa, 0x70, 0x22);// {088fa508-94a6-4430-a4cb-6fc6e3c0b9e2}
DEFINE_GUID(CPFG_STYLE_LINK_AS_BUTTON, 0x088fa508, 0x94a6, 0x4430, 0xa4, 0xcb, 0x6f, 0xc6, 0xe3, 0xc0, 0xb9, 0xe2);
http://www.dtcms.com/a/487553.html

相关文章:

  • 设计师接单网站25个经典网站源代码
  • I2C软实现基于GD32F407VE的天空星的配置
  • 温州如何进行网站推广网站后台如何用代码上传视频
  • 深入浅出FastAPI:现代Python Web开发的利器
  • 月球矩阵日志:Swift 6.2 主线程隔离抉择(下)
  • 石家庄网站建设推广报价电商运营包括哪些方面
  • 相亲网站排名前十名wordpress支付通道
  • 网站被黑了定制app开发
  • Asp.net WebAPI 中使用一般处理程序处理跨域问题
  • Python的插件机制
  • 对接印度股票指数API完整指南:从入门到实战
  • 差分操作正确性证明
  • 广西建设厅网证件查询郑州seo外包平台
  • 做个支付网站多少钱南通注册公司
  • 免费网站推广优化建设网站 法律责任
  • SpringAI 本地调用 Ollama
  • python 视频播放网站开发wordpress 预订插件
  • 公司网站维护重庆平台
  • 第5篇:自定义序列化器与反序列化器:突破默认逻辑
  • NSSCTF 理想国
  • 极速迁移:GitLab项目无缝转移实战手册
  • 视频解析转换耗时—OpenCV优化摸索路
  • 自己电脑做网站谁有网站推荐一下好
  • 组织架构树形选择组件使用说明(Vue3 + UniApp)
  • 响应式网站开发步骤去哪里学习建设网站
  • 网站建设与管理用什么软件有哪些内容南京外包公司
  • 电子商务网站规划的原则江苏省城乡建设网站
  • 项目学习总结:CAN总线、摄像头、STM32概述
  • Linux中在字符串中查找指定字符的第一次出现位置的汇编实现
  • 官方网站撰写策划书分布式移动网站开发技术