summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.hgignore1
-rw-r--r--fpdf.go120
-rw-r--r--fpdf_test.go44
3 files changed, 119 insertions, 46 deletions
diff --git a/.hgignore b/.hgignore
index 50deff5..508c2b7 100644
--- a/.hgignore
+++ b/.hgignore
@@ -6,3 +6,4 @@ open
pdf.txt
*.sublime*
font/Ubuntu-*
+*.0
diff --git a/fpdf.go b/fpdf.go
index bfa8fc5..e2c8b7c 100644
--- a/fpdf.go
+++ b/fpdf.go
@@ -220,7 +220,8 @@ func (f *Fpdf) Err() bool {
}
// SetErrorf sets the internal Fpdf error with formatted text to halt PDF
-// generation; this may facilitate error handling by application.
+// generation; this may facilitate error handling by application. If an error
+// condition is already set, this call is ignored.
//
// See the documentation for printing in the standard fmt package for details
// about fmtStr and args.
@@ -2012,48 +2013,27 @@ func (f *Fpdf) Ln(h float64) {
}
}
-// Image puts a JPEG, PNG or GIF image in the current page. The size it will
-// take on the page can be specified in different ways. If both w and h are 0,
-// the image is rendered at 96 dpi. If either w or h is zero, it will be
-// calculated from the other dimension so that the aspect ratio is maintained.
-// If w and h are negative, their absolute values indicate their dpi extents.
-//
-// Supported JPEG formats are 24 bit, 32 bit and gray scale. Supported PNG
-// formats are 24 bit, indexed color, and 8 bit indexed gray scale. If a GIF
-// image is animated, only the first frame is rendered. Transparency is
-// supported. It is possible to put a link on the image.
-//
-// imageNameStr may be the name of an image as registered with a call to either
-// RegisterImageReader() or RegisterImage(). In the first case, the image is
-// loaded using an io.Reader. This is generally useful when the image is
-// obtained from some other means than as a disk-based file. In the second
-// case, the image is loaded as a file. Alternatively, imageNameStr may
-// directly specify a sufficiently qualified filename.
-//
-// However the image is loaded, if it is used more than once only one copy is
-// embedded in the file.
-//
-// If x is negative, the current abscissa is used.
-//
-// If flow is true, the current y value is advanced after placing the image and
-// a page break may be made if necessary.
-//
-// tp specifies the image format. Possible values are (case insensitive):
-// "JPG", "JPEG", "PNG" and "GIF". If not specified, the type is inferred from
-// the file extension.
-//
-// If link refers to an internal page anchor (that is, it is non-zero; see
-// AddLink()), the image will be a clickable internal link. Otherwise, if
-// linkStr specifies a URL, the image will be a clickable external link.
-func (f *Fpdf) Image(imageNameStr string, x, y, w, h float64, flow bool, tp string, link int, linkStr string) {
- if f.err != nil {
- return
- }
- info := f.RegisterImage(imageNameStr, tp)
- if f.err != nil {
- return
+// ImageTypeFromMime returns the image type used in various image-related
+// functions (for example, Image()) that is associated with the specified MIME
+// type. For example, "jpg" is returned if mimeStr is "image/jpeg". An error is
+// set if the specified MIME type is not supported.
+func (f *Fpdf) ImageTypeFromMime(mimeStr string) (tp string) {
+ switch mimeStr {
+ case "image/png":
+ tp = "png"
+ case "image/jpg":
+ tp = "jpg"
+ case "image/jpeg":
+ tp = "jpg"
+ case "image/gif":
+ tp = "gif"
+ default:
+ f.SetErrorf("unsupported image type: %s", mimeStr)
}
+ return
+}
+func (f *Fpdf) imageOut(info *ImageInfoType, x, y, w, h float64, flow bool, link int, linkStr string) {
// Automatic width and height calculation if needed
if w == 0 && h == 0 {
// Put image at 96 dpi
@@ -2095,6 +2075,50 @@ func (f *Fpdf) Image(imageNameStr string, x, y, w, h float64, flow bool, tp stri
if link > 0 || len(linkStr) > 0 {
f.newLink(x, y, w, h, link, linkStr)
}
+}
+
+// Image puts a JPEG, PNG or GIF image in the current page. The size it will
+// take on the page can be specified in different ways. If both w and h are 0,
+// the image is rendered at 96 dpi. If either w or h is zero, it will be
+// calculated from the other dimension so that the aspect ratio is maintained.
+// If w and h are negative, their absolute values indicate their dpi extents.
+//
+// Supported JPEG formats are 24 bit, 32 bit and gray scale. Supported PNG
+// formats are 24 bit, indexed color, and 8 bit indexed gray scale. If a GIF
+// image is animated, only the first frame is rendered. Transparency is
+// supported. It is possible to put a link on the image.
+//
+// imageNameStr may be the name of an image as registered with a call to either
+// RegisterImageReader() or RegisterImage(). In the first case, the image is
+// loaded using an io.Reader. This is generally useful when the image is
+// obtained from some other means than as a disk-based file. In the second
+// case, the image is loaded as a file. Alternatively, imageNameStr may
+// directly specify a sufficiently qualified filename.
+//
+// However the image is loaded, if it is used more than once only one copy is
+// embedded in the file.
+//
+// If x is negative, the current abscissa is used.
+//
+// If flow is true, the current y value is advanced after placing the image and
+// a page break may be made if necessary.
+//
+// tp specifies the image format. Possible values are (case insensitive):
+// "JPG", "JPEG", "PNG" and "GIF". If not specified, the type is inferred from
+// the file extension.
+//
+// If link refers to an internal page anchor (that is, it is non-zero; see
+// AddLink()), the image will be a clickable internal link. Otherwise, if
+// linkStr specifies a URL, the image will be a clickable external link.
+func (f *Fpdf) Image(imageNameStr string, x, y, w, h float64, flow bool, tp string, link int, linkStr string) {
+ if f.err != nil {
+ return
+ }
+ info := f.RegisterImage(imageNameStr, tp)
+ if f.err != nil {
+ return
+ }
+ f.imageOut(info, x, y, w, h, flow, link, linkStr)
return
}
@@ -2104,17 +2128,23 @@ func (f *Fpdf) Image(imageNameStr string, x, y, w, h float64, flow bool, tp stri
// case.
//
// See Image() for restrictions on the image and the "tp" parameters.
+//
+// See tutorial 27 for an example of how this function can be used to load an
+// image from the web.
func (f *Fpdf) RegisterImageReader(imgName, tp string, r io.Reader) (info *ImageInfoType) {
// Thanks, Ivan Daniluk, for generalizing this code to use the Reader interface.
+ if f.err != nil {
+ return
+ }
info, ok := f.images[imgName]
if ok {
- return info
+ return
}
// First use of this image, get info
if tp == "" {
f.err = fmt.Errorf("image type should be specified if reading from custom reader")
- return info
+ return
}
tp = strings.ToLower(tp)
if tp == "jpeg" {
@@ -2136,7 +2166,7 @@ func (f *Fpdf) RegisterImageReader(imgName, tp string, r io.Reader) (info *Image
info.i = len(f.images) + 1
f.images[imgName] = info
- return info
+ return
}
// RegisterImage registers an image, adding it to the PDF file but not adding
@@ -2149,7 +2179,7 @@ func (f *Fpdf) RegisterImageReader(imgName, tp string, r io.Reader) (info *Image
func (f *Fpdf) RegisterImage(fileStr, tp string) (info *ImageInfoType) {
info, ok := f.images[fileStr]
if ok {
- return info
+ return
}
file, err := os.Open(fileStr)
diff --git a/fpdf_test.go b/fpdf_test.go
index 41f388e..11b96bb 100644
--- a/fpdf_test.go
+++ b/fpdf_test.go
@@ -22,6 +22,7 @@ import (
"fmt"
"io/ioutil"
"math"
+ "net/http"
"os"
"path/filepath"
"strings"
@@ -1281,7 +1282,48 @@ func ExampleFpdf_tutorial26() {
pdf.EndLayer()
pdf.OutputAndClose(docWriter(pdf, 26))
-
// Output:
// Successfully generated pdf/tutorial26.pdf
+
+}
+
+// This example demonstrates the use of an image that is retrieved from a web
+// server.
+func ExampleFpdf_tutorial27() {
+
+ const (
+ margin = 10
+ wd = 210
+ ht = 297
+ fontSize = 15
+ urlStr = "https://code.google.com/p/gofpdf/logo?cct=1402750750"
+ msgStr = `Images from the web can be easily embedded when a PDF document is generated.`
+ )
+
+ var (
+ rsp *http.Response
+ err error
+ tp string
+ )
+
+ pdf := gofpdf.New("P", "mm", "A4", "")
+ pdf.AddPage()
+ pdf.SetFont("Helvetica", "", fontSize)
+ ln := pdf.PointConvert(fontSize)
+ pdf.MultiCell(wd-margin-margin, ln, msgStr, "", "L", false)
+ rsp, err = http.Get(urlStr)
+ if err == nil {
+ tp = pdf.ImageTypeFromMime(rsp.Header["Content-Type"][0])
+ infoPtr := pdf.RegisterImageReader(urlStr, tp, rsp.Body)
+ if pdf.Ok() {
+ imgWd, imgHt := infoPtr.Extent()
+ pdf.Image(urlStr, (wd-imgWd)/2.0, pdf.GetY()+ln, imgWd, imgHt, false, tp, 0, "")
+ }
+ } else {
+ pdf.SetError(err)
+ }
+ pdf.OutputAndClose(docWriter(pdf, 27))
+ // Output:
+ // Successfully generated pdf/tutorial27.pdf
+
}