Click or drag to resize

Using images in reference topics

The instructions on this page are based on sample code that demonstrates how to install the ImageTools, and how to use them to insert images in Sandcastle reference topics.

The sample is located here.

It includes what follows.

Installing the Image Tools

Install the target version of SHFB

Each release of Novacta.Documentation.ShfbTools targets a specific version of SHFB. Such target version always matches the version of the tools.

Make sure that the SHFB version targeted by the tools is currently installed on your host machine.

You can download the required SHFB release here.

Add the Image Tools to SHFB

Create a console application targeting the .NET Framework, version 4.6.2. In this tutorial, such application is represented by project ImageToolsInstaller.

Add to your console project a reference to the Novacta.Documentation.ShfbTools NuGet package. Remember that, at present, the tools are versioned as pre-release software. Follow these instructions to include pre-release versions when installing the tools.

Request full administration permissions for the console application: add to the project an app.manifest file as follows.

app.manifest
<?xml version="1.0" encoding="utf-8"?>
<assembly manifestVersion="1.0" xmlns="urn:schemas-microsoft-com:asm.v1">
  <assemblyIdentity version="1.0.0.0" name="MyApplication.app"/>
  <trustInfo xmlns="urn:schemas-microsoft-com:asm.v2">
    <security>
      <requestedPrivileges xmlns="urn:schemas-microsoft-com:asm.v3">
        <requestedExecutionLevel level="requireAdministrator" uiAccess="false" />
      </requestedPrivileges>
    </security>
  </trustInfo>

  <compatibility xmlns="urn:schemas-microsoft-com:compatibility.v1">
    <application>
    </application>
  </compatibility>
</assembly>

In your Program class, the implementation of method Main should resemble what follows.

ImageToolsInstaller\Program.cs
using Novacta.Documentation.ShfbTools;
using System;

namespace ImageToolsInstaller
{
    class Program
    {
        static void Main(string[] args)
        {
            // It is assumed that the version of SHFB
            // targeted by the SHFB Tools
            // is installed on the host machine.

            // To install the Image Tools.
            ImageTools.Install();

            Console.ReadKey();
        }
    }
}

When the application is executed, its console output shows a report signaling if the installation was successful. If failure conditions are reported, please act to remove them and try again.

Managing images in reference topics

SHFB documentation projects support the use of images in conceptual topics by exploiting MAML media elements. For example, in the documentation project SampleClassLibrary.Documentation the following conceptual topic refers to the image Function.png at line 34:

SampleClassLibrary.Documentation\Content\OperatingOnIntegers.aml
 1<?xml version="1.0" encoding="utf-8"?>
 2<topic id="b10d4d75-3729-4247-a58a-b9e5b6e4bb4d" revisionNumber="1">
 3  <developerConceptualDocument
 4    xmlns="http://ddue.schemas.microsoft.com/authoring/2003/5"
 5    xmlns:xlink="http://www.w3.org/1999/xlink"
 6    xmlns:ltx="http://www.novacta.net/2018/XSL/ShfbLatexTools">
 7
 8    <introduction>
 9      <para>
10        Class <codeEntityReference qualifyHint="false">
11          T:SampleClassLibrary.IntegerOperation
12        </codeEntityReference> provides method
13        <codeEntityReference qualifyHint="false">
14          M:SampleClassLibrary.IntegerOperation.Operate(System.Func{System.Int32,System.Int32},System.Int32)
15        </codeEntityReference>
16        to manage operations on integer values.
17      </para>
18      <para>
19        In the following example, an integer is squared
20        executing the <codeEntityReference qualifyHint="false">
21          M:SampleClassLibrary.IntegerOperation.Operate(System.Func{System.Int32,System.Int32},System.Int32)
22        </codeEntityReference> method.
23        This is equivalent to define the applied function,
24        say <ltx:latex mode="inline">f:\mathbb{N}\rightarrow \mathbb{N},</ltx:latex>
25        as <ltx:latex>\forall n \in \mathbb{N}: n \mapsto f\left(n\right)=n^2.</ltx:latex>
26        In addition, input validation is also checked.
27      </para>
28      <code source="..\SampleClassLibrary\IntegerOperationExample.cs.txt"
29        language="cs" title="C#" />
30      <para>
31        A representation of the applied function is plotted as follows.
32      </para>
33      <mediaLink>
34        <image xlink:href="Function"/>
35      </mediaLink>
36    </introduction>
37
38    <relatedTopics>
39      <link xlink:href="4c3871a5-d7c6-477c-96ee-e71f0a67f7a8" />
40    </relatedTopics>
41
42  </developerConceptualDocument>
43</topic>

Note that the image file has been added to the sub-folder media, and its property 'Build Action' set to 'Image'.

Media elements are specific to conceptual topics. However, provided that the property 'Copy To Media' of an image file has been set to 'True', then the same image can also be inserted in Sandcastle reference topics and managed by the ImageTools, since they introduce an analog <image> element which can be inserted in the XML comments on your code:

XML
<image>
  <src>Function.png</src>
  <alt>My function</alt>
  <width>100%</width>
</image>

A nested element tagged <src> is mandatory, and defines the source of the image. Nested nodes tagged <alt> and <width>, used to specify image's alternate text and width, are instead optional. Such child elements correspond to attributes of the HTML <img> element by which the images are actually represented in the outputted documentation files.

More thoroughly, <image> elements are transformed in different ways, depending on the available presentation styles and their corresponding help file formats. For example, for styles VS2010 and VS2013 having Website as a help output, the element discussed above is transformed into

XML
<img src="../media/Function.png" alt ="My function" width="100%"></img>

while, for output MsHelpViewer, it becomes

XML
<img src="media/Function.png" alt ="My function" width="100%"></img>

As an example, the following file printout shows the source code for type IntegerOperation, as defined in project SampleClassLibrary:

SampleClassLibrary\IntegerOperation.cs
 1using System;
 2
 3namespace SampleClassLibrary
 4{
 5    /// <summary>
 6    /// Provides a method to operate on integers.
 7    /// </summary>
 8    public static class IntegerOperation
 9    {
10        /// <summary>
11        /// Applies the specified function to the given operand.
12        /// </summary>
13        /// <param name="func">The function.</param>
14        /// <param name="operand">The operand.</param>
15        /// <returns>The result of the operation.</returns>
16        /// <exception cref="ArgumentNullException">
17        /// <paramref name="func"/> is <b>null</b>.</exception>
18        /// <example>
19        /// <para>
20        /// In the following example, the applied function, say 
21        /// <latex mode='inline'>f:\mathbb{N}\rightarrow \mathbb{N},</latex> is defined as
22        /// <latex mode='display'>
23        /// \forall n \in \mathbb{N}: n \mapsto f\left(n\right)=n^2.
24        /// </latex>
25        /// A plot of such function is displayed in the following
26        /// figure.
27        /// <image>
28        /// <alt>A function.</alt>
29        /// <src>Function.png</src>
30        /// <width>100%</width>
31        /// </image>
32        /// An integer is thus squared 
33        /// executing the <see cref="Operate(Func{int, int}, int)"/> method.
34        /// In addition, input validation is also checked.
35        /// </para>
36        /// <para>
37        /// <code language="cs">
38        /// using System;
39        /// namespace SampleClassLibrary.CodeExamples
40        /// {
41        ///     public class IntegerOperationExample
42        ///     {
43        ///         public void Main()
44        ///         {
45        ///             // Define an operator that squares its operand
46        ///             Func<![CDATA[<]]>int, int> square = (int operand) => operand * operand;
47        /// 
48        ///             // Define an operand
49        ///             int integer = 2;
50        /// 
51        ///             // Operate on it
52        ///             Console.WriteLine("Squaring {0}...", integer);
53        ///             int result = IntegerOperation.Operate(square, integer);
54        ///             Console.WriteLine("...the result is {0}.", result);
55        /// 
56        ///             // Check that an operator cannot be null
57        ///             try
58        ///             {
59        ///                 IntegerOperation.Operate(null, 0);
60        ///             }
61        ///             catch (Exception e)
62        ///             {
63        ///                 Console.WriteLine();
64        ///                 Console.WriteLine("Cannot apply a null function:");
65        ///                 Console.WriteLine(e.Message);
66        ///             }
67        ///         }
68        ///     }
69        /// }
70        ///  
71        /// // Executing method Main() produces the following output:
72        /// // 
73        /// // Squaring 2...
74        /// // ...the result is 4.
75        /// // 
76        /// // Cannot apply a null function:
77        /// // Value cannot be null.
78        /// // Parameter name: func
79        /// </code>
80        /// </para>
81        /// </example>
82        public static int Operate(Func<int, int> func, int operand)
83        {
84            if (func==null)
85            {
86                throw new ArgumentNullException(nameof(func));
87            }
88            return func(operand);
89        }
90    }
91}

Note the <image> element at lines 27-31 in the XML comments on method Operate. You can check here how the corresponding documentation looks like.