/// <summary> /// This is the definition of what it means for a field to pass all current restrictions. /// </summary> /// <param name="flid"></param> /// <returns></returns> bool Accept(int flid) { if (m_mdc.get_IsVirtual(flid)) { return(false); } // LT-13636 -- The line below kept custom fields referencing custom lists from being valid browse columns. //if (m_destClsid != 0 && m_mdc.GetDstClsId(flid) != m_destClsid) is too strict! Should accept a subclass! if (m_destClsid != 0) { var flidDestClass = m_mdc.GetDstClsId(flid); var acceptableClasses = ((IFwMetaDataCacheManaged)m_mdc).GetAllSubclasses(m_destClsid); if (!acceptableClasses.ContainsCollection(new int[] { flidDestClass })) { return(false); } } switch (m_restrictions) { case "none": return(true); case "customOnly": return(((IFwMetaDataCacheManaged)m_mdc).IsCustom(flid)); case "featureDefns": return(flid == FsFeatureSystemTags.kflidFeatures); } return(true); }
/// <summary> /// looks up plural form alternative first for given flid, secondly for its destination class. /// </summary> /// <param name="mdc"></param> /// <param name="tbl"></param> /// <param name="owningFlid"></param> /// <param name="titleStr">*{dstClass}* if couldn't find result.</param> /// <returns>true if we found an alternate form. false if titleStr is null or in *{key}* format.</returns> public static bool TryFindPluralFormFromFlid(IFwMetaDataCache mdc, StringTable tbl, int owningFlid, out string titleStr) { // first see if we can find an expanded name for the name of a flid. string flidName = mdc.GetFieldName(owningFlid); if (!String.IsNullOrEmpty(flidName)) { if (TryFindString(tbl, "AlternativeTitles", flidName, out titleStr)) return true; } // secondly, see if we can find the plural form for the destination class. int dstClass = mdc.GetDstClsId(owningFlid); return TryFindPluralFormFromClassId(mdc, tbl, dstClass, out titleStr); }
/// <summary> /// This is invoked when a generated part ref (<part ref="Custom" param="fieldName"/>) /// invokes the standard slice (<slice editor="autoCustom".../>). It comes up with the /// appropriate default slice for the custom field indicated in the param attribute of /// the caller. /// </summary> static Slice MakeAutoCustomSlice(FdoCache cache, ICmObject obj, XmlNode caller) { IFwMetaDataCache mdc = cache.DomainDataByFlid.MetaDataCache; int flid = GetCustomFieldFlid(caller, mdc, obj); if (flid == 0) { return(null); } Slice slice = null; var type = (CellarPropertyType)mdc.GetFieldType(flid); switch (type) { case CellarPropertyType.String: case CellarPropertyType.MultiUnicode: case CellarPropertyType.MultiString: int ws = mdc.GetFieldWs(flid); switch (ws) { case 0: // a desperate default. case WritingSystemServices.kwsAnal: slice = new StringSlice(obj, flid, cache.DefaultAnalWs); break; case WritingSystemServices.kwsVern: slice = new StringSlice(obj, flid, cache.DefaultVernWs); break; case WritingSystemServices.kwsAnals: case WritingSystemServices.kwsVerns: case WritingSystemServices.kwsAnalVerns: case WritingSystemServices.kwsVernAnals: slice = new MultiStringSlice(obj, flid, ws, 0, false, true, true); break; default: throw new Exception("unhandled ws code in MakeAutoCustomSlice"); } break; case CellarPropertyType.Integer: slice = new IntegerSlice(cache, obj, flid); break; case CellarPropertyType.GenDate: slice = new GenDateSlice(cache, obj, flid); break; case CellarPropertyType.OwningAtomic: int dstClsid = mdc.GetDstClsId(flid); if (dstClsid == StTextTags.kClassId) { slice = new StTextSlice(obj, flid, cache.DefaultAnalWs); } break; case CellarPropertyType.ReferenceAtomic: slice = new AtomicReferenceSlice(cache, obj, flid); break; case CellarPropertyType.ReferenceCollection: case CellarPropertyType.ReferenceSequence: slice = new ReferenceVectorSlice(cache, obj, flid); break; } if (slice == null) { throw new Exception("unhandled field type in MakeAutoCustomSlice"); } slice.Label = mdc.GetFieldLabel(flid); return(slice); }
private void m_tvClasses_AfterSelect(object sender, System.Windows.Forms.TreeViewEventArgs e) { m_lvfields.Items.Clear(); uint clid = (uint)m_tvClasses.SelectedNode.Tag; int countFoundFlids = m_mdc.GetFields(clid, true, (int)CellarModuleDefns.kgrfcptAll, 0, null); int allFlidCount = countFoundFlids; uint[] uIds; using (ArrayPtr flids = MarshalEx.ArrayToNative(allFlidCount, typeof(uint))) { countFoundFlids = m_mdc.GetFields(clid, true, (int)CellarModuleDefns.kgrfcptAll, allFlidCount, flids); uIds = (uint[])MarshalEx.NativeToArray(flids, allFlidCount, typeof(uint)); } m_lvfields.SuspendLayout(); List <ListViewItem> list = new List <ListViewItem>(); for (int i = uIds.Length - 1; i >= 0; --i) { uint flid = uIds[i]; if (flid == 0) { continue; // Keep looking for suitable flids lower in the array. } string className = m_mdc.GetOwnClsName(flid); ListViewItem lvi = new ListViewItem(className); //m_lvfields.Items.Add(className); list.Add(lvi); // flid lvi.SubItems.Add(flid.ToString()); // field name string fieldname = m_mdc.GetFieldName(flid); lvi.SubItems.Add(fieldname); int flidType = m_mdc.GetFieldType(flid); string type = "Not recognized"; string signature = "Not recognized"; uint dstClid; switch (flidType) { // Basic data types. case (int)CellarModuleDefns.kcptBoolean: type = "Basic"; signature = "Boolean"; break; case (int)CellarModuleDefns.kcptInteger: type = "Basic"; signature = "Integer"; break; case (int)CellarModuleDefns.kcptNumeric: type = "Basic"; signature = "Numeric"; break; case (int)CellarModuleDefns.kcptFloat: type = "Basic"; signature = "Float"; break; case (int)CellarModuleDefns.kcptTime: type = "Basic"; signature = "Time"; break; case (int)CellarModuleDefns.kcptGuid: type = "Basic"; signature = "Guid"; break; case (int)CellarModuleDefns.kcptImage: type = "Basic"; signature = "Image"; break; case (int)CellarModuleDefns.kcptGenDate: type = "Basic"; signature = "GenDate"; break; case (int)CellarModuleDefns.kcptBinary: type = "Basic"; signature = "Binary"; break; case (int)CellarModuleDefns.kcptString: type = "Basic"; signature = "String"; break; case (int)CellarModuleDefns.kcptBigString: type = "Basic"; signature = "String (big)"; break; case (int)CellarModuleDefns.kcptMultiString: type = "Basic"; signature = "MultiString"; break; case (int)CellarModuleDefns.kcptMultiBigString: type = "Basic"; signature = "MultiString (big)"; break; case (int)CellarModuleDefns.kcptUnicode: type = "Basic"; signature = "Unicode"; break; case (int)CellarModuleDefns.kcptBigUnicode: type = "Basic"; signature = "Unicode (big)"; break; case (int)CellarModuleDefns.kcptMultiUnicode: type = "Basic"; signature = "MultiUnicode"; break; case (int)CellarModuleDefns.kcptMultiBigUnicode: type = "Basic"; signature = "MultiUnicode (big)"; break; // CmObjects. case (int)CellarModuleDefns.kcptOwningAtom: type = "OA"; dstClid = m_mdc.GetDstClsId(flid); signature = m_mdc.GetClassName(dstClid); break; case (int)CellarModuleDefns.kcptReferenceAtom: type = "RA"; dstClid = m_mdc.GetDstClsId(flid); signature = m_mdc.GetClassName(dstClid); break; case (int)CellarModuleDefns.kcptOwningCollection: type = "OC"; dstClid = m_mdc.GetDstClsId(flid); signature = m_mdc.GetClassName(dstClid); break; case (int)CellarModuleDefns.kcptReferenceCollection: type = "RC"; dstClid = m_mdc.GetDstClsId(flid); signature = m_mdc.GetClassName(dstClid); break; case (int)CellarModuleDefns.kcptOwningSequence: type = "OS"; dstClid = m_mdc.GetDstClsId(flid); signature = m_mdc.GetClassName(dstClid); break; case (int)CellarModuleDefns.kcptReferenceSequence: type = "RS"; dstClid = m_mdc.GetDstClsId(flid); signature = m_mdc.GetClassName(dstClid); break; } // Type lvi.SubItems.Add(type); // Signature lvi.SubItems.Add(signature); } m_lvfields.Items.AddRange(list.ToArray()); m_lvfields.ResumeLayout(true); }
/// <summary> /// Return whether it is OK to move the objects indicated by odi to the specified destination. /// </summary> /// <param name="hvoDstOwner"></param> /// <param name="flidDst"></param> /// <param name="ihvoDstStart"></param> /// <param name="odi"></param> /// <returns></returns> public bool OkToMove(int hvoDstOwner, int flidDst, int ihvoDstStart, ObjectDragInfo odi) { CheckDisposed(); FDO.FdoCache cache = Slice.ContainingDataTree.Cache; if (flidDst == odi.FlidSrc) { // Verify that it is not a no-operation. if (hvoDstOwner == odi.HvoSrcOwner) { // Same property of same object. If it's a collection, disable. FieldType fieldType = cache.GetFieldType(flidDst); // We can't drag it to the position it's already at; that's no change. We also can't drag it // to the position one greater: that amounts to trying to place it after itself, which (after // removing it from before itself) amounts to a no-operation. if (fieldType == FieldType.kcptOwningSequence && ihvoDstStart != odi.IhvoSrcStart && ihvoDstStart != odi.IhvoSrcStart + 1) { // It's a sequence and the target and source positions are different, so we can do it. return(true); } } else { // Different objects; need to verify no circular ownership involved. for (int ihvo = odi.IhvoSrcStart; ihvo <= odi.IhvoSrcEnd; ihvo++) { int hvo = cache.GetVectorItem(odi.HvoSrcOwner, odi.FlidSrc, ihvo); // See if hvoDstOwner is owned by hvo int hvo2 = hvoDstOwner; // loop from hvo2 to root owner of hvo2. If hvo2 or any of its owners is hvo, // we have a problem. while (hvo2 != 0) { if (hvo == hvo2) { return(false); // circular ownership, can't drop. } hvo2 = cache.GetOwnerOfObject(hvo2); } } return(true); } } else { // Different property, check signature. IFwMetaDataCache mdc = cache.MetaDataCacheAccessor; uint luclid = mdc.GetDstClsId((uint)flidDst); for (int ihvo = odi.IhvoSrcStart; ihvo <= odi.IhvoSrcEnd; ihvo++) { int hvo = cache.GetVectorItem(odi.HvoSrcOwner, odi.FlidSrc, ihvo); uint cls = (uint)cache.GetClassOfObject(hvo); while (cls != 0 && cls != luclid) { cls = mdc.GetBaseClsId(cls); } if (cls == 0) { return(false); // wrong signature, can't drop. } } // All sigs OK, allow drop. return(true); } // If none of those cases is OK, can't do it. return(false); }