From d8075c91a9478caaae49cc6390cac8a86a319775 Mon Sep 17 00:00:00 2001 From: mwlang Date: Fri, 16 Aug 2013 06:54:28 -0400 Subject: [PATCH 1/8] changes to work with Ruby 2.0 --- lib/pdf/writer.rb | 22 +++++++++++++--------- lib/pdf/writer/fontmetrics.rb | 6 +++--- lib/pdf/writer/graphics.rb | 8 ++------ lib/pdf/writer/graphics/imageinfo.rb | 8 ++++++-- 4 files changed, 24 insertions(+), 20 deletions(-) diff --git a/lib/pdf/writer.rb b/lib/pdf/writer.rb index e25338a..8575cee 100644 --- a/lib/pdf/writer.rb +++ b/lib/pdf/writer.rb @@ -1,3 +1,4 @@ +#encoding: ASCII-8BIT #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ @@ -6,13 +7,12 @@ # Licensed under a MIT-style licence. See LICENCE in the main distribution # for full licensing information. # -# $Id$ +# $Id: writer.rb 202 2008-03-16 23:30:11Z sandal $ #++ require 'thread' require 'open-uri' require 'transaction/simple' -require 'pdf/core_ext/mutex' require 'color' # A class to provide the core functionality to create a PDF document @@ -20,7 +20,7 @@ module PDF class Writer # The version of PDF::Writer. - VERSION = '1.2.0' + VERSION = '1.3.0' # Escape the text so that it's safe for insertion into the PDF # document. @@ -710,7 +710,7 @@ def render(debug = false) xref = [] - content = "%PDF-#{@version}\n%\303\242\303\243\303\217\303\223\n" + content = "%PDF-#{@version}\n%âãÏÓ\n" pos = content.size objects.each do |oo| @@ -741,6 +741,10 @@ def render(debug = false) end alias :to_s :render + def render_to_file(filename) + IO.binwrite(filename, render) + end + # Loads the font metrics. This is now thread-safe. def load_font_metrics(font) metrics = PDF::Writer::FontMetrics.open(font) @@ -1467,11 +1471,11 @@ def add_text(x, y, text, size = nil, angle = 0, word_space_adjust = 0) end def char_width(font, char) - if RUBY_VERSION >= '1.9' - char = char.bytes.to_a.first unless @fonts[font].c[char] - else - char = char[0] unless @fonts[font].c[char] - end + if RUBY_VERSION >= '1.9' + char = char.ord unless @fonts[font].c[char] + else + char = char[0] unless @fonts[font].c[char] + end if @fonts[font].differences and @fonts[font].c[char].nil? name = @fonts[font].differences[char] || 'M' diff --git a/lib/pdf/writer/fontmetrics.rb b/lib/pdf/writer/fontmetrics.rb index a071783..77c7304 100644 --- a/lib/pdf/writer/fontmetrics.rb +++ b/lib/pdf/writer/fontmetrics.rb @@ -6,7 +6,7 @@ # Licensed under a MIT-style licence. See LICENCE in the main distribution # for full licensing information. # -# $Id$ +# $Id: fontmetrics.rb 168 2007-11-08 19:04:08Z sandal $ #++ class PDF::Writer::FontMetrics @@ -78,7 +78,7 @@ def self.open(font_name) font = PDF::Writer::FontMetrics.new # An AFM file contains key names followed by valuees. - file.each_line do |line| + file.each do |line| line.chomp! line.strip! key, *values = line.split @@ -152,7 +152,7 @@ def self.open(font_name) # C 39 ; WX 222 ; N quoteright ; B 53 463 157 718 ; bits = line.chomp.strip.split(/;/).collect { |r| r.strip } dtmp = {} - + bits.each do |bit| b = bit.split if b.size > 2 diff --git a/lib/pdf/writer/graphics.rb b/lib/pdf/writer/graphics.rb index 289f071..0bbc5b5 100644 --- a/lib/pdf/writer/graphics.rb +++ b/lib/pdf/writer/graphics.rb @@ -6,7 +6,7 @@ # Licensed under a MIT-style licence. See LICENCE in the main distribution # for full licensing information. # -# $Id$ +# $Id: graphics.rb 166 2007-11-08 18:22:05Z sandal $ #++ # Points for use in the drawing of polygons. class PDF::Writer::PolygonPoint @@ -543,11 +543,7 @@ def add_image_from_file(image, x, y, width = nil, height = nil, link = nil) if image.respond_to?(:read) data = image.read else - if RUBY_VERSION >= '1.9' - open(image,'rb:binary') { |ff| data = ff.read } - else - open(image,'rb') { |ff| data = ff.read } - end + open(image, 'rb') { |ff| data = ff.read } end add_image(data, x, y, width, height, nil, link) diff --git a/lib/pdf/writer/graphics/imageinfo.rb b/lib/pdf/writer/graphics/imageinfo.rb index 0ace52f..d0dc5da 100644 --- a/lib/pdf/writer/graphics/imageinfo.rb +++ b/lib/pdf/writer/graphics/imageinfo.rb @@ -1,3 +1,4 @@ +#encoding: ASCII-8BIT #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ @@ -9,7 +10,7 @@ # This file is also licensed under standard Ruby licensing provisions: the # Ruby licence and the GNU General Public Licence, version 2 or later. # -# $Id$ +# $Id: imageinfo.rb 173 2007-11-15 17:58:43Z sandal $ #++ require 'pdf/writer/oreader' @@ -98,8 +99,10 @@ def @data.read_o(length = 1, offset = nil) attr_reader :channels attr_reader :info - + attr_reader :signature + def discover_format + @signature = @top[0,12] if @top =~ %r{^GIF8[79]a} Formats::GIF elsif @top[0, 3] == "\xff\xd8\xff" @@ -127,6 +130,7 @@ def discover_format elsif @top[0] == 10 Formats::PCX else + # raise [@top[0,8], @top[0,8] == "\x89PNG\x0d\x0a\x1a\x0a", @top[0,8] == "\x89PNG\r\n\x1A\n", @top[0,8].encoding, "\x89PNG\x0d\x0a\x1a\x0a".encoding].inspect Formats::OTHER # might be WBMP end end From a496740edeb79147379298d66705463af4411c66 Mon Sep 17 00:00:00 2001 From: mwlang Date: Fri, 16 Aug 2013 09:19:29 -0400 Subject: [PATCH 2/8] documented Ruby 2.0 --- ChangeLog | 6 ++++++ README | 8 ++++++++ 2 files changed, 14 insertions(+) diff --git a/ChangeLog b/ChangeLog index f54539d..7f361b7 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,11 @@ = PDF::Writer Change Log +== PDF::Writer 1.3.0: August 16, 2013 +* Ruby 2.0 compatibility. + o ImageInfo fixes encoding issue + o Writer fixes enumeration of String + o Fixed computation of font-width calculations + == PDF::Writer 1.2.1: May 13, 2009 * Ruby 1.9 compatibility. diff --git a/README b/README index e3f61a9..9a26cbb 100644 --- a/README +++ b/README @@ -12,6 +12,14 @@ This software is based on Adobe's PDF Reference, Fifth Edition, version 1.6. This and earlier editions are available from Adobe's PDF developer website[http://partners.adobe.com/public/developer/pdf/index_reference.html]. +== Ruby 2.0 Compatibility +This gem version has been updated to work with Ruby 2.0. This is a maintenance +effort only to support moving existing projects from Ruby 1.8 to 2.0. New project +development should use Prawn[1] over PDF-Writer as it is actively maintained and +is also the successor/rewrite of this library. + +[1] http://prawn.majesticseacreature.com/ + == LICENCE NOTES Please read the file LICENCE for licensing restrictions on this library, as well as important patent considerations. From 4b2069edd91b6c849597bb181d649b456003c2f2 Mon Sep 17 00:00:00 2001 From: mwlang Date: Fri, 16 Aug 2013 09:27:05 -0400 Subject: [PATCH 3/8] removed extraneous debugging code --- lib/pdf/writer/graphics/imageinfo.rb | 3 --- 1 file changed, 3 deletions(-) diff --git a/lib/pdf/writer/graphics/imageinfo.rb b/lib/pdf/writer/graphics/imageinfo.rb index d0dc5da..b7186de 100644 --- a/lib/pdf/writer/graphics/imageinfo.rb +++ b/lib/pdf/writer/graphics/imageinfo.rb @@ -99,10 +99,8 @@ def @data.read_o(length = 1, offset = nil) attr_reader :channels attr_reader :info - attr_reader :signature def discover_format - @signature = @top[0,12] if @top =~ %r{^GIF8[79]a} Formats::GIF elsif @top[0, 3] == "\xff\xd8\xff" @@ -130,7 +128,6 @@ def discover_format elsif @top[0] == 10 Formats::PCX else - # raise [@top[0,8], @top[0,8] == "\x89PNG\x0d\x0a\x1a\x0a", @top[0,8] == "\x89PNG\r\n\x1A\n", @top[0,8].encoding, "\x89PNG\x0d\x0a\x1a\x0a".encoding].inspect Formats::OTHER # might be WBMP end end From f9764b0aaa679b78b7b45ff49d8f75a595c83c53 Mon Sep 17 00:00:00 2001 From: mwlang Date: Wed, 16 Oct 2013 17:34:52 -0400 Subject: [PATCH 4/8] changing ASCII-8BIT to WINDOWS-1252 encoding for writer --- lib/pdf/writer.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/pdf/writer.rb b/lib/pdf/writer.rb index 8575cee..ce20043 100644 --- a/lib/pdf/writer.rb +++ b/lib/pdf/writer.rb @@ -1,4 +1,4 @@ -#encoding: ASCII-8BIT +#encoding: WINDOWS-1252 #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ From 89c72415f882cbb58bdb46b57b3e0df835c1d1e1 Mon Sep 17 00:00:00 2001 From: mwlang Date: Wed, 16 Oct 2013 17:46:46 -0400 Subject: [PATCH 5/8] changing encoding to Windows-1252 --- lib/pdf/writer/graphics/imageinfo.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/pdf/writer/graphics/imageinfo.rb b/lib/pdf/writer/graphics/imageinfo.rb index b7186de..7de6c89 100644 --- a/lib/pdf/writer/graphics/imageinfo.rb +++ b/lib/pdf/writer/graphics/imageinfo.rb @@ -1,4 +1,4 @@ -#encoding: ASCII-8BIT +#encoding: Windows-1252 #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ From f9e49123dbfefd34c1db7fbc533118a4b6258ac2 Mon Sep 17 00:00:00 2001 From: mwlang Date: Wed, 16 Oct 2013 18:00:50 -0400 Subject: [PATCH 6/8] reverted fileinfo back to ASCII-8BIT --- lib/pdf/writer/graphics/imageinfo.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/pdf/writer/graphics/imageinfo.rb b/lib/pdf/writer/graphics/imageinfo.rb index 7de6c89..b7186de 100644 --- a/lib/pdf/writer/graphics/imageinfo.rb +++ b/lib/pdf/writer/graphics/imageinfo.rb @@ -1,4 +1,4 @@ -#encoding: Windows-1252 +#encoding: ASCII-8BIT #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ From 7abfd9b0e1d894732cfb15e922fe80d1e8d79ba0 Mon Sep 17 00:00:00 2001 From: mwlang Date: Fri, 18 Oct 2013 08:26:30 -0400 Subject: [PATCH 7/8] testing ISO-8859-1 contents --- lib/pdf/writer.rb | 24 +++++++--- lib/pdf/writer/graphics.rb | 5 +- lib/pdf/writer/graphics/imageinfo.rb | 14 ++++-- test/test_image_read.rb | 70 ++++++++++++++++++++++++++++ 4 files changed, 99 insertions(+), 14 deletions(-) create mode 100644 test/test_image_read.rb diff --git a/lib/pdf/writer.rb b/lib/pdf/writer.rb index ce20043..9ff3943 100644 --- a/lib/pdf/writer.rb +++ b/lib/pdf/writer.rb @@ -1,4 +1,4 @@ -#encoding: WINDOWS-1252 +#encoding: ISO-8859-1 #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ @@ -714,10 +714,17 @@ def render(debug = false) pos = content.size objects.each do |oo| - cont = oo.to_s - content << cont - xref << pos - pos += cont.size + begin + cont = oo.to_s + content << cont + xref << pos + pos += cont.size + rescue + puts '*' * 80 + puts cont.inspect + puts cont.encoding.name + puts '*' * 80 + end end # pos += 1 # Newline character before XREF @@ -1032,6 +1039,8 @@ def current_font! # add content to the currently active object def add_content(cc) + puts "add_content: #{cc.encoding.name}" + raise cc.inspect if cc.encoding.name == 'UTF-8' @current_contents << cc end @@ -1375,9 +1384,9 @@ def add_text(x, y, text, size = nil, angle = 0, word_space_adjust = 0) end select_font("Helvetica") if @fonts.empty? - + text = text.to_s - + # If there are any open callbacks, then they should be called, to show # the start of the line @callbacks.reverse_each do |ii| @@ -1611,6 +1620,7 @@ def adjust_wrapped_text(text, actual, width, x, just) # # +justification+:: :left, :right, :center, or :full def add_text_wrap(x, y, width, text, size = nil, justification = :left, angle = 0, test = false) + raise 'wtf' if text =~ /Scottish/ if text.kind_of?(Numeric) and size.kind_of?(String) text, size = size, text warn PDF::Writer::Lang[:add_textw_parameters_reversed] % caller[0] diff --git a/lib/pdf/writer/graphics.rb b/lib/pdf/writer/graphics.rb index 0bbc5b5..dd7df78 100644 --- a/lib/pdf/writer/graphics.rb +++ b/lib/pdf/writer/graphics.rb @@ -1,3 +1,4 @@ +#encoding: ISO-8859-1 #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ @@ -543,7 +544,7 @@ def add_image_from_file(image, x, y, width = nil, height = nil, link = nil) if image.respond_to?(:read) data = image.read else - open(image, 'rb') { |ff| data = ff.read } + open(image, 'r:ISO-8859-1:ISO-8859-1') { |ff| data = ff.read } end add_image(data, x, y, width, height, nil, link) @@ -660,7 +661,7 @@ def image(image, options = {}) if image.respond_to?(:read) image_data = image.read else - image_data = open(image, "rb") { |file| file.read } + image_data = open(image, "r:ISO-8859-1:ISO-8859-1") { |file| file.read } end info = PDF::Writer::Graphics::ImageInfo.new(image_data) end diff --git a/lib/pdf/writer/graphics/imageinfo.rb b/lib/pdf/writer/graphics/imageinfo.rb index b7186de..b4d5ca7 100644 --- a/lib/pdf/writer/graphics/imageinfo.rb +++ b/lib/pdf/writer/graphics/imageinfo.rb @@ -1,4 +1,4 @@ -#encoding: ASCII-8BIT +#encoding: ISO-8859-1 #-- # PDF::Writer for Ruby. # http://rubyforge.org/projects/ruby-pdf/ @@ -48,8 +48,8 @@ def formats alias :type_list :formats end - JPEG_SOF_BLOCKS = %W(\xc0 \xc1 \xc2 \xc3 \xc5 \xc6 \xc7 \xc9 \xca \xcb \xcd \xce \xcf) - JPEG_APP_BLOCKS = %W(\xe0 \xe1 \xe2 \xe3 \xe4 \xe5 \xe6 \xe7 \xe8 \xe9 \xea \xeb \xec \xed \xee \xef) + JPEG_SOF_BLOCKS = %W(\xc0 \xc1 \xc2 \xc3 \xc5 \xc6 \xc7 \xc9 \xca \xcb \xcd \xce \xcf).map{|m| m.force_encoding("ISO-8859-1")} + JPEG_APP_BLOCKS = %W(\xe0 \xe1 \xe2 \xe3 \xe4 \xe5 \xe6 \xe7 \xe8 \xe9 \xea \xeb \xec \xed \xee \xef).map{|m| m.force_encoding("ISO-8859-1")} # Receive image & make size. argument is image String or IO def initialize(data, format = nil) @@ -174,8 +174,12 @@ def measure_JPEG @data.read_o(2) # Skip the first two bytes of JPEG identifier. loop do marker, code, length = @data.read_o(4).unpack('aan') + + marker.force_encoding("ISO-8859-1") + code.force_encoding("ISO-8859-1") + raise "JPEG marker not found!" if marker != c_marker - + if JPEG_SOF_BLOCKS.include?(code) @bits, @height, @width, @channels = @data.read_o(6).unpack("CnnC") break @@ -352,7 +356,7 @@ def measure_TIFF Dir.glob("*").each do |file| print "#{file} (string)\n" - open(file, "rb") do |fh| + open(file, "r:ISO-8859-1:ISO-8859-1") do |fh| image = PDF::Writer::Graphics::ImageInfo.new(fh.read) print <<-EOF Format : #{image.format} diff --git a/test/test_image_read.rb b/test/test_image_read.rb new file mode 100644 index 0000000..ab2a9ac --- /dev/null +++ b/test/test_image_read.rb @@ -0,0 +1,70 @@ +#encoding: UTF-8 +$LOAD_PATH.unshift(File.dirname(__FILE__) + "/../lib") +require "pdf/writer" + +MAIN_TEXT_WIDTH = 330 +MAIN_TEXT_LINE_SPACING = 16 +PADDING_BOTTOM = 20 + +def write_text(pdf, text, options = {}) + y = options[:y] if options[:y] + left = options[:left] if options[:left] + width = options[:width] if options[:width] + size = options[:font_size] || 0 + height = options[:leading] + + # Filled with the text that would flow onto the next page + next_page_text = nil + + text.each_line do |line| + start = true + loop do + break if (line.nil? or line.empty?) and not start + + start = false + + y -= height + + if y < (pdf.absolute_bottom_margin + PADDING_BOTTOM) + if options[:no_newpage] + # Collect remaining text so it can be returned + next_page_text = "" if next_page_text.nil? + next_page_text += line + line = nil + else + pdf.start_new_page + y = options[:new_page_y] || multi_page_top_y(pdf) + end + end + + if next_page_text.nil? + line = pdf.add_text_wrap(left, y, width, line, size) + end + end + end + + if options[:no_newpage] + {:leftover_text => next_page_text, :next_line_y => y} + else + y + end +end + + +pdf = PDF::Writer.new +top_logo_file = '/Users/mwlang/projects/clients/taftlaw/taft_site/website/public/images/hr_taft_logo.jpg' +pdf.image(top_logo_file, {:width => 85, :justification => :right, :pad => 0 }) + +body = "\r\n\t\r\n\t\t\r\n\t\t\t\r\n\t\t\t\r\n\t\t\t\r\n\t\t\r\n\t\t\r\n\t\t\t\r\n\t\t\t\r\n\t\t\t\r\n\t\t\r\n\t\t\r\n\t\t\t\r\n\t\t\t\r\n\t\t\t\r\n\t\t\r\n\t\r\n\r\n\r\nCHARLES R. \"ROCKY\" SAXBE is Partner-in-Charge of the Columbus office. He maintains an active litigation practice representing clients in all aspects of civil litigation. Over the course of his illustrious career, he has acted as principal litigation counsel in numerous complex litigation cases, including serving as principal outside Ohio special counsel for the State of Ohio in the national tobacco litigation. He has appeared in numerous jury trials and has appeared before the Ohio Supreme Court, Ohio Courts of Appeals, and the Sixth Circuit U.S. Court of Appeals. According to Chambers USA, who interviews clients for feedback, Rocky is held in high regard \"for his political acumen, especially in election law-related and complex civil litigation.\" Rocky has a long affiliation with the political scene in Ohio, having served four terms in the Ohio House of Representatives. He provides counsel to elected officials, political party organizations and candidates on election, campaign finance and public ethics law.\r\n\r\nRepresentative Experience\r\n\r\n\r\n\tServed as principal outside Ohio special counsel for the State of Ohio in the \"national tobacco litigation,\" contributing significantly to the record setting $10 billion settlement for the State of Ohio.\r\n\tHas been the principal litigation counsel in numerous complex litigations, including numerous jury trials and has appeared before Ohio Supreme Court, Ohio Courts of Appeals, and the Sixth Circuit U.S. Court of Appeals.\r\n\tProvided counsel to elected officials, political party organizations and candidates on election, campaign finance and public ethics law.\r\n\tFrequent mediator assigned by the Federal Court for the Southern District of Ohio, providing expert testimony in the areas of attorneys' fees and malpractice.\r\n\tServes as legislative counsel for the Ohio Association of Municipal and County Judges.\r\n\r\n\r\nAchievements and Awards\r\n\r\n\r\n\tRecipient of the Ohio State Bar Association Distinguished Service Award\r\n\tAV Peer Review (Preeminent) Rated by Martindale-Hubbell\r\n\tBest Lawyers in America, Commercial Litigation, Government Relations Law & Bet-the-Company Litigation\r\n\tListed for inclusion in Ohio Super Lawyers, General Litigation (2004 - 2013)\r\n\tChambers USA, Litigation\r\n\r\n\r\nProfessional Memberships and Community Service\r\n\r\n\r\n\tColumbus Bar Association\r\n\tOhio State Bar Association\r\n\tAmerican Bar Associations\r\n\tChampaign County Bar Association\r\n\tGreater Columbus Arts Council, Past Chairman\r\n\tBexley Library Board, Past President\r\n\tColumbus College of Art and Design, Past Chairman\r\n\tCentral State University, Past Trustee\r\n\tMechanicsburg Lodge #113 F&AM, Past Master\r\n\tAncient and Accepted Scottish Rite, 33°\r\n\tVietnam Veterans of America\r\n\tAmerican Legion\r\n\tScioto Valley Rugby Football Club (SVRFC Hall of Fame)\r\n\r\n\r\nOther Professional Experience\r\n\r\n\r\n\tU.S. Marine Corps, infantry platoon commander with the First Marine Division in the Republic of Vietnam and was discharged with the rank of Captain\r\n\tElected to the Ohio House of Representatives in 1974 where he served four terms\r\n\tRepublican nominee for Ohio Attorney General in 1982\r\n\r\n" +write_text(pdf, + body, + { + :no_newpage => true, + :y => pdf.absolute_top_margin - 140, + :left => pdf.absolute_left_margin, + :leading => MAIN_TEXT_LINE_SPACING, + :width => MAIN_TEXT_WIDTH + } +) + +pdf.render \ No newline at end of file From 9339c702a5799edea0c6a1ff74c889fd7c0ac44b Mon Sep 17 00:00:00 2001 From: mwlang Date: Fri, 18 Oct 2013 08:42:00 -0400 Subject: [PATCH 8/8] removed debugging messages --- lib/pdf/writer.rb | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/lib/pdf/writer.rb b/lib/pdf/writer.rb index 9ff3943..5c96f11 100644 --- a/lib/pdf/writer.rb +++ b/lib/pdf/writer.rb @@ -715,15 +715,16 @@ def render(debug = false) objects.each do |oo| begin - cont = oo.to_s + cont = oo.to_s.force_encoding("ISO-8859-1") content << cont xref << pos pos += cont.size rescue - puts '*' * 80 - puts cont.inspect - puts cont.encoding.name - puts '*' * 80 + # puts '*' * 80 + # puts cont.inspect + # puts cont.encoding.name + # puts '*' * 80 + raise end end @@ -1039,8 +1040,6 @@ def current_font! # add content to the currently active object def add_content(cc) - puts "add_content: #{cc.encoding.name}" - raise cc.inspect if cc.encoding.name == 'UTF-8' @current_contents << cc end @@ -1620,7 +1619,6 @@ def adjust_wrapped_text(text, actual, width, x, just) # # +justification+:: :left, :right, :center, or :full def add_text_wrap(x, y, width, text, size = nil, justification = :left, angle = 0, test = false) - raise 'wtf' if text =~ /Scottish/ if text.kind_of?(Numeric) and size.kind_of?(String) text, size = size, text warn PDF::Writer::Lang[:add_textw_parameters_reversed] % caller[0]