Welcome Guest!
 VB Helper
 Previous Message All Messages Next Message 
VB Helper Newsletter  Rod Stephens
 May 07, 2009 07:03 PDT 

My book "Beginning Database Design Solutions" got two new, very positive
reviews at Amazon. Check 'em out at:

    
http://www.amazon.com/Beginning-Database-Design-Solutions-Programmer/product-reviews/0470385499/ref=dp_top_cm_cr_acr_txt?ie=UTF8&showViewpoints=1

----------
DevX posted another of my WPF articles:

    WPF Wonders: An Alphabetical Compendium of WPF Controls
    http://www.devx.com/dotnet/Article/41560
    Among many other changes, WPF brings a completely new set of
controls. Learn which controls do what and pick up a few tips on getting
the most out of them in your WPF applications.

    This article summarizes the most useful WPF controls. Some will be
familiar friends (TextBox, Label, Button) but others will be new
acquaintances (StackPanel, BulletDecorator, DocumentViewer).
----------
I've just posted an XAML-only robot arm example. It's pretty cool both
because of what it does and because it uses absolutely no code (other
than XAML code) to control three joints and a hand.

I'm not sure how much farther you could take this article and get
something actually useful out of it but it's impressive that you can get
this far without writing code.
----------
Have a great week and thanks for subscribing!

Rod
RodSte-@vb-helper.com

Books To Keep: http://www.BooksToKeep.com
----------
*** Now Available ***

Beginning Database Design Solutions
http://www.amazon.com/exec/obidos/ASIN/0470385499/vbhelper/

Visual Basic 2008 Programmer's Reference
http://www.amazon.com/exec/obidos/ASIN/0470182628/vbhelper/
==========

    VB.NET Contents:
1. New HowTo: Make a Label use the largest font it can while still
allowing its text to fit in Visual Basic .NET
2. New HowTo: Make a Label use the largest font it can while still
allowing its text to fit allowing wrapping in Visual Basic .NET

    Both Contents:
3. New HowTo: Simulate a robot arm with three rotating joints and a hand
using XAML code
==========
++++++++++
<VB.NET>
++++++++++
==========
1. New HowTo: Make a Label use the largest font it can while still
allowing its text to fit in Visual Basic .NET
http://www.vb-helper.com/howto_net_large_font.html
http://www.vb-helper.com/HowTo/howto_net_large_font.zip

When you change the text in the program's TextBox, the following code
executes. It first creates a Graphics object. It then creates a series
of fonts in increasingly larger sizes and uses the Graphics object's
MeasureString method to see if the text will fit in the Label. When it
finds a font size that's too big, it stops and uses the previous font
size.

' Copy this text into the Label using hte biggest font that will fit.
Private Sub txtSample_TextChanged(ByVal sender As System.Object, ByVal e
As System.EventArgs) Handles txtSample.TextChanged
    Dim txt As String = txtSample.Text

    ' Only bother if there's text.
    If txt.Length > 0 Then
        Dim best_size As Integer = 100

        ' See how much room we have, allowing a bit
        ' for the Label's internal margin.
        Dim wid As Integer = lblSample.DisplayRectangle.Width - 3
        Dim hgt As Integer = lblSample.DisplayRectangle.Height - 3

        ' Make a Graphics object to measure the text.
        Using gr As Graphics = lblSample.CreateGraphics()
            For i As Integer = 10 To 100
                Using test_font As New Font(lblSample.Font.FontFamily,
i)
                    ' See how much space the text would need,
                    ' specifying a maximum width.
                    Dim text_size As SizeF = gr.MeasureString( _
                        txt & "m", test_font)
                    If text_size.Width > wid OrElse text_size.Height >
hgt Then
                        best_size = i - 1
                        Exit For
                    End If
                End Using
            Next i
        End Using

        ' Use that font size.
        lblSample.Font = New Font(lblSample.Font.FontFamily, best_size)
    End If

    ' Display the text.
    lblSample.Text = txt
End Sub

The Label control seems to cheat when it's Font is set to a small font
(under around 9 point). Then it seems to use a font different from the
one that is used by a Graphics object drawing thue same text with the
same font. That makes the code fail to correctly measure the text as it
would be drawn by the Label.

To prevent this problem, the code doesn't use fonts smaller than 9 point
so it won't work for too much text in a small label.
==========
2. New HowTo: Make a Label use the largest font it can while still
allowing its text to fit allowing wrapping in Visual Basic .NET
http://www.vb-helper.com/howto_net_large_font_wrapped.html
http://www.vb-helper.com/HowTo/howto_net_large_font_wrapped.zip

When you change the text in the program's TextBox, the following code
executes. It first creates a Graphics object. It then creates a series
of fonts in increasingly larger sizes and uses the Graphics object's
MeasureString method to see if the text will fit in the Label. The code
specifies the maximum width that the text can use and checks the
resulting height to see if there's room for the text.

When it finds a font size that's too big, it stops and uses the previous
font size.

' Copy this text into the Label using hte biggest font that will fit.
Private Sub txtSample_TextChanged(ByVal sender As System.Object, ByVal e
As System.EventArgs) Handles txtSample.TextChanged
    Dim txt As String = txtSample.Text

    ' Only bother if there's text.
    If txt.Length > 0 Then
        Dim best_size As Integer = 100

        ' See how much room we have, allowing a bit
        ' for the Label's internal margin.
        Dim wid As Integer = lblSample.DisplayRectangle.Width - 3
        Dim hgt As Integer = lblSample.DisplayRectangle.Height - 3

        ' Make a Graphics object to measure the text.
        Using gr As Graphics = lblSample.CreateGraphics()
            For i As Integer = 10 To 100
                Using test_font As New Font(lblSample.Font.FontFamily,
i)
                    ' See how much space the text would need,
                    ' specifying a maximum width.
                    Dim text_size As SizeF = gr.MeasureString( _
                        txtSample.Text, test_font, wid)
                    If text_size.Height > hgt Then
                        best_size = i - 1
                        Debug.WriteLine(best_size)
                        Exit For
                    End If
                End Using
            Next i
        End Using

        ' Use that font size.
        lblSample.Font = New Font(Me.Font.FontFamily, best_size)
    End If

    ' Display the text.
    lblSample.Text = txt
End Sub

The Label control seems to cheat when it's Font is set to a small font
(under around 9 point). Then it seems to use a font different from the
one that is used by a Graphics object drawing thue same text with the
same font. That makes the code fail to correctly measure the text as it
would be drawn by the Label.

To prevent this problem, the code doesn't use fonts smaller than 9 point
so it won't work for too much text in a small label.
==========
++++++++++
<Both>
++++++++++
==========
3. New HowTo: Simulate a robot arm with three rotating joints and a hand
using XAML code
http://www.vb-helper.com/howto_xaml_robot_arm.html
http://www.vb-helper.com/HowTo/howto_xaml_robot_arm.zip

(Picture at http://www.vb-helper.com/howto_xaml_robot_arm.jpg.)

The basic idea is to consider the stages of the arm one after another
and use transformations to move from one to the next.

Suppose the three arm segments have lengths L1, L2, and L3 and the
angles of rotation at the three joints are A1, A2, and A3.

The first joint rotates the arm by angle A1 at a fixed shoulder. The
second joint is translated distance L1 away in the direction of the
first arm segment.

The second joint rotates the arm by angle A2 at the "elbow." The third
joint is translated distance L2 away in the direction of the second arm
segment.

The third joint rotates the arm by angle A3 at the "wrist." The end of
the arm is translated distance L3 away in the direction of the third arm
segment.

-----

To draw the arm, start by drawing the shoulder at the origin. This
example adds a translation first to center the shoulder in the drawing
area.

Next the code applies the rotation A1 at the shoulder and draws a
rectangle representing the first arm segment. There are is one tricky
issue here.

The rotation is <B>prepended</B> to the previous translation so the
rotation occurs before the translation that centers the shoulder.
Imagine the arm in its own world coordinate space with the shoulder at
the origin. The program draws a horizontal rectangle representing the
first arm segment. The transformations then rotate it to the correct
angle and translate it so the shoulder is centered. This puts the first
arm segment in the correct position.

Next the code must draw the elbow joint. To do this, it <B>prepends</B>
a translation of distance L1 in the X direction and 0 in the Y
direction. It then draws the elbow joint at the origin.

Again imagine the arm in world coordinate space and suppose you draw the
elbow at the origin. The new translation moves the joint to (L1, 0). The
rotation of angle A1 rotates the joint to match the rotation of the
first arm segment. Finally the shoulder's translation moves the whole
thing so the base of the first arm segment is centered in the drawing
area.

The code continues like this as many times as necessary to draw each arm
segment and joint. In eachv step, it prepends the new translations and
rotations.

-----

The following code shows how the program draws the third arm segment.
Notice how is uses binding to use the angles selected by the slider
controls sliJoint1, sliJoint2, and sliJoint3. The values L1 and L2 are
static resource values giving the arm lengths. The values Cx and Cy give
the center of the drawing area.

<!-- Third arm segment -->
<Line X1="0" Y1="0" X2="{StaticResource L3}" Y2="0">
<Line.RenderTransform>
    <TransformGroup>
      <RotateTransform Angle="{Binding ElementName=sliJoint3,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L2}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint2,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L1}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint1,
Path=Value}"/>
      <TranslateTransform X="{StaticResource Cx}" Y="{StaticResource
Cy}"/>
    </TransformGroup>
</Line.RenderTransform>
</Line>

The code finishes by drawing a hand with two fingers. As it does for the
rest of the arm, the code draws the pieces of the hand at the origin and
uses transformations to move it where it belongs. The following code
shows how the program draws the hand. There are lots of details but the
only real tricks is how the program draws Finger 1. The sliHand slider
control determines how far apart the fingers are. The program uses its
value directly to draw Finger 2. To draw Finger 1, it uses a
ScaleTransform to reflect the translation across the X axis, making the
finger move the negative of the distances selected by sliHand.

<!-- Hand - Palm -->
<Line X1="0" Y1="-15" X2="0" Y2="15" Stroke="Black" StrokeThickness="3">
<Line.RenderTransform>
    <TransformGroup>
      <TranslateTransform X="{StaticResource L3}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint3,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L2}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint2,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L1}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint1,
Path=Value}"/>
      <TranslateTransform X="{StaticResource Cx}" Y="{StaticResource
Cy}"/>
    </TransformGroup>
</Line.RenderTransform>
</Line>

<!-- Hand - Finger 1 -->
<Line X1="0" Y1="0" X2="20" Y2="0" Stroke="Black" StrokeThickness="3">
<Line.RenderTransform>
    <TransformGroup>
      <TranslateTransform X="0" Y="{Binding ElementName=sliHand,
Path=Value}"/>
      <ScaleTransform ScaleX="1" ScaleY="-1"/>
      <TranslateTransform X="{StaticResource L3}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint3,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L2}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint2,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L1}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint1,
Path=Value}"/>
      <TranslateTransform X="{StaticResource Cx}" Y="{StaticResource
Cy}"/>
    </TransformGroup>
</Line.RenderTransform>
</Line>

<!-- Hand - Finger 2 -->
<Line X1="0" Y1="0" X2="20" Y2="0" Stroke="Black" StrokeThickness="3">
<Line.RenderTransform>
    <TransformGroup>
      <TranslateTransform X="0" Y="{Binding ElementName=sliHand,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L3}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint3,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L2}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint2,
Path=Value}"/>
      <TranslateTransform X="{StaticResource L1}" Y="0"/>
      <RotateTransform Angle="{Binding ElementName=sliJoint1,
Path=Value}"/>
      <TranslateTransform X="{StaticResource Cx}" Y="{StaticResource
Cy}"/>
    </TransformGroup>
</Line.RenderTransform>
</Line>
==========
Archives:
    http://www.topica.com/lists/VBHelper
    http://www.topica.com/lists/VB6Helper
    http://www.topica.com/lists/VBNetHelper

Post questions at:
    http://www.topica.com/lists/VBHelperQA
	
 Previous Message All Messages Next Message 
  Check It Out!

  Topica Channels
 Best of Topica
 Art & Design
 Books, Movies & TV
 Developers
 Food & Drink
 Health & Fitness
 Internet
 Music
 News & Information
 Personal Finance
 Personal Technology
 Small Business
 Software
 Sports
 Travel & Leisure
 Women & Family

  Start Your Own List!
Email lists are great for debating issues or publishing your views.
Start a List Today!

© 2001 Topica Inc. TFMB
Concerned about privacy? Topica is TrustE certified.
See our Privacy Policy.