Convert Figma logo to code with AI

signintech logogopdf

A simple library for generating PDF written in Go lang

2,509
269
2,509
113

Top Related Projects

1,629

A maroto way to create PDFs. Maroto is inspired in Bootstrap and uses gofpdf. Fast and simple.

2,543

Golang PDF library for creating and processing PDF files (pure go)

6,748

A PDF processor written in Go.

Quick Overview

signintech/gopdf is a pure Go library for creating PDF documents. It provides a simple and efficient way to generate PDFs programmatically without relying on external dependencies or C libraries.

Pros

  • Pure Go implementation, making it easy to use and deploy across different platforms
  • Lightweight and efficient, suitable for both small and large PDF generation tasks
  • Supports various PDF features like text, images, shapes, and tables
  • Active development and community support

Cons

  • Limited advanced PDF features compared to some more established PDF libraries
  • Documentation could be more comprehensive for complex use cases
  • May have performance limitations for extremely large or complex PDF documents
  • Limited support for PDF form creation and manipulation

Code Examples

  1. Creating a simple PDF with text:
package main

import (
    "github.com/signintech/gopdf"
)

func main() {
    pdf := gopdf.GoPdf{}
    pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})
    pdf.AddPage()
    err := pdf.AddTTFFont("arial", "arial.ttf")
    if err != nil {
        panic(err)
    }
    pdf.SetFont("arial", "", 14)
    pdf.Cell(nil, "Hello, World!")
    pdf.WritePdf("hello.pdf")
}
  1. Adding an image to a PDF:
pdf := gopdf.GoPdf{}
pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})
pdf.AddPage()
pdf.Image("image.jpg", 10, 10, nil)
pdf.WritePdf("with_image.pdf")
  1. Creating a table in a PDF:
pdf := gopdf.GoPdf{}
pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})
pdf.AddPage()

pdf.SetLineWidth(0.5)
pdf.Line(10, 10, 100, 10)
pdf.Line(10, 20, 100, 20)
pdf.Line(10, 10, 10, 20)
pdf.Line(100, 10, 100, 20)

pdf.SetFont("arial", "", 12)
pdf.SetX(15)
pdf.SetY(15)
pdf.Cell(nil, "Table Cell")

pdf.WritePdf("table.pdf")

Getting Started

To use signintech/gopdf in your Go project:

  1. Install the library:

    go get github.com/signintech/gopdf
    
  2. Import it in your Go file:

    import "github.com/signintech/gopdf"
    
  3. Create a new PDF instance and start using the library's functions to generate your PDF:

    pdf := gopdf.GoPdf{}
    pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})
    // Add content to your PDF
    pdf.WritePdf("output.pdf")
    

Competitor Comparisons

1,629

A maroto way to create PDFs. Maroto is inspired in Bootstrap and uses gofpdf. Fast and simple.

Pros of maroto

  • Higher-level abstraction for creating PDFs, making it easier to generate complex documents
  • Built-in support for tables, charts, and other common PDF elements
  • More user-friendly API with a focus on simplicity and readability

Cons of maroto

  • Less flexibility for low-level PDF manipulation compared to gopdf
  • Potentially larger binary size due to additional features and dependencies
  • May have a steeper learning curve for users familiar with low-level PDF creation

Code Comparison

maroto:

m := maroto.New()
m.Row(40, func() {
    m.Col(12, func() {
        m.Text("Hello, World!")
    })
})
m.OutputFileAndClose("output.pdf")

gopdf:

pdf := gopdf.GoPdf{}
pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})
pdf.AddPage()
pdf.SetFont("Arial", "", 14)
pdf.Cell(nil, "Hello, World!")
pdf.WritePdf("output.pdf")

Both libraries allow for PDF creation in Go, but maroto provides a higher-level API with more built-in functionality, while gopdf offers more low-level control over PDF generation.

2,543

Golang PDF library for creating and processing PDF files (pure go)

Pros of unipdf

  • More comprehensive PDF manipulation capabilities, including reading, editing, and form filling
  • Better support for complex PDF structures and features
  • Actively maintained with regular updates and improvements

Cons of unipdf

  • Commercial license required for production use, which can be costly
  • Steeper learning curve due to more extensive API and features
  • Larger codebase and dependencies compared to gopdf

Code Comparison

unipdf:

pdf := creator.New()
page := pdf.NewPage()
font, _ := pdf.NewStandardFont(fonts.Helvetica)
text := page.NewTextBox("Hello, World!", 100, 100, 400, 50)
text.SetFont(font)

gopdf:

pdf := gopdf.GoPdf{}
pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})
pdf.AddPage()
pdf.SetFont("Arial", "", 14)
pdf.Cell(nil, "Hello, World!")

Both libraries allow for basic PDF creation, but unipdf offers more advanced features and flexibility at the cost of complexity. gopdf provides a simpler API for basic PDF generation tasks, making it easier to get started but with limited advanced functionality.

6,748

A PDF processor written in Go.

Pros of pdfcpu

  • More comprehensive PDF manipulation capabilities, including merging, splitting, and encryption
  • Actively maintained with regular updates and bug fixes
  • Supports both creation and modification of existing PDF files

Cons of pdfcpu

  • Steeper learning curve due to more complex API
  • Larger codebase and dependencies, potentially increasing project size
  • May be overkill for simple PDF generation tasks

Code Comparison

pdfcpu:

import "github.com/pdfcpu/pdfcpu/pkg/api"

err := api.AddWatermarks(inputFile, outputFile, nil, watermarkContent, nil)

gopdf:

import "github.com/signintech/gopdf"

pdf := gopdf.GoPdf{}
pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})
pdf.AddPage()
pdf.Text("Hello, World!")
pdf.WritePdf("output.pdf")

Summary

pdfcpu offers a more feature-rich solution for PDF manipulation, including advanced operations like merging and encryption. It's actively maintained but comes with a steeper learning curve. gopdf, on the other hand, provides a simpler API focused primarily on PDF generation, making it easier to use for basic tasks but limiting its capabilities for more complex operations. The choice between the two depends on the specific requirements of your project and the level of PDF manipulation needed.

Convert Figma logo designs to code with AI

Visual Copilot

Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.

Try Visual Copilot

README

gopdf

gopdf is a simple library for generating PDF document written in Go lang.

A minimum version of Go 1.13 is required.

Features

  • Unicode subfont embedding. (Chinese, Japanese, Korean, etc.)
  • Draw line, oval, rect, curve
  • Draw image ( jpg, png )
    • Set image mask
  • Password protection
  • Font kerning

Installation

go get -u github.com/signintech/gopdf

Print text


package main
import (
	"log"
	"github.com/signintech/gopdf"
)

func main() {

	pdf := gopdf.GoPdf{}
	pdf.Start(gopdf.Config{ PageSize: *gopdf.PageSizeA4 })
	pdf.AddPage()
	err := pdf.AddTTFFont("wts11", "../ttf/wts11.ttf")
	if err != nil {
		log.Print(err.Error())
		return
	}

	err = pdf.SetFont("wts11", "", 14)
	if err != nil {
		log.Print(err.Error())
		return
	}
	pdf.Cell(nil, "您好")
	pdf.WritePdf("hello.pdf")

}

Set text color using RGB color model

pdf.SetTextColor(156, 197, 140)
pdf.Cell(nil, "您好")

Set text color using CMYK color model

pdf.SetTextColorCMYK(0, 6, 14, 0)
pdf.Cell(nil, "Hello")

Image


package main
import (
	"log"
	"github.com/signintech/gopdf"
)

func main() {
	pdf := gopdf.GoPdf{}
	pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4 })
	pdf.AddPage()
	var err error
	err = pdf.AddTTFFont("loma", "../ttf/Loma.ttf")
	if err != nil {
		log.Print(err.Error())
		return
	}

	pdf.Image("../imgs/gopher.jpg", 200, 50, nil) //print image
	err = pdf.SetFont("loma", "", 14)
	if err != nil {
		log.Print(err.Error())
		return
	}
	pdf.SetXY(250, 200) //move current location
	pdf.Cell(nil, "gopher and gopher") //print text

	pdf.WritePdf("image.pdf")
}

Links


package main

import (
	"log"
	"github.com/signintech/gopdf"
)

func main()  {
	pdf := gopdf.GoPdf{}
	pdf.Start(gopdf.Config{ PageSize: *gopdf.PageSizeA4 })
	pdf.AddPage()
	err := pdf.AddTTFFont("times", "./test/res/times.ttf")
	if err != nil {
		log.Print(err.Error())
		return
	}

	err = pdf.SetFont("times", "", 14)
	if err != nil {
		log.Print(err.Error())
		return
	}

	pdf.SetXY(30, 40)
	pdf.Text("Link to example.com")
	pdf.AddExternalLink("http://example.com/", 27.5, 28, 125, 15)

	pdf.SetXY(30, 70)
	pdf.Text("Link to second page")
	pdf.AddInternalLink("anchor", 27.5, 58, 120, 15)

	pdf.AddPage()
	pdf.SetXY(30, 100)
	pdf.SetAnchor("anchor")
	pdf.Text("Anchor position")

	pdf.WritePdf("hello.tmp.pdf")

}

Header and Footer


package main

import (
    "log"
    "github.com/signintech/gopdf"
)

func main() {
    pdf := gopdf.GoPdf{}
    pdf.Start(gopdf.Config{ PageSize: *gopdf.PageSizeA4 })

    err := pdf.AddTTFFont("font1", "./test/res/font1.ttf")
    if err != nil {
        log.Print(err.Error())
        return
    }

    err = pdf.SetFont("font1", "", 14)
    if err != nil {
        log.Print(err.Error())
        return
    }

    pdf.AddHeader(func() {
        pdf.SetY(5)
        pdf.Cell(nil, "header")
    })
    pdf.AddFooter(func() {
        pdf.SetY(825)
        pdf.Cell(nil, "footer")
    })

    pdf.AddPage()
    pdf.SetY(400)
    pdf.Text("page 1 content")
    pdf.AddPage()
    pdf.SetY(400)
    pdf.Text("page 2 content")

    pdf.WritePdf("header-footer.tmp.pdf")

}

Draw line

pdf.SetLineWidth(2)
pdf.SetLineType("dashed")
pdf.Line(10, 30, 585, 30)

Draw oval

pdf.SetLineWidth(1)
pdf.Oval(100, 200, 500, 500)

Draw polygon

pdf.SetStrokeColor(255, 0, 0)
pdf.SetLineWidth(2)
pdf.SetFillColor(0, 255, 0)
pdf.Polygon([]gopdf.Point{{X: 10, Y: 30}, {X: 585, Y: 200}, {X: 585, Y: 250}}, "DF")

Draw rectangle with round corner

pdf.SetStrokeColor(255, 0, 0)
pdf.SetLineWidth(2)
pdf.SetFillColor(0, 255, 0)
err := pdf.Rectangle(196.6, 336.8, 398.3, 379.3, "DF", 3, 10)
if err != nil {
	return err
}

Draw rectangle with round corner using CMYK color model

pdf.SetStrokeColorCMYK(88, 49, 0, 0)
pdf.SetLineWidth(2)
pdf.SetFillColorCMYK(0, 5, 89, 0)
err := pdf.Rectangle(196.6, 336.8, 398.3, 379.3, "DF", 3, 10)
if err != nil {
	return err
}

Rotation text or image

pdf.SetXY(100, 100)
pdf.Rotate(270.0, 100.0, 100.0)
pdf.Text("Hello...")
pdf.RotateReset() //reset

Set transparency

Read about transparency in pdf (page 320, section 11)

// alpha - value of transparency, can be between `0` and `1`
// blendMode - default value is `/Normal` - read about [blendMode and kinds of its](https://www.adobe.com/content/dam/acom/en/devnet/acrobat/pdfs/PDF32000_2008.pdf) `(page 325, section 11.3.5)`

transparency := Transparency{
	Alpha: 0.5,
	BlendModeType: "",
}
pdf.SetTransparency(transparency Transparency)

Password protection

package main

import (
	"log"

	"github.com/signintech/gopdf"
)


func main() {

	pdf := gopdf.GoPdf{}
	pdf.Start(gopdf.Config{
		PageSize: *gopdf.PageSizeA4,
		Protection: gopdf.PDFProtectionConfig{
			UseProtection: true,
			Permissions: gopdf.PermissionsPrint | gopdf.PermissionsCopy | gopdf.PermissionsModify,
			OwnerPass:   []byte("123456"),
			UserPass:    []byte("123456789")},
	})

	pdf.AddPage()
	pdf.AddTTFFont("loma", "../ttf/loma.ttf")
	pdf.Cell(nil,"Hi")
	pdf.WritePdf("protect.pdf")
}

Import existing PDF

Import existing PDF power by package gofpdi created by @phpdave11 (thank you :smile:)

package main

import (
        "github.com/signintech/gopdf"
        "io"
        "net/http"
        "os"
)

func main() {
        var err error

        // Download a Font
        fontUrl := "https://github.com/google/fonts/raw/master/ofl/daysone/DaysOne-Regular.ttf"
        if err = DownloadFile("example-font.ttf", fontUrl); err != nil {
            panic(err)
        }

        // Download a PDF
        fileUrl := "https://tcpdf.org/files/examples/example_012.pdf"
        if err = DownloadFile("example-pdf.pdf", fileUrl); err != nil {
            panic(err)
        }

        pdf := gopdf.GoPdf{}
        pdf.Start(gopdf.Config{PageSize: *gopdf.PageSizeA4})

        pdf.AddPage()

        err = pdf.AddTTFFont("daysone", "example-font.ttf")
        if err != nil {
            panic(err)
        }

        err = pdf.SetFont("daysone", "", 20)
        if err != nil {
            panic(err)
        }

        // Color the page
        pdf.SetLineWidth(0.1)
        pdf.SetFillColor(124, 252, 0) //setup fill color
        pdf.RectFromUpperLeftWithStyle(50, 100, 400, 600, "FD")
        pdf.SetFillColor(0, 0, 0)

        pdf.SetXY(50, 50)
        pdf.Cell(nil, "Import existing PDF into GoPDF Document")

        // Import page 1
        tpl1 := pdf.ImportPage("example-pdf.pdf", 1, "/MediaBox")

        // Draw pdf onto page
        pdf.UseImportedTemplate(tpl1, 50, 100, 400, 0)

        pdf.WritePdf("example.pdf")

}

// DownloadFile will download a url to a local file. It's efficient because it will
// write as it downloads and not load the whole file into memory.
func DownloadFile(filepath string, url string) error {
        // Get the data
        resp, err := http.Get(url)
        if err != nil {
            return err
        }
        defer resp.Body.Close()

        // Create the file
        out, err := os.Create(filepath)
        if err != nil {
            return err
        }
        defer out.Close()

        // Write the body to file
        _, err = io.Copy(out, resp.Body)
        return err
}

Possible to set Trim-box

package main

import (
	"log"

	"github.com/signintech/gopdf"
)

func main() {

    pdf := gopdf.GoPdf{}
    mm6ToPx := 22.68

    // Base trim-box
    pdf.Start(gopdf.Config{
        PageSize: *gopdf.PageSizeA4,
        TrimBox: gopdf.Box{Left: mm6ToPx, Top: mm6ToPx, Right: gopdf.PageSizeA4.W - mm6ToPx, Bottom: gopdf.PageSizeA4.H - mm6ToPx},
    })

    // Page trim-box
    opt := gopdf.PageOption{
        PageSize: *gopdf.PageSizeA4,
        TrimBox: &gopdf.Box{Left: mm6ToPx, Top: mm6ToPx, Right: gopdf.PageSizeA4.W - mm6ToPx, Bottom: gopdf.PageSizeA4.H - mm6ToPx},
    }
    pdf.AddPageWithOption(opt)

    if err := pdf.AddTTFFont("wts11", "../ttf/wts11.ttf"); err != nil {
        log.Print(err.Error())
        return
    }

    if err := pdf.SetFont("wts11", "", 14); err != nil {
        log.Print(err.Error())
        return
    }

    pdf.Cell(nil,"Hi")
    pdf.WritePdf("hello.pdf")
}

Placeholder.

this function(s) made for experimental. There may be changes in the future.

With the placeholder function(s), you can create a placeholder to define a position. To make room for text to be add later.

There are 2 related function(s):

  • PlaceHolderText(...) used to create a placeholder to fill in text later.
  • FillInPlaceHoldText(...) used for filling in text into the placeholder that was created with PlaceHolderText.

Use case: For example, when you want to print the "total number of pages" on every page in pdf file, but you don't know the "total number of pages" until you have created all the pages. You can use func PlaceHolderText to create the point where you want "total number of pages" to be printed. And then when you have created all the pages so you know the "total number of pages", you call FillInPlaceHoldText(...). This function will take the text (in this case, text is "total number of pages") replace at the point that been created since func PlaceHolderText.

func main(){
    	pdf := GoPdf{}
	pdf.Start(Config{PageSize: *PageSizeA4})
	pdf.AddTTFFont("font1", "font1.ttf")
	pdf.SetFont("font1", "", 14) }

	for i := 0; i < 5; i++ {
		pdf.AddPage()
        	pdf.Br(20)
        	//create PlaceHolder
		err = pdf.PlaceHolderText("totalnumber", 30)
		if err != nil {
			log.Print(err.Error())
			return
		}

	}

    	//fillin text to PlaceHolder
	err = pdf.FillInPlaceHoldText("totalnumber",fmt.Sprintf("%d", 5), Left)
	if err != nil {
		log.Print(err.Error())
		return
	}

	pdf.WritePdf("placeholder_text.pdf")
}

Table Create

package main

import (
    "fmt"

    "github.com/signintech/gopdf"
)

func main() {

	// Create a new PDF document
	pdf := &gopdf.GoPdf{}
	// Start the PDF with a custom page size (we'll adjust it later)
	pdf.Start(gopdf.Config{PageSize: gopdf.Rect{W: 430, H: 200}})
	// Add a new page to the document
	pdf.AddPage()

	 pdf.AddTTFFont("font1", "./font1.ttf")
	pdf.SetFont("font1", "", 11)
	
	pdf.AddTTFFont("font2", "./font2.ttf")
	pdf.SetFont("font2", "", 11)
	
	// Set the starting Y position for the table
	tableStartY := 10.0
	// Set the left margin for the table
	marginLeft := 10.0

	// Create a new table layout
	table := pdf.NewTableLayout(marginLeft, tableStartY, 25, 5)

	// Add columns to the table
	table.AddColumn("CODE", 50, "left")
	table.AddColumn("DESCRIPTION", 200, "left")
	table.AddColumn("QTY.", 40, "right")
	table.AddColumn("PRICE", 60, "right")
	table.AddColumn("TOTAL", 60, "right")

	// Add rows to the table
	table.AddRow([]string{"001", "Product A", "2", "10.00", "20.00"})
	table.AddRow([]string{"002", "Product B", "1", "15.00", "15.00"})
	table.AddRow([]string{"003", "Product C", "3", "5.00", "15.00"})

	// Set the style for table cells
	table.SetTableStyle(gopdf.CellStyle{
		BorderStyle: gopdf.BorderStyle{
			Top:    true,
			Left:   true,
			Bottom: true,
			Right:  true,
			Width:  1.0,
		},
		FillColor: gopdf.RGBColor{R: 255, G: 255, B: 255},
		TextColor: gopdf.RGBColor{R: 0, G: 0, B: 0},
		FontSize:  10,
	})

	// Set the style for table header
	table.SetHeaderStyle(gopdf.CellStyle{
		BorderStyle: gopdf.BorderStyle{
			Top:      true,
			Left:     true,
			Bottom:   true,
			Right:    true,
			Width:    2.0,
			RGBColor: gopdf.RGBColor{R: 100, G: 150, B: 255},
		},
		FillColor: gopdf.RGBColor{R: 255, G: 200, B: 200},
		TextColor: gopdf.RGBColor{R: 255, G: 100, B: 100},
		Font:      "font2",
		FontSize:  12,
	})

	table.SetCellStyle(gopdf.CellStyle{
		BorderStyle: gopdf.BorderStyle{
			Right:    true,
			Bottom:   true,
			Width:    0.5,
			RGBColor: gopdf.RGBColor{R: 0, G: 0, B: 0},
		},
		FillColor: gopdf.RGBColor{R: 255, G: 255, B: 255},
		TextColor: gopdf.RGBColor{R: 0, G: 0, B: 0},
		Font:      "font1",
		FontSize:  10,
	})

	// Draw the table
	table.DrawTable()


	// Save the PDF to the specified path
     pdf.WritePdf("table.pdf")

}

result: table

visit https://github.com/oneplus1000/gopdfsample for more samples.