André Alves de Lima

Talking about Software Development and more…

Trabalhando com código de barras no Report Viewer

Um dos assuntos mais requisitados com relação ao Report Viewer é a questão da utilização de código de barras nos relatórios. Como é que podemos exibir código de barras no Report Viewer?

Pois bem, no vídeo de hoje eu vou mostrar para você as duas opções que nós temos para exibirmos código de barras nos nossos relatórios do Report Viewer. A primeira opção será através de uma fonte de código de barras. Já a segunda opção será a geração da imagem do código de barras e envio dessa imagem pronta para o relatório. Assiste aí e depois me conta o que você achou:

Opção 1: Utilizando fonte de código de barras

Uma opção que podemos empregar para exibirmos código de barras nas nossas aplicações (tanto nos relatórios como nas telas) é a utilização de fontes de código de barras. Muitos tipos de códigos de barras (se você ainda não sabe, existem inúmeros tipos diferentes) possuem fontes que podem ser instaladas e convertem automaticamente texto em código de barras. Por exemplo, se pesquisarmos por “free barcode 128 font” no Google (128 é um tipo de código de barras, talvez o mais conhecido), encontraremos muitas opções que podemos utilizar:

Para testar essa sistemática, eu baixei a fonte “Code 128” do site dafont.com. Uma vez instalada, nós podemos simplesmente formatar um TextBox do relatório escolhendo essa fonte:

Veja só o resultado:

Dependendo do tipo de código de barras, você encontrará facilmente fontes gratuitas na internet. Caso você não encontre, aí você terá que partir para a segunda opção.

Opção 2: Enviando imagem do código de barras para o relatório

A segunda opção que temos para exibirmos código de barras no Report Viewer é a geração de uma imagem com o código de barras no lado da aplicação e o envio dessa imagem pronta para o relatório. Isso quer dizer que nós teremos que criar uma nova coluna do tipo “byte[]” na DataTable que está alimentando o relatório (ou uma nova propriedade, caso você esteja alimentando o relatório através de classes e não através de DataTables). Vamos dar o nome de “ImagemCB” (imagem do código de barras) para essa nova coluna:

Feito isso, temos que dar um “refresh” nos campos do DataSet do relatório para que a nova coluna apareça:

Agora nós podemos adicionar uma nova coluna na nossa tabela do relatório e, dentro dessa coluna, nós colocaremos um controle do tipo “Image“:

Nas propriedades da imagem, nós temos que configurar que o conteúdo dela virá do banco de dados (opção “Database“) e a coluna correspondente é a “ImagemCB” (que é justamente a nova coluna que criamos anteriormente):

Vamos também configurar o tamanho da imagem para que ela seja automaticamente redimensionada para caber na célula da tabela, além de adicionarmos um “padding” para que o código de barras não saia grudado nas bordas da célula:

Agora que nós já preparamos o nosso relatório para que a imagem do código de barras seja exibida, como é que nós fazemos para gerarmos a imagem para cada produto? Simples, nós utilizaremos uma biblioteca que já implementa essa funcionalidade!

A biblioteca open source mais conhecida que eu encontrei para geração de códigos de barras no .NET é a BarcodeLib. O código fonte dessa biblioteca está disponível no GitHub e você encontra os releases dela no NuGet também. Além do “Code 128“, ela suporta também outros formatos conhecidos de código de barras.

Para utilizá-la no nosso projeto, vamos adicionar uma referência através do NuGet:

A chamada para gerarmos uma imagem do código de barras com a biblioteca BarcodeLib é muito simples. Nós só temos que chamar o método “Encode” passando o tipo de código de barras e o conteúdo dele. Porém, como o relatório está esperando um array de bytes com a imagem, nós temos que converter o retorno da biblioteca (que será uma instância de “Image“). Para isso, eu utilizei o método “ImageToByteArray” que eu encontrei nesta thread do StackOverflow. Veja como é que fica o código completo:

// C#
private void Form1_Load(object sender, EventArgs e)
{
	using (var bc = new BarcodeLib.Barcode())
	{
		this.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 1", "12345", ImageToByteArray(bc.Encode(BarcodeLib.TYPE.CODE128, "12345")));
		this.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 2", "23456", ImageToByteArray(bc.Encode(BarcodeLib.TYPE.CODE128, "23456")));
		this.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 3", "34567", ImageToByteArray(bc.Encode(BarcodeLib.TYPE.CODE128, "34567")));
		this.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 4", "45678", ImageToByteArray(bc.Encode(BarcodeLib.TYPE.CODE128, "45678")));
		this.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 5", "56789", ImageToByteArray(bc.Encode(BarcodeLib.TYPE.CODE128, "56789")));
	}

	this.reportViewer1.RefreshReport();
}

public static byte[] ImageToByteArray(System.Drawing.Image image)
{
	using(var ms = new MemoryStream())
	{
		image.Save(ms, System.Drawing.Imaging.ImageFormat.Png);
		return ms.ToArray();
	}
}
    ' VB.NET
    Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        Using Bc = New BarcodeLib.Barcode()
            Me.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 1", "12345", ImageToByteArray(Bc.Encode(BarcodeLib.TYPE.CODE128, "12345")))
            Me.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 2", "23456", ImageToByteArray(Bc.Encode(BarcodeLib.TYPE.CODE128, "23456")))
            Me.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 3", "34567", ImageToByteArray(Bc.Encode(BarcodeLib.TYPE.CODE128, "34567")))
            Me.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 4", "45678", ImageToByteArray(Bc.Encode(BarcodeLib.TYPE.CODE128, "45678")))
            Me.DataSetRelatorio.DataTableProduto.AddDataTableProdutoRow("Produto 5", "56789", ImageToByteArray(Bc.Encode(BarcodeLib.TYPE.CODE128, "56789")))
        End Using

        Me.ReportViewer1.RefreshReport()
    End Sub

    Public Shared Function ImageToByteArray(Image As System.Drawing.Image) As Byte()
        Using Ms = New MemoryStream()
            Image.Save(Ms, Imaging.ImageFormat.Png)
            Return Ms.ToArray()
        End Using
    End Function

Execute a aplicação e confira o resultado:

Mas pera aí, por que os códigos não são iguais?

Uma coisa que você pode estar se perguntando é: se os códigos são iguais, porque o resultado é diferente com a fonte? Veja só, se dermos um zoom no relatório nós conseguiremos observar melhor a diferença:

Isso acontece porque o “Code 128” não é somente uma conversão direta de texto em código de barras. Como você pode conferir na Wikipedia, tem toda uma lógica que nós teríamos que seguir na hora de construirmos a string que deverá ser exibida com a fonte (como, por exemplo, caracteres de inicialização e finalização, além do “caractere verificador“). Se você quiser saber mais a respeito da geração da string para o “Code 128“, dê uma olhada nestes links:

Code 128/GS1-128 Barcode FAQ & Tutorial

Code 128 Check Character Calculation Examples

E se você quiser testar a geração de códigos de barras, existem inúmeros sites que fazem isso gratuitamente, como estes aqui:

Online Barcode Generator

Baixe o projeto de exemplo

Para baixar o projeto de exemplo desse artigo, assine a minha newsletter. Ao fazer isso, além de ter acesso ao projeto, você receberá um e-mail toda semana sobre o artigo publicado e ficará sabendo também em primeira mão sobre o artigo da próxima semana, além de receber dicas “bônus” que eu só compartilho por e-mail. Inscreva-se utilizando o formulário no final do artigo.

Concluindo

No artigo de hoje você conferiu duas maneiras de exibirmos código de barras no Report Viewer. A primeira delas foi através de uma fonte. Já a segunda opção foi a geração da imagem do código de barras no lado da aplicação e envio da mesma para o relatório através do DataSet.

E você, já precisou trabalhar com código de barras na sua aplicação? Como é que você resolveu essa demanda? Trabalhou com uma fonte ou alguma biblioteca para geração dos códigos? Estou curioso para saber mais sobre as suas experiências na caixa de comentários logo abaixo!

Até a próxima!

André Lima

Photo by Pixabay used under Creative Commons
https://pixabay.com/en/startup-start-up-notebooks-creative-593327/

Image by Pixabay used under Creative Commons
https://pixabay.com/en/tax-forms-income-business-468440/

Song Rocket Power Kevin MacLeod (incompetech.com)
Licensed under Creative Commons: By Attribution 3.0 License
http://creativecommons.org/licenses/by/3.0/

Newsletter do André Lima

* indicates required



Powered by MailChimp

2 thoughts on “Trabalhando com código de barras no Report Viewer

Deixe uma resposta

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *