private async Task BindPlacementAsync(BuildShapeContext context, string displayType, string stereotype) { var theme = await _themeManager.GetThemeAsync(); var shapeTable = _shapeTableManager.GetShapeTable(theme.Id); context.FindPlacement = (partShapeType, differentiator, defaultLocation) => { ShapeDescriptor descriptor; if (shapeTable.Descriptors.TryGetValue(partShapeType, out descriptor)) { var placementContext = new ShapePlacementContext { Shape = context.Shape }; // define which location should be used if none placement is hit descriptor.DefaultPlacement = defaultLocation; var placement = descriptor.Placement(placementContext); if (placement != null) { placement.Source = placementContext.Source; return placement; } } return new PlacementInfo { Location = defaultLocation, Source = String.Empty }; }; }
private void ApplyImplementation(BuildShapeContext context, string displayType) { var placement = context.FindPlacement(_shapeType, _differentiator, _defaultLocation); if (String.IsNullOrEmpty(placement.Location) || placement.Location == "-") { return; } // Parse group placement. _groupId = placement.GetGroup(); if (!String.Equals(context.GroupId ?? "", _groupId ?? "", StringComparison.OrdinalIgnoreCase)) { return; } var newShape = _shapeBuilder(context); // Ignore it if the driver returned a null shape. if (newShape == null) { return; } ShapeMetadata newShapeMetadata = newShape.Metadata; newShapeMetadata.Prefix = _prefix; newShapeMetadata.DisplayType = displayType; newShapeMetadata.PlacementSource = placement.Source; newShapeMetadata.Tab = placement.GetTab(); // The _processing callback is used to delay execution of costly initialization // that can be prevented by caching if(_processing != null) { newShapeMetadata.OnProcessing(_processing); } // Apply cache settings if(!String.IsNullOrEmpty(_cacheId) && _cache != null) { _cache(newShapeMetadata.Cache(_cacheId)); } // If a specific shape is provided, remove all previous alternates and wrappers. if (!String.IsNullOrEmpty(placement.ShapeType)) { newShapeMetadata.Type = placement.ShapeType; newShapeMetadata.Alternates.Clear(); newShapeMetadata.Wrappers.Clear(); } foreach (var alternate in placement.Alternates) { newShapeMetadata.Alternates.Add(alternate); } foreach (var wrapper in placement.Wrappers) { newShapeMetadata.Wrappers.Add(wrapper); } dynamic parentShape = context.Shape; if(placement.IsLayoutZone()) { parentShape = context.Layout; } var position = placement.GetPosition(); var zones = placement.GetZones(); foreach(var zone in zones) { parentShape = parentShape.Zones[zone]; } if (String.IsNullOrEmpty(position)) { parentShape.Add(newShape); } else { parentShape.Add(newShape, position); } }