Context menus with Data Standard

Data Standard builds on top of WPF (Windows Presentation Foundation), so more or less everything supported by WPF can be done with Data Standard. The options are endless, however today I’d like to introduce context menus.

2014-03-14_08-43-12

Context menus can be configured everywhere on the Data Standard user interface. The interesting thing is that you can have a generic context menu that is accessible in the whole form area, but you can also have very local context menus for certain areas or controls. Basically, you only have to decide to which control you like to add the context menu. In the general case, you probably attach the context menu to the most outside Gird, like this:

<ScrollViewer VerticalScrollBarVisibility="Auto" HorizontalScrollBarVisibility="Auto">
 <ScrollViewer.ContextMenu>
  <ContextMenu>
   <MenuItem Header="Copy to clipboard" Command="{Binding PsCmd[CopyToClipboard]}">
    <MenuItem.Icon>
     <Image Source="C:\ProgramData\Autodesk\Vault 2014\Extensions\DataStandard\Vault\cO.ico"/>
    </MenuItem.Icon>
   </MenuItem>
  <MenuItem Header="Save to CSV" Command="{Binding PsCmd[SaveToCSV]}"/>
 </ContextMenu>
</ScrollViewer.ContextMenu>

In the case of the DataSheet tab, the most outer control is a ScrollViever, which is responsible for scrolling in case the visible area is too small. Anyway, it’s a control and it eposes the ContextMenu property. Well almost every control has such property, so the same would apply to a single TextBox, if you like. Inside the ContextMenu we will define the ContextMenu area and then several MenuItems. Each MenuItem exposes properties such as Header for the menu text, Icon for the picture to be displayed, and Command, which can be bound to a PowerShell function via the PsCmd. Here are the functions:

function CopyToClipboard
{
  $text = @($Prop["Title"].Value,$Prop["Description"].Value,$Prop["Category Name"].Value,$Prop["State"].Value)
  $text = $text -join ","
  [Windows.Forms.Clipboard]::SetText($text)
}

function SaveToCSV
{
  $text = @($Prop["Title"].Value,$Prop["Description"].Value,$Prop["Category Name"].Value,$Prop["State"].Value)
  $text | Export-Csv C:\temp\mycsv.csv
}

The first function copies some properties of the selected file into the clipboard. We use the standard .Net function SetText, which is in the assembly Windows.Forms.Clipboard. Just pass any text to the function and it will be in your clipboard ready to be pasted. As you can see, I collect the several file properties into an array ( @(“…”,”…”,”…”) ) and then transform it into a comma separated string via the –join parameter. You would say “why not create the string as comma separated in the first place?”. Good question, but I was willing to show you this little genial parameter –join which allows you to easily transform an array into a string with the separator you prefer. This are the little things that makes PowerShell so great. For a developer, transforming an array into a string is not a big deal, but for a non-developer, this could be a big headache. Such small arguments, parameters, etc. makes it by far easier to script rather then to develop.

Anyway, now we have 2 menu items that are available across the whole form. In case we like to ha a specific command for a specific control, then it look identical to what we did so far, but for our specific control. For instance, I’d like copying just the title to my clipboard. So, I define a context menu for the TextBox only, like this:

<TextBox Text="{Binding Prop[Title].Value}" Grid.Column="1" Grid.Row="3">
 <TextBox.ContextMenu>
</span><span style="line-height: 1.5;">  <ContextMenu>
   <MenuItem Header="Copy to clipboard" Command="{Binding PsCmd[CopyTitleToClipboard]}">
    <MenuItem.Icon>
     <Image Source="C:\ProgramData\Autodesk\Vault 2014\Extensions\DataStandard\Vault\cO.ico"/>
    </MenuItem.Icon>
   </MenuItem>
  </ContextMenu>
 </TextBox.ContextMenu>
</TextBox></span><span style="line-height: 1.5;">

and here is the according powerShell function:

function CopyTitleToClipboard
{
  [Windows.Forms.Clipboard]::SetText($Prop["Title"].Value)
}

Try it out! You will have 2 menu items for the whole form, and just a single menu item for the TextBox title. So, now It’s up to you. You are free to configure any context menu as you like. Of course you can have nested menu items and separators. Have fun!

And here is the complete code.

This entry was posted in Data Standard, PowerShell. Bookmark the permalink.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s