wpf中的条形码生成器

发布于 2024-10-01 14:00:01 字数 31 浏览 0 评论 0原文

在wpf中生成各种类型的条形码的最佳方法是什么?

What the best method to genearate barcode in various type in wpf.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

俏︾媚 2024-10-08 14:00:01

条形码字体是一种简单的方法,但部署起来可能很困难,因为客户可能需要在运行应用程序的每台计算机上安装该字体。这可能不切实际,特别是对于 XBAP、Silverlight 和 WinPhone7 部署。

在 WPF 中自己生成条形码非常容易。虽然它可以用纯 XAML 完成,但我发现使用 XAML 和代码的混合是最简单的。

从接受字符并返回条形画笔和宽度的转换器开始:

public class BarcodeConverter : IValueConverter
{
  public static readonly BarcodeConverter Instance = new BarcodeConverter();

  Dictionary<char, string> _codes = new Dictionary<char, string>
  {
    { '0', "nnnwwnwnn" },
    { '1', "wnnwnnnnw" },
    { '2', "nnwwnnnnw" },
    // etc
    { 'A', "wnnnnwnnw" },
    { 'B', "nnwnnwnnw" },
    // etc
  };

  public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
  {
    string code;
    if(!_codes.TryGetValue((char)value, out code)) return null;

    return
      from i in Enumerable.Range(0, code.Length)
      select new
      {
        color = i%2==0 ? Brushes.Black : Brushes.Transparent,
        width = code[i]=='n' ? 5 : 10,
      };
  }
  public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
  {
    throw new NotImplementedException();
  }
}

现在构建条形的 XAML 很简单:

<ItemsPanelTemplate x:Key="HorizontalPanel">
  <StackPanel Orientation="Horizontal"/>
</ItemsPanelTemplate>

<DataTemplate x:Key="SingleBarTemplate">
  <Rectangle Fill="{Binding color}" Width="{Binding width}" />
</DataTemplate>

<DataTemplate x:Key="SingleCodeTemplate">
  <DockPanel>
    <TextBlock DockPanel.Dock="Bottom" Text="{Binding}" />  <!-- Display character at bottom of code -->
    <ItemsControl ItemsSource="{Binding Converter={x:Static my:BarcodeConverter.Instance}}"
                  ItemsPanel="{StaticResource HorizontalPanel}"
                  ItemTemplate="{StaticResource SingleBarTemplate}" />
  </DockPanel>
</DataTemplate>

<DataTemplate x:Key="BarcodeTemplate">
  <ItemsControl ItemsSource="{Binding}"
                ItemsPanel="{StaticResource HorizontalPanel}"
                ItemTemplate="{StaticResource SingleBarTemplate}"
                Height="60" />
</DataTemplate>

BarcodeTemplate 可以与 ContentPresenter 一起使用来显示任何字符串,例如:

<ContentPresenter Content="123456789"
                  ContentTemplate="{StaticResource BarcodeTemplate}" />

或者

<ContentPresenter Content="{Binding UPCCode}"
                  ContentTemplate="{StaticResource BarcodeTemplate}" />

我认为这个解决方案是在 WPF 中生成条形码的“最佳方法”,因为:

  1. 它简单且独立,
  2. 它不依赖于计算机上安装的字体,并且
  3. 它可以在任何 WPF 或 Silverlight 实现上工作。

Barcode fonts are an easy way to do it, but they can be difficult to deploy because the customer will probably need the font installed on each machine that runs your application. This can be impractical, particularly for XBAP, Silverlight, and WinPhone7 deployments.

It is quite easy to generate the barcodes yourself in WPF. Although it can be done in pure XAML, I find it simplest using a mixture of XAML and code.

Start with a converter that takes a character and returns the bar brushes and widths:

public class BarcodeConverter : IValueConverter
{
  public static readonly BarcodeConverter Instance = new BarcodeConverter();

  Dictionary<char, string> _codes = new Dictionary<char, string>
  {
    { '0', "nnnwwnwnn" },
    { '1', "wnnwnnnnw" },
    { '2', "nnwwnnnnw" },
    // etc
    { 'A', "wnnnnwnnw" },
    { 'B', "nnwnnwnnw" },
    // etc
  };

  public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
  {
    string code;
    if(!_codes.TryGetValue((char)value, out code)) return null;

    return
      from i in Enumerable.Range(0, code.Length)
      select new
      {
        color = i%2==0 ? Brushes.Black : Brushes.Transparent,
        width = code[i]=='n' ? 5 : 10,
      };
  }
  public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
  {
    throw new NotImplementedException();
  }
}

Now the XAML to construct the bars is trivial:

<ItemsPanelTemplate x:Key="HorizontalPanel">
  <StackPanel Orientation="Horizontal"/>
</ItemsPanelTemplate>

<DataTemplate x:Key="SingleBarTemplate">
  <Rectangle Fill="{Binding color}" Width="{Binding width}" />
</DataTemplate>

<DataTemplate x:Key="SingleCodeTemplate">
  <DockPanel>
    <TextBlock DockPanel.Dock="Bottom" Text="{Binding}" />  <!-- Display character at bottom of code -->
    <ItemsControl ItemsSource="{Binding Converter={x:Static my:BarcodeConverter.Instance}}"
                  ItemsPanel="{StaticResource HorizontalPanel}"
                  ItemTemplate="{StaticResource SingleBarTemplate}" />
  </DockPanel>
</DataTemplate>

<DataTemplate x:Key="BarcodeTemplate">
  <ItemsControl ItemsSource="{Binding}"
                ItemsPanel="{StaticResource HorizontalPanel}"
                ItemTemplate="{StaticResource SingleBarTemplate}"
                Height="60" />
</DataTemplate>

The BarcodeTemplate can be used with a ContentPresenter to display any string, for example:

<ContentPresenter Content="123456789"
                  ContentTemplate="{StaticResource BarcodeTemplate}" />

or

<ContentPresenter Content="{Binding UPCCode}"
                  ContentTemplate="{StaticResource BarcodeTemplate}" />

I would argue that this solution is the "best method" to generate barcodes in WPF because:

  1. It is simple and self-contained,
  2. It does not rely on a font being installed on the computer, and
  3. It can work on any WPF or Silverlight implementation.
蹲墙角沉默 2024-10-08 14:00:01

以下是我最终得到的:

<Window x:Class="ScratchClient.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="655.85" Width="687"
    xmlns:local="clr-namespace:ScratchClient">
<Window.Resources>
    <local:BarcodeConverter x:Key="barcodeConverter"/>
    <ItemsPanelTemplate x:Key="HorizontalPanel">
        <StackPanel Orientation="Horizontal" HorizontalAlignment="Center"/>
    </ItemsPanelTemplate>
    <DataTemplate x:Key="SingleBarTemplate">
        <Rectangle Fill="{Binding color}" Width="{Binding width}" />
    </DataTemplate>
    <DataTemplate x:Key="SingleCodeTemplate">
        <DockPanel>
            <TextBlock DockPanel.Dock="Bottom" Text="{Binding}" />
            <ItemsControl ItemsSource="{Binding Converter={StaticResource barcodeConverter}}"
              ItemsPanel="{StaticResource HorizontalPanel}"
              ItemTemplate="{StaticResource SingleBarTemplate}" />
        </DockPanel>
    </DataTemplate>
    <DataTemplate x:Key="BarcodeTemplate">
        <ItemsControl ItemsSource="{Binding}"
            ItemsPanel="{StaticResource HorizontalPanel}"
            ItemTemplate="{StaticResource SingleCodeTemplate}"
            Height="100" />
    </DataTemplate>
</Window.Resources>
<Grid>
    <ContentPresenter Name="barcode" Content="*WIKIPEDIA*" ContentTemplate="{StaticResource BarcodeTemplate}">
        <ContentPresenter.RenderTransform>
            <ScaleTransform ScaleX="2" ScaleY="2"></ScaleTransform>
        </ContentPresenter.RenderTransform>
    </ContentPresenter>
</Grid>

public class BarcodeConverter : IValueConverter
{
    //W Wide - Black
    //N Narrow - Black
    //w Wide - White
    //n Narrow - White
    #region code details
    Dictionary<char, string> _codes = new Dictionary<char, string>
    {
        {'0',"NnNwWnWnN"},
        {'1',"WnNwNnNnW"},
        {'2',"NnWwNnNnW"},
        {'3',"WnWwNnNnN"},
        {'4',"NnNwWnNnW"},
        {'5',"WnNwWnNnN"},
        {'6',"NnWwWnNnN"},
        {'7',"NnNwNnWnW"},
        {'8',"WnNwNnWnN"},
        {'9',"NnWwNnWnN"},
        {'A',"WnNnNwNnW"},
        {'B',"NnWnNwNnW"},
        {'C',"WnWnNwNnN"},
        {'D',"NnNnWwNnW"},
        {'E',"WnNnWwNnN"},
        {'F',"NnWnWwNnN"},
        {'G',"NnNnNwWnW"},
        {'H',"WnNnNwWnN"},
        {'I',"NnWnNwWnN"},
        {'J',"NnNnWwWnN"},
        {'K',"WnNnNnNwW"},
        {'L',"NnWnNnNwW"},
        {'M',"WnWnNnNwN"},
        {'N',"NnNnWnNwW"},
        {'O',"WnNnWnNwN"},
        {'P',"NnWnWnNwN"},
        {'Q',"NnNnNnWwW"},
        {'R',"WnNnNnWwN"},
        {'S',"NnWnNnWwN"},
        {'T',"NnNnWnWwN"},
        {'U',"WwNnNnNnW"},
        {'V',"NwWnNnNnW"},
        {'W',"WwWnNnNnN"},
        {'X',"NwNnWnNnW"},
        {'Y',"WwNnWnNnN"},
        {'Z',"NwWnWnNnN"},
        {'-',"NwNnNnWnW"},
        {'.',"WwNnNnWnN"},
        {' ',"NwWnNnWnN"},
        {'

我在github中创建了一个开源控件: https://github.com/KevinPan/wpf-barcode< /a>,请尝试。

希望这有帮助。

,"NwNwNwNnN"}, {'/',"NwNwNnNwN"}, {'+',"NwNnNwNwN"}, {'%',"NnNwNwNwN"}, {'*',"NwNnWnWnN"}, }; #endregion public object Convert(object value, Type targetType, object parameter, CultureInfo culture) { string code; int narrow = 1, wide = 3; if (!_codes.TryGetValue((char)value, out code)) return null; code += 'n'; var result = from i in Enumerable.Range(0, code.Length) select new { color = (code[i] == 'W' || code[i] == 'N') ? Brushes.Black : Brushes.Transparent, width = (code[i] == 'n' || code[i] == 'N') ? narrow : wide }; return result; } public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) { throw new NotImplementedException(); } }

我在github中创建了一个开源控件: https://github.com/KevinPan/wpf-barcode< /a>,请尝试。

希望这有帮助。

The following is what I have finally:

<Window x:Class="ScratchClient.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="655.85" Width="687"
    xmlns:local="clr-namespace:ScratchClient">
<Window.Resources>
    <local:BarcodeConverter x:Key="barcodeConverter"/>
    <ItemsPanelTemplate x:Key="HorizontalPanel">
        <StackPanel Orientation="Horizontal" HorizontalAlignment="Center"/>
    </ItemsPanelTemplate>
    <DataTemplate x:Key="SingleBarTemplate">
        <Rectangle Fill="{Binding color}" Width="{Binding width}" />
    </DataTemplate>
    <DataTemplate x:Key="SingleCodeTemplate">
        <DockPanel>
            <TextBlock DockPanel.Dock="Bottom" Text="{Binding}" />
            <ItemsControl ItemsSource="{Binding Converter={StaticResource barcodeConverter}}"
              ItemsPanel="{StaticResource HorizontalPanel}"
              ItemTemplate="{StaticResource SingleBarTemplate}" />
        </DockPanel>
    </DataTemplate>
    <DataTemplate x:Key="BarcodeTemplate">
        <ItemsControl ItemsSource="{Binding}"
            ItemsPanel="{StaticResource HorizontalPanel}"
            ItemTemplate="{StaticResource SingleCodeTemplate}"
            Height="100" />
    </DataTemplate>
</Window.Resources>
<Grid>
    <ContentPresenter Name="barcode" Content="*WIKIPEDIA*" ContentTemplate="{StaticResource BarcodeTemplate}">
        <ContentPresenter.RenderTransform>
            <ScaleTransform ScaleX="2" ScaleY="2"></ScaleTransform>
        </ContentPresenter.RenderTransform>
    </ContentPresenter>
</Grid>

public class BarcodeConverter : IValueConverter
{
    //W Wide - Black
    //N Narrow - Black
    //w Wide - White
    //n Narrow - White
    #region code details
    Dictionary<char, string> _codes = new Dictionary<char, string>
    {
        {'0',"NnNwWnWnN"},
        {'1',"WnNwNnNnW"},
        {'2',"NnWwNnNnW"},
        {'3',"WnWwNnNnN"},
        {'4',"NnNwWnNnW"},
        {'5',"WnNwWnNnN"},
        {'6',"NnWwWnNnN"},
        {'7',"NnNwNnWnW"},
        {'8',"WnNwNnWnN"},
        {'9',"NnWwNnWnN"},
        {'A',"WnNnNwNnW"},
        {'B',"NnWnNwNnW"},
        {'C',"WnWnNwNnN"},
        {'D',"NnNnWwNnW"},
        {'E',"WnNnWwNnN"},
        {'F',"NnWnWwNnN"},
        {'G',"NnNnNwWnW"},
        {'H',"WnNnNwWnN"},
        {'I',"NnWnNwWnN"},
        {'J',"NnNnWwWnN"},
        {'K',"WnNnNnNwW"},
        {'L',"NnWnNnNwW"},
        {'M',"WnWnNnNwN"},
        {'N',"NnNnWnNwW"},
        {'O',"WnNnWnNwN"},
        {'P',"NnWnWnNwN"},
        {'Q',"NnNnNnWwW"},
        {'R',"WnNnNnWwN"},
        {'S',"NnWnNnWwN"},
        {'T',"NnNnWnWwN"},
        {'U',"WwNnNnNnW"},
        {'V',"NwWnNnNnW"},
        {'W',"WwWnNnNnN"},
        {'X',"NwNnWnNnW"},
        {'Y',"WwNnWnNnN"},
        {'Z',"NwWnWnNnN"},
        {'-',"NwNnNnWnW"},
        {'.',"WwNnNnWnN"},
        {' ',"NwWnNnWnN"},
        {'

And I have created an open source control in github: https://github.com/KevinPan/wpf-barcode, please try.

Hope this helps.

,"NwNwNwNnN"}, {'/',"NwNwNnNwN"}, {'+',"NwNnNwNwN"}, {'%',"NnNwNwNwN"}, {'*',"NwNnWnWnN"}, }; #endregion public object Convert(object value, Type targetType, object parameter, CultureInfo culture) { string code; int narrow = 1, wide = 3; if (!_codes.TryGetValue((char)value, out code)) return null; code += 'n'; var result = from i in Enumerable.Range(0, code.Length) select new { color = (code[i] == 'W' || code[i] == 'N') ? Brushes.Black : Brushes.Transparent, width = (code[i] == 'n' || code[i] == 'N') ? narrow : wide }; return result; } public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) { throw new NotImplementedException(); } }

And I have created an open source control in github: https://github.com/KevinPan/wpf-barcode, please try.

Hope this helps.

玉环 2024-10-08 14:00:01

也许最简单的方法是使用条形码字体。例如:

<Window x:Class="BarcodeTest.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Bar Code Test" Height="209" Width="426">
    <Grid>
        <TextBlock FontFamily="IDAutomationHC39M" FontSize="30" 
                   SnapsToDevicePixels="True"
                   VerticalAlignment="Center"
                   HorizontalAlignment="Center">*0123456789*</TextBlock>
    </Grid>
</Window>

本示例使用字体“IDAutomationHC39M”。生成的条形码如下所示:

alt text

此网页列出了各种免费软件或共享软件条形码字体: http://www.adams1.com/fonts.html

Probably the easiest way is to use barcode fonts. For example:

<Window x:Class="BarcodeTest.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Bar Code Test" Height="209" Width="426">
    <Grid>
        <TextBlock FontFamily="IDAutomationHC39M" FontSize="30" 
                   SnapsToDevicePixels="True"
                   VerticalAlignment="Center"
                   HorizontalAlignment="Center">*0123456789*</TextBlock>
    </Grid>
</Window>

This example uses the font "IDAutomationHC39M". The resulting barcode looks like this:

alt text

This web page lists various freeware or shareware barcode fonts: http://www.adams1.com/fonts.html .

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文