Home
Search
 
What's New
Index
Books
Links
Q & A
Newsletter
Banners
 
Feedback
Tip Jar
 
C# Helper...
 
XML RSS Feed
Follow VBHelper on Twitter
 
 
 
MSDN Visual Basic Community
 
 
 
 
 
TitlePreview and print a core sample report with Visual Basic 2005
DescriptionThis example shows how to preview and print a core sample report with Visual Basic 2005.
Keywordsprint, preview, core sample, VB 2005
CategoriesVB.NET, Graphics
 
This example displays a core sample report showing various notations at different core depths, together with graphics hilighting different soil types.

The form contains a PrintPreviewDialog control named ppdCoreSample. At design time, its Document property was set to the PrintDocument object pdocCoreSample.

When you click the Preview button, the following code executes. It calls subroutine DefineData to build some sample data. It then sets the PrintPreview dialog's size, sets it to appear maximized, and shows the dialog.

 
' Make and display some data.
Private Sub btnPreview_Click(ByVal sender As System.Object, _
    ByVal e As System.EventArgs) Handles btnPreview.Click
    ' Define the data.
    DefineData()

    ' Display the preview.
    ppdCoreSample.Width = 800
    ppdCoreSample.Height = 600
    DirectCast(ppdCoreSample, Form).WindowState = _
        FormWindowState.Maximized
    ppdCoreSample.ShowDialog()
End Sub
 
The program stores information aboout a core sample layer in a CoreLayer object. The class's only constructor simply initializes the object's fields.
 
Private Class CoreLayer
    Public Thickness As Single      ' Feet.
    Public Recovery As Single       ' Shown as a percent.
    Public Moisture As String       ' d, m, w, or s.
    Public Plasticity As Single     ' ?
    Public PID As Integer           ' PPM.
    Public FillStyle As Drawing2D.HatchStyle
    Public AstmClass As AstmClassifications
    Public Description As String

    ' Constructor omitted ...
End Class
 
Subroutine DefineData initializes an array of CoreLayer objects.
 
' Define the data.
Private m_CoreData() As CoreLayer
Private Sub DefineData()
    m_CoreData = New CoreLayer() { _
        New CoreLayer(0.5, -1, "d", -1, -1, Nothing, _
            AstmClassifications.None, "Crushed stone and " & _
            "fill."), _
        New CoreLayer(2, -1, "d", -1, 4, _
            HatchStyle.DiagonalCross, _
            AstmClassifications.ML, "SILT w/fine sand, not " & _
            "hard, crumbly, dark brown, no odor."), _
        ... others omitted...
    }
End Sub
 
When the PrintPreviewDialog is displayed, it raises the PrintDocument object's PrintPage event handler shown in the following code to generate printed pages. The code starts by drawing a string in the page's top area. In a real application, this would include information about the sample.

Next the code makes a font and StringFormat object to use while drawing text. It calls subroutine DrawRotatedString, described shortly, to draw header text for each of the report's columns. It passes in X and Y coordinates to position each column header. DrawRotatedString automatically increases the X coordinate (it's passed ByRef) after it draws a header so the next header is moved to the right.

The program draws the ground line. It then loops through the CoreLayer objects, calling subroutine DrawSample for each. It draws depth marks to show the depth every five feet and draws a box around the whole thing.

Finally the code draws some summary text at the bottom. It sets e.HasMorePages = False so the printout ends after this page.

 
Private Const COL_WID As Integer = 30
Private Const HEADER_HGT As Integer = 100
Private Const Y_SCALE As Single = 20    ' Pixels per foot
    ' vertically.
Private Const MAX_FEET As Single = 30

Private Sub pdocCoreSample_PrintPage(ByVal sender As _
    System.Object, ByVal e As _
    System.Drawing.Printing.PrintPageEventArgs) Handles _
    pdocCoreSample.PrintPage
    Dim xmin As Integer = e.MarginBounds.Left
    Dim xmax As Integer = e.MarginBounds.Right
    Dim y As Integer = e.MarginBounds.Top

    ' Draw top area here.
    Using the_font As New Font("Times New Roman", 20, _
        FontStyle.Regular)
        e.Graphics.DrawString("Top stuff goes here...", _
            the_font, Brushes.Black, xmin, y)
        ' ...

        y += 150
    End Using

    ' Draw the core data area.
    Dim ymin As Integer = y
    Using the_font As New Font("Times New Roman", 10, _
        FontStyle.Regular)
        Using center_format As New StringFormat()
            center_format.Alignment = StringAlignment.Center
            center_format.LineAlignment = _
                StringAlignment.Center

            ' Draw column headers.
            Dim x As Integer = xmin + COL_WID \ 2
            y += HEADER_HGT \ 2
            DrawRotatedString(e.Graphics, the_font, _
                center_format, x, y, "Depth (feet)")
            DrawRotatedString(e.Graphics, the_font, _
                center_format, x, y, "Recovery %")
            DrawRotatedString(e.Graphics, the_font, _
                center_format, x, y, "Moisture")
            DrawRotatedString(e.Graphics, the_font, _
                center_format, x, y, "Plasticity")
            DrawRotatedString(e.Graphics, the_font, _
                center_format, x, y, "PID (ppm)")
            DrawRotatedString(e.Graphics, the_font, _
                center_format, x, y, "Graphic Log")
            DrawRotatedString(e.Graphics, the_font, _
                center_format, x, y, "ASTM Class.")

            y += HEADER_HGT \ 2
            e.Graphics.DrawLine(Pens.Black, xmin, y, xmax, _
                y)

            xmin = e.MarginBounds.Left
            Dim y0 As Integer = y + 0.5 * Y_SCALE
            y = y0

            ' Draw the ground line.
            Using ground_pen As New Pen(Color.Black)
                ground_pen.DashStyle = DashStyle.Custom
                ground_pen.DashPattern = New Single() {25, _
                    25}
                e.Graphics.DrawLine(ground_pen, xmin + _
                    COL_WID, y0, xmax, y0)
            End Using

            ' Draw the ground line's "0".
            e.Graphics.DrawString("0", the_font, _
                Brushes.Black, xmin + COL_WID \ 2, y, _
                center_format)

            ' Draw sample data.
            Dim total_feet As Single = 0
            For i As Integer = 0 To m_CoreData.Length - 1
                DrawSample(e.Graphics, m_CoreData(i), xmin, _
                    y, xmax, the_font, center_format, _
                    total_feet)
            Next i

            ' Draw depth markers.
            For i As Integer = 5 To MAX_FEET - 5 Step 5
                y = y0 + Y_SCALE * i
                e.Graphics.DrawLine(Pens.Black, xmin + _
                    COL_WID, y, xmin + 2 * COL_WID, y)
                e.Graphics.DrawString(i.ToString, the_font, _
                    Brushes.Black, xmin + COL_WID \ 2, y, _
                    center_format)
            Next i

            ' Draw lines and a box around everything.
            y = y0 + MAX_FEET * Y_SCALE
            ' Box.
            e.Graphics.DrawRectangle(Pens.Black, xmin, _
                ymin, xmax - xmin, y - ymin)
            ' Column lines.
            For i As Integer = 1 To 7
                x = xmin + COL_WID * i
                e.Graphics.DrawLine(Pens.Black, x, ymin, x, _
                    y)
            Next i
        End Using
    End Using

    ' Draw bottom area here.
    y += 20
    Using the_font As New Font("Times New Roman", 20, _
        FontStyle.Regular)
        e.Graphics.DrawString("Bottom stuff goes here...", _
            the_font, Brushes.Black, xmin, y)
        ' ...
    End Using

    e.HasMorePages = False
End Sub
 
Subroutine DrawRotatedString draws a string rotated 90 degrees. It applies a rotation transformation to the Graphics object to rotate the text 90 degrees and a translation transformation to move the text to its desired location. It then draws the text centered at the origin. The Graphics object's transformations rotate the text and move it to the proper position.

The subroutine resets the Graphics object's transformation to remove the rotation and translation, and it increases the X coordinate so the next column header appears to the right.

 
' Draw a string centered at the given position rotated 90
' degrees.
' Increment x by COL_WID.
Private Sub DrawRotatedString(ByVal gr As Graphics, ByVal _
    the_font As Font, ByVal center_format As StringFormat, _
    ByRef x As Integer, ByVal y As Integer, ByVal txt As _
    String)
    gr.RotateTransform(-90)
    gr.TranslateTransform(x, y, MatrixOrder.Append)
    gr.DrawString(txt, the_font, Brushes.Black, 0, 0, _
        center_format)

    gr.ResetTransform()
    x += COL_WID
End Sub
 
Subroutine DrawSample draws the data for a CoreLayer object. It draws a line to mark the sample's end depth and draws appropriate text in the sample's columns. The subroutine fills the area in the graphic log column with the CoreLayer's hatch pattern.
 
' Draw a sample.
Private Sub DrawSample(ByVal gr As Graphics, ByVal _
    core_data As CoreLayer, ByVal x1 As Integer, ByVal y1 _
    As Single, ByVal x2 As Single, ByVal the_font As Font, _
    ByVal center_format As StringFormat, ByRef total_feet _
    As Single)
    ' Divider line below.
    Dim ymin As Integer = y1 + total_feet * Y_SCALE
    Dim ymax As Integer = ymin + core_data.Thickness * _
        Y_SCALE
    gr.DrawLine(Pens.Black, x1 + COL_WID * 2, ymax, x2, _
        ymax)

    Dim ymid As Integer = ymin + (core_data.Thickness * _
        Y_SCALE) \ 2
    Dim xmid As Integer = x1 + COL_WID + COL_WID \ 2

    ' % Recovery.
    If core_data.Recovery >= 0 Then
        gr.DrawString(core_data.Recovery.ToString(), _
            the_font, Brushes.Black, xmid, ymid, _
                center_format)
    End If

    ' Moisture.
    xmid += COL_WID
    gr.DrawString(core_data.Moisture, _
        the_font, Brushes.Black, xmid, ymid, center_format)

    ' Plasticity.
    xmid += COL_WID
    If core_data.Plasticity >= 0 Then
        gr.DrawString(core_data.Plasticity.ToString(), _
            the_font, Brushes.Black, xmid, ymid, _
                center_format)
    End If

    ' PID.
    xmid += COL_WID
    If core_data.PID >= 0 Then
        gr.DrawString(core_data.PID.ToString(), _
            the_font, Brushes.Black, xmid, ymid, _
                center_format)
    End If

    ' Graphic log.
    xmid += COL_WID
    If core_data.FillStyle <> Nothing Then
        Using fill_brush As New _
            HatchBrush(core_data.FillStyle, Color.Black, _
            Color.White)
            Dim xmin As Integer = x1 + 5 * COL_WID
            gr.FillRectangle(fill_brush, xmin, ymin, _
                COL_WID, ymax - ymin)
        End Using
    End If

    ' ASTM classification.
    xmid += COL_WID
    If core_data.AstmClass <> AstmClassifications.None Then
        gr.DrawString(core_data.AstmClass.ToString(), _
            the_font, Brushes.Black, xmid, ymid, _
                center_format)
    End If

    ' Description.
    Using descr_format As New StringFormat()
        descr_format.Alignment = StringAlignment.Near
        descr_format.LineAlignment = StringAlignment.Center

        Dim x As Integer = x1 + 7 * COL_WID + 4
        xmid += COL_WID
        Dim rect As New Rectangle(x, ymin, x2 - x - 8, ymax _
            - ymin)
        gr.DrawString(core_data.Description, _
            the_font, Brushes.Black, rect, descr_format)
    End Using

    total_feet += core_data.Thickness
End Sub
 
 
Copyright © 1997-2006 Rocky Mountain Computer Consulting, Inc.   All rights reserved.
  Updated