基本自定义 > Windchill 自定义基础 > Windchill 自定义入门 > 创建 UI > Pet 信息页面
  
Pet 信息页面
将 Pet 表纳入“站点” > “实用程序”
此时,可以访问 acme.pet.table,但要求用户手动指定 URL。Pet 不是 WTContained,因此,纳入表格的逻辑位置位于“站点” > “实用程序”下。
1. 站点实用程序或由 codebase\netmarkets\jsp\object\commonUtilities.jspf 托管,由 Windchill 交付并由 Windchill 托管的文件。该文件不应在原位置更新;而是应通过“安全区域”机制进行处理。
a. 在加载点下创建以下两个目录结构:
wtSafeArea\ptcOrig\codebase\netmarkets\jsp\object
wtSafeArea\siteMod\codebase\netmarkets\jsp\object
commonUtilities.jspf 复制到刚刚在上面创建的两个目录。
2. 如下所示编辑 wtSafeArea\siteMod\codebase\netmarkets\jsp\object,添加以粗体显示的项:
a. <%@ page import="com.ptc.netmarkets.object.objectResource"%> 后,添加 <%@ page import="com.acme.acmeResource"%>
<%@ page import="com.ptc.netmarkets.object.objectResource"%>
<%@ page import="com.acme.acmeResource"%>
b. private static final String ENTERPRISE_RESOURCE = "wt.enterprise.enterpriseResource"; 后,添加 private static final String ACME_RESOURCE = "com.acme.acmeResource";
<%! private static final String OBJECT_CONFIG_RESOURCE =
"com.ptc.netmarkets.object.objectResource";
private static final String ENTERPRISE_RESOURCE =
"wt.enterprise.enterpriseResource";
private static final String ACME_RESOURCE = "com.acme.acmeResource";
c. ResourceBundle enterpriseRb = ResourceBundle.getBundle(ENTERPRISE_RESOURCE, localeBean.getLocale()); 后,添加 ResourceBundle acmeRb = ResourceBundle.getBundle(ACME_RESOURCE, localeBean.getLocale());
ResourceBundle objectRb = ResourceBundle.getBundle
(OBJECT_CONFIG_RESOURCE, localeBean.getLocale());
ResourceBundle enterpriseRb = ResourceBundle.getBundle
(ENTERPRISE_RESOURCE, localeBean.getLocale());
ResourceBundle acmeRb = ResourceBundle.getBundle(
ACME_RESOURCE, localeBean.getLocale());
d. "PERSONAL_CABINETS” , 后,添加 "PET_ADMINISTRATION" ,
String [] knownUtilities={"AUDITING_PURGE",
"AUDITING_LICENSE_USAGE",
"AUDITING_ORGANIZATION_USAGE",
"AUDITING_SECURITY_REPORT_QUERIES",
"AUDITING_SECURITY_REPORTS",
"CALENDAR_MANAGEMENT",
"CLASSIFICATION_ADMINISTRATOR",
"SCMI_ADAPTER_ADMINISTRATOR",
"SCMI_ADMINISTRATOR",
"CONFIGURATION_FILE_GENERATOR",
"ESI_TRANSACTION_ADMIN",
"REPLICATION_ADMINISTRATOR",
"CCS_MANAGER",
"IMPORT_EXPORT",
"INFO_ENGINE" ,
"NUMBERING_SCHEMES",
"VERSIONING_SCHEMES",
"LIFE_CYCLE_ADMIN",
"ESI_DISTRIBUTION_TARGET_ADMIN",
"OPTEGRA_GATEWAY",
"RULES_ADMINISTRATION",
"PACKAGES_MAPPING_MANAGER",
"PARTICIPANT_ADMINISTRATION",
"PERSONAL_CABINETS" ,
"PET_ADMINISTRATION",
e. if (wvs_enabled ) { 块后,添加 linkDatum.put("PET_ADMINISTRATION.isUtilityInstalled", "Yes");
if (wvs_enabled ) {
linkDatum.put("CAD_AGENT.isUtilityInstalled" , "Yes" );
linkDatum.put("PRODUCT_VIEW.isUtilityInstalled" , "Yes" );
linkDatum.put("PUBLISH_MONITOR.isUtilityInstalled" , "Yes" );
linkDatum.put("PUBLISH_SCHEDULER.isUtilityInstalled" , "Yes" );
linkDatum.put("PUBLISH_THB_CONTROL.isUtilityInstalled" , "Yes" );
}
linkDatum.put("PET_ADMINISTRATION.isUtilityInstalled", "Yes");
f. linkDatum.put("AUDITING_SECURITY_REPORTS.isAuditUtility" , "Yes" ); 后,添加 // set ACME utility flag. Define only if the utility is considered an ACME utility linkDatum.put("PET_ADMINISTRATION.isACMEUtility", "Yes");
// set audit utility flag. Define only if the utility is considered an
// auditing utility
linkDatum.put("AUDITING_PURGE.isAuditUtility" , "Yes" );
linkDatum.put("AUDITING_ORGANIZATION_USAGE.isAuditUtility" , "Yes" );
linkDatum.put("AUDITING_LICENSE_USAGE.isAuditUtility" , "Yes" );
linkDatum.put("AUDITING_SECURITY_REPORT_QUERIES.isAuditUtility", "Yes" );
linkDatum.put("AUDITING_SECURITY_REPORTS.isAuditUtility" , "Yes" );
// set ACME utility flag. Define only if the utility is
considered an ACME utility
linkDatum.put("PET_ADMINISTRATION.isACMEUtility", "Yes"
);
g. linkDatum.put("PERSONAL_CABINETS.idText" , linkBean.getLinkID(null,"textLink:deletedUsersCabinets") ); 后,添加 linkDatum.put("PET_ADMINISTRATION.idText" , linkBean.getLinkID(null,"textLink:petAdmin") );
// The value to use for id. An entry is required for all known utilities
linkDatum.put("AUDITING_PURGE.idText" , linkBean.getLinkID(null,"textLink:auditingPurge") );
linkDatum.put("AUDITING_ORGANIZATION_USAGE.idText" , linkBean.getLinkID(null,"textLink:auditingOrgUsage") );
linkDatum.put("AUDITING_LICENSE_USAGE.idText" , linkBean.getLinkID(null,"textLink:auditingLicenseUsage") );
linkDatum.put("AUDITING_SECURITY_REPORT_QUERIES.idText" , linkBean.getLinkID(null,"textLink:auditingReportQueries") );
linkDatum.put("AUDITING_SECURITY_REPORTS.idText" , linkBean.getLinkID(null,"textLink:auditingReports") );
linkDatum.put("CAD_AGENT.idText" , linkBean.getLinkID(null,"textLink:cadAgentAdmin") );
linkDatum.put("CALENDAR_MANAGEMENT.idText" , linkBean.getLinkID(null,"textLink:calendarManagement") );
linkDatum.put("CLASSIFICATION_ADMINISTRATOR.idText" , linkBean.getLinkID(null,"textLink:classificationAdministrator") );
linkDatum.put("CONFIGURATION_FILE_GENERATOR.idText" , linkBean.getLinkID(null,"textLink:configurationFileGenerator") );
linkDatum.put("ESI_DISTRIBUTION_TARGET_ADMIN.idText" , linkBean.getLinkID(null,"textLink:ESI_DISTRIBUTION_TARGET_ADMIN") );
linkDatum.put("ESI_TRANSACTION_ADMIN.idText" , linkBean.getLinkID(null,"textLink:ESI") );
linkDatum.put("EXTERNAL_STORAGE.idText" , linkBean.getLinkID(null,"textLink:externalStorageAdmin") );
linkDatum.put("IMPORT_EXPORT.idText" , linkBean.getLinkID(null,"textLink:importExportAdmin") );
linkDatum.put("PACKAGES_MAPPING_MANAGER.idText" , linkBean.getLinkID(null,"textLink:packageMappingManager") );
linkDatum.put("INFO_ENGINE.idText" , linkBean.getLinkID(null,"textLink:infoEngineAdmin") );
linkDatum.put("LIFE_CYCLE_ADMIN.idText" , linkBean.getLinkID(null,"textLink:lifeCycleTemplateAdmin") );
linkDatum.put("NUMBERING_SCHEMES.idText" , linkBean.getLinkID(null,"textLink:numberingSchemesAdmin") );
linkDatum.put("POLICY_ADMINISTRATOR.idText" , linkBean.getLinkID(null,"textLink:policyAdmin") );
linkDatum.put("PERSONAL_CABINETS.idText" , linkBean.getLinkID(null,"textLink:deletedUsersCabinets") );
linkDatum.put("PET_ADMINISTRATION.idText" , linkBean.getLinkID(null,"textLink:petAdmin") );
h. linkDatum.put("VIEW_NETWORK.pageLoc" , viewAction.getActionUrl(actionBean, linkBean, objectBean, localeBean, urlFactoryBean,nmcontext, sessionBean,request)); 后,添加 //ACME pageLocs linkDatum.put("PET_ADMINISTRATION.pageLoc", NetmarketURL.convertToShellURL("ptc1/comp/acme.pet.table"));
//We need to get the locale specific link for the network admin .

NmAction viewAction = NmActionServiceHelper.service.getAction
("view","list");
linkDatum.put("VIEW_NETWORK.pageLoc"
, viewAction.getActionUrl(actionBean, linkBean,
objectBean, localeBean,
urlFactoryBean,nmcontext, sessionBean,request));
//ACME pageLocs
linkDatum.put("PET_ADMINISTRATION.pageLoc", NetmarketURL.convertToShellURL("ptc1/comp/acme.pet.table"));
i. linkDatum.put("NUMBERING_SCHEMES.urlPrarms" ,"'NumberingSchemes','resizable=yes,scrollbars=yes,menubar=yes,toolbar=yes,location=yes,status=yes'"); 后,添加 linkDatum.put("PET_ADMINISTRATION.urlPrarms" ,"'PetAdmin','resizable=yes,scrollbars=yes,menubar=yes,toolbar=yes,location=yes,status=yes'" );
linkDatum.put("ESI_TRANSACTION_ADMIN.urlPrarms","'ESITransaction','
directories=no,location=no,menubar=no,scrollbars=yes,status=yes,
toolbar=no,resizable=yes,height=1000,width=1400'" );

linkDatum.put("EXTERNAL_STORAGE.urlPrarms"
,"'ExternalStorage','resizable=yes,scrollbars=yes,menubar=no,
toolbar=no,location=no,status=yes,height=455,width=640'" );
linkDatum.put("IMPORT_EXPORT.urlPrarms"
,"'_blank','resizable=yes,scrollbars=yes,menubar=no,
toolbar=no,location=no,
status=yes,height=455,width=640'");
linkDatum.put("PACKAGES_MAPPING_MANAGER.urlPrarms"
,"'_blank','resizable=yes,scrollbars=yes,menubar=no,
toolbar=no,location=no,
status=yes,height=500,width=880'");
linkDatum.put("INFO_ENGINE.urlPrarms"
,"'InfoEngine','resizable=yes,scrollbars=yes,menubar=yes,
toolbar=yes,
location=yes,status=yes'" );
linkDatum.put("LIFE_CYCLE_ADMIN.urlPrarms"
,"'LifeCycleAdmin','resizable=yes,scrollbars=yes,menubar=yes,
toolbar=yes,
location=yes,status=yes'");
linkDatum.put("NUMBERING_SCHEMES.urlPrarms"
,"'NumberingSchemes','resizable=yes,scrollbars=yes,menubar=yes,
toolbar=yes,
location=yes,status=yes'");
linkDatum.put("PET_ADMINISTRATION.urlPrarms"
,"'PetAdmin','resizable=yes,scrollbars=yes,menubar=yes,
toolbar=yes,
location=yes,status=yes'" );
j. linkDatum.put("PERSONAL_CABINETS.linkText" ,objectRb.getString(objectResource.PERSONAL_CABINETS)); 后,添加 linkDatum.put("PET_ADMINISTRATION.linkText" ,acmeRb.getString(acmeResource.PET_ADMINISTRATION));
linkDatum.put("EXTERNAL_STORAGE.linkText" ,objectRb.getString(objectResource.EXTERNAL_STORAGE));
linkDatum.put("IMPORT_EXPORT.linkText"
,objectRb.getString(objectResource.IMPORT_EXPORT));
linkDatum.put("PACKAGES_MAPPING_MANAGER.linkText"
,objectRb.getString(objectResource.PACKAGES_MAPPING_MANAGER));
linkDatum.put("INFO_ENGINE.linkText"
,objectRb.getString(objectResource.INFO_ENGINE));
linkDatum.put("LIFE_CYCLE_ADMIN.linkText"
,objectRb.getString(objectResource.LIFE_CYCLE_ADMIN));
linkDatum.put("NUMBERING_SCHEMES.linkText"
,objectRb.getString(objectResource.NUMBERING_SCHEMES));
linkDatum.put("PERSONAL_CABINETS.linkText"
,objectRb.getString(objectResource.PERSONAL_CABINETS));
linkDatum.put("PET_ADMINISTRATION.linkText"
,acmeRb.getString(acmeResource.PET_ADMINISTRATION));
k. linkDatum.put("PERSONAL_CABINETS.linkDesc" ,objectRb.getString(objectResource.PERSONAL_CABINETS_DESCRIPTION)); 后,添加 linkDatum.put("PET_ADMINISTRATION.linkDesc" ,acmeRb.getString(acmeResource.PET_ADMINISTRATION_DESCRIPTION));
linkDatum.put("EXTERNAL_STORAGE.linkDesc"
,objectRb.getString(objectResource.EXTERNAL_STORAGE_DESCRIPTION));
linkDatum.put("IMPORT_EXPORT.linkDesc"
,objectRb.getString(objectResource.IMPORT_EXPORT_DESCRIPTION));
linkDatum.put("PACKAGES_MAPPING_MANAGER.linkDesc"
,objectRb.getString(objectResource.PACKAGES_MAPPING_MANAGER_DESCRIPTION));
linkDatum.put("INFO_ENGINE.linkDesc"
,objectRb.getString(objectResource.INFO_ENGINE_DESCRIPTION));
linkDatum.put("LIFE_CYCLE_ADMIN.linkDesc"
,objectRb.getString(objectResource.LIFE_CYCLE_ADMIN_DESCRIPTION));
linkDatum.put("NUMBERING_SCHEMES.linkDesc"
,objectRb.getString(objectResource.NUMBERING_SCHEMES_DESCRIPTION));
linkDatum.put("PERSONAL_CABINETS.linkDesc"
,objectRb.getString(objectResource.PERSONAL_CABINETS_DESCRIPTION));
linkDatum.put("PET_ADMINISTRATION.linkDesc"
,acmeRb.getString(acmeResource.PET_ADMINISTRATION_DESCRIPTION));
l.
objectRb.getString(objectResource.AUDITING_ADMINISTRATION)};
boolean [] systemHeader={true,false,false};
boolean [] auditHeader={false,false,true};
替换为
objectRb.getString(objectResource.AUDITING_ADMINISTRATION),
acmeRb.getString(acmeResource.ACME_ADMINISTRATION)};
boolean [] systemHeader={true,false,false,false};
boolean [] auditHeader={false,false,true,false};
boolean [] acmeHeader={false,false,false,true};
m. //Match audit/nonaudit 部分后,添加 //Match acme/noacme String isACME = knownUtilities[i].concat(".isACMEUtility"); if (linkDatum.containsKey(isACME)!=acmeHeader[currentHeader]) { continue;
//Match audit/nonaudit
String isAudit = knownUtilities[i].concat(".isAuditUtility");
if (linkDatum.containsKey(isAudit)!=auditHeader[currentHeader]) {
continue;
}
//Match acme/noacme
String isACME = knownUtilities[i].concat(".isACMEUtility");
if (linkDatum.containsKey(isACME)!=acmeHeader[currentHeader]) {
continue;
n. <% } else if ("RULES_ADMINISTRATION".equals(knownUtilities[i])) { %> href="<%=pageLoc%>" 后,添加 <% } else if ("PET_ADMINISTRATION".equals(knownUtilities[i])) { %> href="<%=pageLoc%>"
<% } else if ("RULES_ADMINISTRATION".equals(knownUtilities[i])) { %>
href="<%=pageLoc%>"
<% } else if ("PET_ADMINISTRATION".equals(knownUtilities[i])) { %>
href="<%=pageLoc%>"
<% }
3. 启用 PET_ADMINISTRATION
a. 在加载点下创建以下两个目录结构:
wtSafeArea\ptcOrig\codebase\netmarkets\jsp\site
wtSafeArea\siteMod\codebase\netmarkets\jsp\site
b. 将 listUtilities.jspf 复制到刚刚在上面创建的两个目录。
c. 编辑 wtSafeArea\siteMod\codebase\netmarkets\jsp\site\listUtilities.jsp,将以下内容附加 (在第 67 行后) 到 enabled:
showUtility.put("PET_ADMINISTRATION" , "Enable");
4. 部署站点修改:ant -f bin/swmaint.xml installSiteChanges
5. 创建导入的 acmeResource,如下所示
package com.acme;
import wt.util.resource.*;
@RBUUID("com.acme.acmeResource")
public class acmeResource extends WTListResourceBundle {
@RBEntry("ACME Administration")
public static final String ACME_ADMINISTRATION = "acme_administration";
@RBEntry("Pet Administration")
public static final String PET_ADMINISTRATION = "pet_administration";
@RBEntry("CRUD opererations for pets")
public static final String PET_ADMINISTRATION_DESCRIPTION =
"pet_administration_description";
}
6. 启动/重新启动 Windchill
7. “站点” > “实用程序”应合并 ACME Administration,如下所示
Pet 信息页面
表当前显示了一个 "i",表示 (Stimpy 的) 信息页,但信息页尚未创建 (单击 "i" 时将导致错误)。
1. 创建信息页的主构建器。如下所示完成源:
package com.acme.mvc.builders;
import wt.util.WTException;
import com.ptc.jca.mvc.builders.DefaultInfoComponentBuilder;
import com.ptc.mvc.components.ComponentBuilder;
import com.ptc.mvc.components.ComponentId;
import com.ptc.mvc.components.ComponentParams;
import com.ptc.mvc.components.InfoConfig;
import com.ptc.mvc.components.TypeBased;

@ComponentBuilder(ComponentId.INFOPAGE_ID)
@TypeBased("com.acme.Pet")
public class PetInfoBuilder extends DefaultInfoComponentBuilder {
@Override
protected InfoConfig buildInfoConfig(final ComponentParams params)
throws WTException {
final InfoConfig info = getComponentConfigFactory().newInfoConfig();
info.setTabSet("petDetails");
return info;
}
}
2. 通过创建操作模型 (在 config\actions\Pet-actionmodels.xml 中) 定义 petDetails 选项卡集。
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE actionmodels SYSTEM 'actionmodels.dtd'>
<actionmodels>
<model name="petDetails">
<action name="primaryAttributes" type="object"/>
<action name="attachments" type="object"/>
</model>
</actionmodels>
3. 定义 primaryAttributes
package com.acme.mvc.builders;
import wt.util.WTException;
import com.acme.Pet;
import com.ptc.core.ui.resources.ComponentType;
import com.ptc.jca.mvc.components.AbstractAttributesComponentBuilder;
import com.ptc.jca.mvc.components.JcaAttributeConfig;
import com.ptc.jca.mvc.components.JcaGroupConfig;
import com.ptc.mvc.components.AttributePanelConfig;
import com.ptc.mvc.components.ComponentBuilder;
import com.ptc.mvc.components.ComponentConfigFactory;
import com.ptc.mvc.components.ComponentId;
import com.ptc.mvc.components.ComponentParams;
import com.ptc.mvc.components.TypeBased;

@ComponentBuilder("primaryAttributes")
@TypeBased("com.acme.Pet")
public class PetInfoAttributesBuilder extends
AbstractAttributesComponentBuilder {
@Override
protected AttributePanelConfig buildAttributesComponentConfig
(final ComponentParams params)
throws WTException {
final ComponentConfigFactory factory = getComponentConfigFactory();

final AttributePanelConfig panel; {
panel = factory.newAttributePanelConfig(ComponentId.ATTRIBUTE_PANEL_ID);
panel.setComponentType(ComponentType.WIZARD_ATTRIBUTES_TABLE);

final JcaGroupConfig group; {
group = (JcaGroupConfig) factory.newGroupConfig();
group.setId("attributes");
group.setLabel("Attributes");
group.setIsGridLayout(true);

group.addComponent(getAttribute(Pet.NAME, factory));
group.addComponent(getAttribute(Pet.KIND, factory));
group.addComponent(getAttribute(Pet.DATE_OF_BIRTH, factory));
group.addComponent(getAttribute(Pet.FIXED, factory));
}
panel.addComponent(group);
}
return panel;
}
JcaAttributeConfig getAttribute(final String id, final
ComponentConfigFactory factory) {
final JcaAttributeConfig attribute = (JcaAttributeConfig)
factory.newAttributeConfig();
attribute.setId(id);
return attribute;
}
}
4. 通过将 Pet-configs.xml 更新为包含以下内容来注册 bean:
<bean class="com.acme.mvc.builders.PetInfoBuilder"/>
<bean class="com.acme.mvc.builders.PetInfoAttributesBuilder"/>
5. Pet-actionmodels.xml 添加至 site.xconf.
a. 在最后一行之前,</Configuration> 添加 <AddToProperty name="com.ptc.netmarkets.util.misc.defaultActionmodels" value="config/actions/Petactionmodels.xml"/>
b. 运行 bin/xconfmanager -pF 以传播更改。
6. 启动/重新启动 Windchill,然后验证 (请注意内容的“附件”选项卡)。