Not
Bu sayfaya erişim yetkilendirme gerektiriyor. Oturum açmayı veya dizinleri değiştirmeyi deneyebilirsiniz.
Bu sayfaya erişim yetkilendirme gerektiriyor. Dizinleri değiştirmeyi deneyebilirsiniz.
DSL Tanımlarını düzenlemek için kullandığınız tasarımcıya uzantılar oluşturabilirsiniz. Yapabileceğiniz uzantı türleri arasında menü komutları ekleme, sürükleme ve çift tıklama hareketleri için işleyiciler ekleme ve belirli değer türleri veya ilişkiler değiştiğinde tetiklenen kurallar yer alır. Uzantılar Visual Studio Tümleştirme Uzantısı (VSIX) olarak paketlenebilir ve diğer kullanıcılara dağıtılabilir.
Örnek kod ve bu özellik hakkında daha fazla bilgi için bkz. Visual Studio Görselleştirme ve Modelleme SDK'sı.
Çözümü ayarlama
Uzantınızın kodunu içeren bir proje ve projeyi dışarı aktaran bir VSIX projesi ayarlayın. Çözümünüz aynı VSIX'e dahil edilen diğer projeleri içerebilir.
DSL Tasarım Aracı Uzantısı Çözümü oluşturmak için
Sınıf Kitaplığı proje şablonunu kullanarak yeni bir proje oluşturun. Bu proje uzantılarınızın kodunu içerir.
Yeni bir VSIX Projesi projesi oluşturun.
Çözüme Ekle'yi seçin.
Source.extension.vsixmanifest , VSIX bildirim düzenleyicisinde açılır.
İçerik alanının üst kısmında İçerik Ekle'ye tıklayın.
İçerik Ekle iletişim kutusunda İçerik Türü Seç'i MEF Bileşeni olarak, Project'i ise sınıf kitaplığı projenize ayarlayın.
Sürümleri Seç'e tıklayın ve Visual Studio Enterprise'ın işaretli olduğundan emin olun.
VSIX projesinin çözümün Başlangıç projesi olduğundan emin olun.
Sınıf kitaplığı projesinde, aşağıdaki derlemelere başvurular ekleyin:
Microsoft.VisualStudio.CoreUtility
Microsoft.VisualStudio.Modeling.Sdk.11.0
Microsoft.VisualStudio.Modeling.Sdk.Diagrams.11.0
Microsoft.VisualStudio.Modeling.Sdk.DslDefinition.11.0
Microsoft.VisualStudio.Modeling.Sdk.Integration.11.0
System.ComponentModel.Composition
System.Drawing
System.Drawing.Design
System.Windows.Forms
Test ve Dağıtım
Bu konudaki uzantılardan herhangi birini test etmek için çözümü derleyin ve çalıştırın. Visual Studio'nun deneysel bir örneği açılır. Bu örnekte bir DSL çözümü açın. DslDefinition diyagramını düzenleyin. Uzantı davranışı görülebilir.
Uzantıları ana Visual Studio'ya ve diğer bilgisayarlara dağıtmak için şu adımları izleyin:
VSIX yükleme dosyasını, VSIX projenizde bin\*\*.vsix içinde bulun
Bu dosyayı hedef bilgisayara kopyalayın ve ardından Windows Gezgini'nde (veya Dosya Gezgini) çift tıklayın.
Uzantının yüklendiğini onaylamak için Visual Studio Uzantı Yöneticisi açılır.
Uzantıyı kaldırmak için şu adımları izleyin:
Visual Studio'da, Araçlar menüsünde Uzantı Yöneticisi'ne tıklayın.
Uzantıyı seçin ve silin.
Kısayol Menü Komutu Ekle
DSL Tasarım Aracı yüzeyinde veya DSL Gezgini penceresinde bir kısayol menüsü komutunun görünmesini sağlamak için, aşağıdakine benzer bir sınıf yazın.
sınıfı uygulamalı ICommandExtension
ve özniteliğine DslDefinitionModelCommandExtension
sahip olmalıdır.
using System.Collections.Generic;
using System.ComponentModel.Composition;
using System.Linq;
using Microsoft.VisualStudio.Modeling.Diagrams;
using Microsoft.VisualStudio.Modeling.Diagrams.ExtensionEnablement;
using Microsoft.VisualStudio.Modeling.DslDefinition;
using Microsoft.VisualStudio.Modeling.DslDefinition.ExtensionEnablement;
using Microsoft.VisualStudio.Modeling.DslDesigner;
using Microsoft.VisualStudio.Modeling.ExtensionEnablement;
namespace Fabrikam.SimpleDslDesignerExtension
{
/// <summary>
/// Command extending the DslDesigner.
/// </summary>
[DslDefinitionModelCommandExtension]
public class MyDslDesignerCommand : ICommandExtension
{
/// <summary>
/// Selection Context for this command
/// </summary>
[Import]
IVsSelectionContext SelectionContext { get; set; }
/// <summary>
/// Is the command visible and active?
/// This is called when the user right-clicks.
/// </summary>
public void QueryStatus(IMenuCommand command)
{
command.Visible = true;
// Is there any selected DomainClasses in the Dsl explorer?
command.Enabled =
SelectionContext.AtLeastOneSelected<DomainClass>();
// Is there any selected ClassShape on the design surface?
command.Enabled |=
(SelectionContext.GetCurrentSelection<ClassShape>()
.Count() > 0);
}
/// <summary>
/// Executes the command
/// </summary>
/// <param name="command">Command initiating this action</param>
public void Execute(IMenuCommand command)
{
...
}
/// <summary>
/// Label for the command
/// </summary>
public string Text
{
get { return "My Command"; }
}
}
}
Fare Hareketlerini İşleme
Kod, menü komutunun koduna benzer.
[DslDefinitionModelGestureExtension]
class MouseGesturesExtensions : IGestureExtension
{
/// <summary>
/// Double-clicking on a shape representing a Domain model element displays this model element in a dialog box
/// </summary>
/// <param name="targetElement">Shape element on which the user has clicked</param>
/// <param name="diagramPointEventArgs">event args for this double-click</param>
public void OnDoubleClick(ShapeElement targetElement,
DiagramPointEventArgs diagramPointEventArgs)
{
ModelElement modelElement = PresentationElementHelper.
GetDslDefinitionModelElement(targetElement);
if (modelElement != null)
{
MessageBox.Show(string.Format(
"Double clicked on {0}", modelElement.ToString()),
"Model element double-clicked");
}
}
/// <summary>
/// Tells if the DslDesigner can consume the to-be-dropped information
/// </summary>
/// <param name="targetMergeElement">Shape on which we try to drop</param>
/// <param name="diagramDragEventArgs">Drop event</param>
/// <returns><c>true</c> if we can consume the to be dropped data, and <c>false</c> otherwise</returns>
public bool CanDragDrop(ShapeElement targetMergeElement,
DiagramDragEventArgs diagramDragEventArgs)
{
if (diagramDragEventArgs.Data.GetDataPresent(DataFormats.FileDrop))
{
diagramDragEventArgs.Effect = DragDropEffects.Copy;
return true;
}
return false;
}
/// <summary>
/// Processes the drop by displaying the dropped text
/// </summary>
/// <param name="targetMergeElement">Shape on which we dropped</param>
/// <param name="diagramDragEventArgs">Drop event</param>
public void OnDragDrop(ShapeElement targetDropElement, DiagramDragEventArgs diagramDragEventArgs)
{
if (diagramDragEventArgs.Data.GetDataPresent(DataFormats.FileDrop))
{
string[] droppedFiles =
diagramDragEventArgs.Data.
GetData(DataFormats.FileDrop) as string[];
MessageBox.Show(string.Format("Dropped text {0}",
string.Join("\r\n", droppedFiles)), "Dropped Text");
}
}
}
Değer Değişikliklerine Yanıt Verme
Bu işleyicinin düzgün çalışması için bir etki alanı modeli gerekir. Basit bir etki alanı modeli sunuyoruz.
using System.Diagnostics;
using Microsoft.VisualStudio.Modeling;
using Microsoft.VisualStudio.Modeling.DslDefinition;
namespace Fabrikam.SimpleDslDesignerExtension
{
/// <summary>
/// Rule firing when the type of a domain model property is changed. The change is displayed
/// in the debugger (Output window of the Visual Studio instance debugging this extension)
/// </summary>
[RuleOn(typeof(PropertyHasType))]
public class DomainPropertyTypeChangedRule : RolePlayerChangeRule
{
/// <summary>
/// Method called when the Type of a Domain Property
/// is changed by the user in a DslDefinition
/// </summary>
/// <param name="e"></param>
public override void RolePlayerChanged(RolePlayerChangedEventArgs e)
{
// We are only interested in the type
if (e.DomainRole.Id == PropertyHasType.TypeDomainRoleId)
{
PropertyHasType relationship =
e.ElementLink as PropertyHasType;
DomainType newType = e.NewRolePlayer as DomainType;
DomainType oldType = e.OldRolePlayer as DomainType;
DomainProperty property = relationship.Property;
// We write about the Type change in the debugger
Debug.WriteLine(string.Format("The type of the Domain property '{0}' of domain class '{1}' changed from '{2}' to '{3}'",
property.Name,
property.Class.Name,
oldType.GetFullName(false),
newType.GetFullName(false))
} } } );
Aşağıdaki kod basit bir model uygular. Yer tutucuyu değiştirmek için yeni bir GUID oluşturun.
using System;
using System.ComponentModel.Composition;
using Microsoft.VisualStudio.Modeling;
using Microsoft.VisualStudio.Modeling.DslDefinition;
namespace Fabrikam.SimpleDslDesignerExtension
{
/// <summary>
/// Simplest possible domain model
/// needed only for extension rules.
/// </summary>
[DomainObjectId(SimpleDomainModelExtension.DomainModelId)]
public class SimpleDomainModelExtension : DomainModel
{
// Id of this domain model extension
// Please replace this with a new GUID:
public const string DomainModelId =
"00000000-0000-0000-0000-000000000000";
/// <summary>
/// Constructor for the domain model extension
/// </summary>
/// <param name="store">Store in which the domain model will be loaded</param>
public SimpleDomainModelExtension(Store store)
: base(store, new Guid(SimpleDomainModelExtension.DomainModelId))
{
}
/// <summary>
/// Rules brought by this domain model extension
/// </summary>
/// <returns></returns>
protected override System.Type[] GetCustomDomainModelTypes()
{
return new Type[] {
typeof(DomainPropertyTypeChangedRule)
};
}
}
/// <summary>
/// Provider for the DomainModelExtension
/// </summary>
[Export(typeof(DomainModelExtensionProvider))] [ProvidesExtensionToDomainModel(typeof(DslDefinitionModelDomainModel))]
public class SimpleDomainModelExtensionProvider
: DomainModelExtensionProvider
{
/// <summary>
/// Extension model type
/// </summary>
public override Type DomainModelType
{
get
{
return typeof(SimpleDomainModelExtension);
}
}
}
}