package org.sakaiproject.tool.assessment.ui.bean.print;
import java.awt.Color;
import java.io.ByteArrayOutputStream;
import java.io.Serializable;
import java.io.StringReader;
import java.io.Reader;
import java.io.IOException;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import javax.faces.context.FacesContext;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import com.lowagie.text.Chunk;
import com.lowagie.text.Document;
import com.lowagie.text.Element;
import com.lowagie.text.Font;
import com.lowagie.text.Image;
import com.lowagie.text.Paragraph;
import com.lowagie.text.pdf.PdfPCell;
import com.lowagie.text.pdf.PdfPTable;
import com.lowagie.text.pdf.PdfWriter;
import org.sakaiproject.tool.assessment.data.dao.assessment.ItemAttachment;
import org.sakaiproject.tool.assessment.data.dao.assessment.PublishedAnswer;
import org.sakaiproject.tool.assessment.data.dao.assessment.PublishedAssessmentAttachment;
import org.sakaiproject.tool.assessment.data.dao.assessment.PublishedItemAttachment;
import org.sakaiproject.tool.assessment.data.dao.assessment.PublishedItemText;
import org.sakaiproject.tool.assessment.data.dao.assessment.PublishedSectionAttachment;
import org.sakaiproject.tool.assessment.data.ifc.shared.TypeIfc;
import org.sakaiproject.tool.assessment.pdf.HTMLWorker;
import com.lowagie.text.html.simpleparser.StyleSheet;
import com.lowagie.text.PageSize;
import org.sakaiproject.tool.assessment.ui.bean.delivery.DeliveryBean;
import org.sakaiproject.tool.assessment.ui.bean.delivery.ItemContentsBean;
import org.sakaiproject.tool.assessment.ui.bean.delivery.MatchingBean;
import org.sakaiproject.tool.assessment.ui.bean.print.settings.PrintSettingsBean;
import org.sakaiproject.tool.assessment.ui.listener.delivery.BeginDeliveryActionListener;
import org.sakaiproject.tool.assessment.ui.listener.delivery.DeliveryActionListener;
import org.sakaiproject.tool.assessment.ui.listener.util.ContextUtil;
import org.sakaiproject.util.FormattedText;
import org.sakaiproject.util.ResourceLoader;
import org.sakaiproject.component.cover.ServerConfigurationService;
/**
*
* @author Joshua Ryan <a href="mailto:joshua.ryan@asu.edu">joshua.ryan@asu.edu</a>
*
* This class is basically just a conveinceince class for abstracting the creation of
* PDF's from assessments
*
*/
public class PDFAssessmentBean implements Serializable {
private static final long serialVersionUID = 1L;
private static Log log = LogFactory.getLog(PDFAssessmentBean.class);
private ResourceLoader printMessages = new ResourceLoader("org.sakaiproject.tool.assessment.bundle.PrintMessages");
private ResourceLoader authorMessages = new ResourceLoader("org.sakaiproject.tool.assessment.bundle.AuthorMessages");
private ResourceLoader deliveryMessages = new ResourceLoader("org.sakaiproject.tool.assessment.bundle.DeliveryMessages");
private ResourceLoader commonMessages = new ResourceLoader("org.sakaiproject.tool.assessment.bundle.CommonMessages");
private String intro = "";
private String title = "";
private ArrayList parts = null;
private ArrayList deliveryParts = null;
private int baseFontSize = 5;
private String actionString = "";
public PDFAssessmentBean() {
if (log.isInfoEnabled())
log.info("Starting PDFAssessementBean with session scope");
}
/**
* Gets the pdf assessments intro
* @return assessment intor in html
*/
public String getIntro() {
return intro;
}
/**
* sets the pdf assessments intro
* @param intro in html
*/
public void setIntro(String intro) {
this.intro = FormattedText.unEscapeHtml(intro);
}
/**
* gets the delivery bean parts of the assessment
* @return
*/
public ArrayList getDeliveryParts() {
return deliveryParts;
}
/**
* gets the parts of the assessment
* @return
*/
public ArrayList getParts() {
return parts;
}
/**
* gets what should be the full set of html chunks for an assessment
* @return
*/
public ArrayList getHtmlChunks() {
return parts;
}
/**
* sets the delivery parts
* @param deliveryParts
*/
public void setDeliveryParts(ArrayList deliveryParts) {
ArrayList parts = new ArrayList();
int numberQuestion = 1;
for (int i=0; i<deliveryParts.size(); i++) {
SectionContentsBean section = new SectionContentsBean((org.sakaiproject.tool.assessment.ui.bean.delivery.SectionContentsBean)deliveryParts.get(i));
ArrayList items = section.getItemContents();
// Renumbering
for (int j=0; items != null && j<items.size(); j++) {
ItemContentsBean itemContents = (ItemContentsBean)items.get(j);
itemContents.setNumber(numberQuestion++);
// Order answers in order (A, B, C, D)
ArrayList question = itemContents.getItemData().getItemTextArraySorted();
for (int k=0; k<question.size(); k++) {
PublishedItemText itemtext = (PublishedItemText)question.get(k);
ArrayList answers = itemtext.getAnswerArray();
for (int t=0; t<answers.size(); t++) {
PublishedAnswer answer = (PublishedAnswer)answers.get(t);
if (answer.getLabel() != null && !answer.getLabel().equals(""))
answer.setSequence(Long.valueOf(answer.getLabel().charAt(0) - 64));
}
}
}
parts.add(section);
}
this.deliveryParts = parts;
}
/**
/**
* sets the parts
* @param parts
*/
public void setParts(ArrayList parts) {
this.parts = parts;
}
/**
* gets the Title
* @return
*/
public String getTitle() {
return title;
}
/**
* sets the Title
* @param title
*/
public void setTitle(String title) {
this.title = title;
}
/**
* generates the pdf file name
* @return pdf file name
*/
public String genName() {
//There has got to be a cleaner way to get a good time stamp in java?
Calendar cal = new GregorianCalendar();
int year = cal.get(Calendar.YEAR);
int month = cal.get(Calendar.MONTH);
int day = cal.get(Calendar.DAY_OF_MONTH);
int hour = cal.get(Calendar.HOUR_OF_DAY);
int min = cal.get(Calendar.MINUTE);
int sec = cal.get(Calendar.SECOND);
String fTitle = FormattedText.convertFormattedTextToPlaintext(title);
int end = Math.min(fTitle.length(), 9);
StringBuffer name = new StringBuffer(fTitle.substring(0, end));
name.append(year);
name.append(month);
name.append(day);
name.append(hour);
name.append(min);
name.append(sec);
name.append(".pdf");
if (log.isWarnEnabled())
log.warn(name.toString());
//log.warn(fTitle.substring(0, end) + year + month + day + hour + min + sec + ".pdf");
return name.toString().replace(" ", "_");
}
public String prepPDF() {
DeliveryBean deliveryBean = (DeliveryBean) ContextUtil.lookupBean("delivery");
deliveryBean.setActionString("previewAssessment");
setActionString(ContextUtil.lookupParam("actionString"));
// Call all the listeners needed to populate the deliveryBean...
BeginDeliveryActionListener beginDeliveryAL = new BeginDeliveryActionListener();
DeliveryActionListener deliveryAL = new DeliveryActionListener();
beginDeliveryAL.processAction(null);
deliveryAL.processAction(null);
setDeliveryParts(deliveryBean.getTableOfContents().getPartsContents());
prepDocumentPDF();
return "print";
}
public String prepDocumentPDF() {
DeliveryBean deliveryBean = (DeliveryBean) ContextUtil.lookupBean("delivery");
PrintSettingsBean printSetting = (PrintSettingsBean) ContextUtil.lookupBean("printSettings");
if (printSetting.getShowPartIntros().booleanValue()) {
StringBuffer assessmentIntros = new StringBuffer();
if (deliveryBean.getInstructorMessage() != null && !"".equals(deliveryBean.getInstructorMessage())) {
assessmentIntros.append(deliveryBean.getInstructorMessage());
assessmentIntros.append("<br />");
}
if (deliveryBean.getAttachmentList() != null && deliveryBean.getAttachmentList().size() > 0) {
assessmentIntros.append("<br />");
assessmentIntros.append(printMessages.getString("attachments"));
List assessmentAttachmentList = deliveryBean.getAttachmentList();
Iterator assessmentAttachmentIter = assessmentAttachmentList.iterator();
while (assessmentAttachmentIter.hasNext()) {
assessmentIntros.append("<br />");
PublishedAssessmentAttachment assessmentAttachment = (PublishedAssessmentAttachment) assessmentAttachmentIter.next();
if (assessmentAttachment.getMimeType().equalsIgnoreCase("image/jpeg") ||
assessmentAttachment.getMimeType().equalsIgnoreCase("image/pjpeg") ||
assessmentAttachment.getMimeType().equalsIgnoreCase("image/gif") ||
assessmentAttachment.getMimeType().equalsIgnoreCase("image/png")) {
assessmentIntros.append(" <img src=\"/samigo");
assessmentIntros.append(assessmentAttachment.getResourceId());
assessmentIntros.append("\" />");
}
else {
assessmentIntros.append(" ");
assessmentIntros.append(assessmentAttachment.getFilename());
}
}
}
setIntro(assessmentIntros.toString());
}
else {
setIntro("");
}
ArrayList pdfParts = new ArrayList();
//for each part in an assessment we add a pdfPart to the pdfBean
for (int i = 0; i < deliveryParts.size(); i++) {
//get the current item
SectionContentsBean section = (SectionContentsBean) deliveryParts.get(i);
ArrayList items = section.getItemContents();
ArrayList resources = new ArrayList();
//create a new part and empty list to fill with items
PDFPartBean pdfPart = new PDFPartBean();
pdfPart.setSectionId(section.getSectionId());
StringBuffer partIntros = new StringBuffer();
partIntros.append("<h2>");
partIntros.append(authorMessages.getString("p"));
partIntros.append(" ");
partIntros.append(i+1);
if (!printSetting.getShowPartIntros().booleanValue()) {
partIntros.append("</h2>");
}
else {
if ("Default".equalsIgnoreCase(section.getTitle())) {
partIntros.append("</h2>");
}
else {
partIntros.append(": ");
partIntros.append(section.getTitle());
partIntros.append("</h2>");
}
partIntros.append("<br />");
if (section.getDescription() != null) {
partIntros.append(section.getDescription());
}
partIntros.append("<br />");
if (section.getAttachmentList() != null && section.getAttachmentList().size() > 0) {
partIntros.append("<br />");
partIntros.append(printMessages.getString("attachments"));
List partAttachmentList = section.getAttachmentList();
Iterator partAttachmentIter = partAttachmentList.iterator();
while (partAttachmentIter.hasNext()) {
partIntros.append("<br />");
PublishedSectionAttachment partAttachment = (PublishedSectionAttachment) partAttachmentIter.next();
if (partAttachment.getMimeType().equalsIgnoreCase("image/jpeg") ||
partAttachment.getMimeType().equalsIgnoreCase("image/pjpeg") ||
partAttachment.getMimeType().equalsIgnoreCase("image/gif") ||
partAttachment.getMimeType().equalsIgnoreCase("image/png")) {
partIntros.append(" <img src=\"/samigo");
partIntros.append(partAttachment.getResourceId());
partIntros.append("\" />");
}
else {
partIntros.append(" ");
partIntros.append(partAttachment.getFilename());
}
}
}
}
pdfPart.setIntro(partIntros.toString());
ArrayList pdfItems = new ArrayList();
//for each item in a section we add a blank pdfItem to the pdfPart
for (int j = 0; j < items.size(); j++) {
PDFItemBean pdfItem = new PDFItemBean();
ItemContentsBean item = (ItemContentsBean) items.get(j);
StringBuffer legacy = new StringBuffer("<h3>");
legacy.append(item.getSequence());
legacy.append("</h3>");
pdfItem.setItemId(item.getItemData().getItemId());
StringBuffer contentBuffer = new StringBuffer();
if (!(item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_BLANK) || item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_NUMERIC))) {
contentBuffer.append("<br />");
contentBuffer.append(item.getItemData().getText());
contentBuffer.append("<br />");
}
if (item.getItemData().getItemAttachmentList() != null && item.getItemData().getItemAttachmentList().size() > 0) {
contentBuffer.append("<br />");
contentBuffer.append(printMessages.getString("attachments"));
contentBuffer.append("<br />");
List itemAttachmentList = item.getItemData().getItemAttachmentList();
Iterator itemAttachmentIter = itemAttachmentList.iterator();
while (itemAttachmentIter.hasNext()) {
PublishedItemAttachment itemAttachment = (PublishedItemAttachment) itemAttachmentIter.next();
if (itemAttachment.getMimeType().equalsIgnoreCase("image/jpeg") ||
itemAttachment.getMimeType().equalsIgnoreCase("image/pjpeg") ||
itemAttachment.getMimeType().equalsIgnoreCase("image/gif") ||
itemAttachment.getMimeType().equalsIgnoreCase("image/png")) {
contentBuffer.append(" <img src=\"/samigo");
contentBuffer.append(itemAttachment.getResourceId());
contentBuffer.append("\" />");
}
else {
contentBuffer.append(" ");
contentBuffer.append(itemAttachment.getFilename());
}
contentBuffer.append("<br />");
}
}
if (item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_BLANK) || item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_NUMERIC)) {
if (item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_NUMERIC)) {
contentBuffer.append("<br />");
contentBuffer.append(deliveryMessages.getString("fin_accepted_instruction"));
contentBuffer.append("<br />");
}
contentBuffer.append("<br />");
contentBuffer.append(item.getItemData().getText());
contentBuffer.append("<br />");
}
if (item.getItemData().getTypeId().equals(TypeIfc.AUDIO_RECORDING)) {
contentBuffer.append(printMessages.getString("time_allowed_seconds"));
contentBuffer.append(":");
contentBuffer.append(item.getItemData().getDuration());
contentBuffer.append("<br />");
contentBuffer.append(printMessages.getString("number_of_tries"));
contentBuffer.append(":");
contentBuffer.append(item.getItemData().getTriesAllowed());
contentBuffer.append("<br />");
}
if (item.getItemData().getTypeId().equals(TypeIfc.FILE_UPLOAD)) {
contentBuffer.append(printMessages.getString("upload_instruction"));
contentBuffer.append("<br />");
contentBuffer.append(printMessages.getString("file"));
contentBuffer.append(":");
contentBuffer.append("<input type='text' size='50' />");
contentBuffer.append("<input type='button' value='");
contentBuffer.append(printMessages.getString("browse"));
contentBuffer.append(":' />");
contentBuffer.append("<input type='button' value='");
contentBuffer.append(printMessages.getString("upload"));
contentBuffer.append(":' />");
contentBuffer.append("<br />");
}
if (item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CORRECT) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CHOICE) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CHOICE_SURVEY) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CORRECT_SINGLE_SELECTION) ||
item.getItemData().getTypeId().equals(TypeIfc.TRUE_FALSE) ||
item.getItemData().getTypeId().equals(TypeIfc.MATRIX_CHOICES_SURVEY)) {
ArrayList question = item.getItemData().getItemTextArraySorted();
for (int k=0; k<question.size(); k++) {
PublishedItemText itemtext = (PublishedItemText)question.get(k);
ArrayList answers = itemtext.getAnswerArraySorted();
contentBuffer.append("<table cols='20' width='100%'>");
for (int t=0; t<answers.size(); t++) {
PublishedAnswer answer = (PublishedAnswer)answers.get(t);
if (StringUtils.isBlank(answer.getText())) break;
contentBuffer.append("<tr>");
contentBuffer.append(getContentAnswer(item, answer, printSetting));
contentBuffer.append("</tr>");
}
contentBuffer.append("</table>");
}
}
if (item.getItemData().getTypeId().equals(TypeIfc.MATCHING)) {
contentBuffer.append("<table cols='20' width='100%'>");
ArrayList question = item.getMatchingArray();
for (int k=0; k<question.size(); k++) {
MatchingBean matching = (MatchingBean)question.get(k);
// if there are distractors or shared matches, answers will
// have fewer answers that matches.
String answer = "";
if (k < item.getAnswers().size()) {
answer = (String)item.getAnswers().get(k);
}
if (matching.getText() == null) break;
contentBuffer.append("<tr><td colspan='10'>");
contentBuffer.append(matching.getText());
contentBuffer.append("</td>");
contentBuffer.append("<td colspan='10'>");
contentBuffer.append(answer);
contentBuffer.append("</td></tr>");
}
contentBuffer.append("</table>");
}
if (printSetting.getShowKeys().booleanValue() || printSetting.getShowKeysFeedback().booleanValue()) {
contentBuffer.append("<br />");
contentBuffer.append(getContentQuestion(item, printSetting));
}
pdfItem.setContent(contentBuffer.toString());
if (legacy != null) {
pdfItem.setMeta(legacy.toString());
}
pdfItems.add(pdfItem);
}
pdfPart.setQuestions(pdfItems);
pdfPart.setResources(resources);
if (resources.size() > 0)
pdfPart.setHasResources(Boolean.valueOf(true));
pdfParts.add(pdfPart);
}
//set the new colleciton of PDF beans to be the contents of the pdfassessment
setParts(pdfParts);
setTitle(deliveryBean.getAssessmentTitle());
return "print";
}
private String getContentAnswer(ItemContentsBean item, PublishedAnswer answer, PrintSettingsBean printSetting) {
StringBuffer contentBuffer = new StringBuffer();
if (item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CORRECT) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CHOICE) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CHOICE_SURVEY) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CORRECT_SINGLE_SELECTION)) {
if (item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CORRECT))
contentBuffer.append("<td colspan='1'><img src='/samigo-app/images/unchecked.gif' /></td>");
else
contentBuffer.append("<td colspan='1'><img src='/samigo-app/images/radiounchecked.gif' /></td>");
contentBuffer.append("<td colspan='10'>");
if (!item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CHOICE_SURVEY)) {
contentBuffer.append(answer.getLabel());
contentBuffer.append(". ");
}
contentBuffer.append(answer.getText());
contentBuffer.append("</td>");
contentBuffer.append("<td colspan='9'>");
if (printSetting.getShowKeysFeedback()) {
contentBuffer.append("<h6>");
contentBuffer.append(commonMessages.getString("feedback"));
contentBuffer.append(": ");
if (answer.getGeneralAnswerFeedback() != null && !answer.getGeneralAnswerFeedback().equals(""))
contentBuffer.append(answer.getGeneralAnswerFeedback());
else
contentBuffer.append("--------");
contentBuffer.append("</h6>");
}
contentBuffer.append("</td>");
}
if (item.getItemData().getTypeId().equals(TypeIfc.TRUE_FALSE)) {
contentBuffer.append("<td colspan='1'><img src='/samigo-app/images/radiounchecked.gif' /></td>");
contentBuffer.append("<td colspan='19'>");
contentBuffer.append(answer.getText());
contentBuffer.append("</td>");
}
return contentBuffer.toString();
}
private String getContentQuestion(ItemContentsBean item, PrintSettingsBean printSetting) {
StringBuffer contentBuffer = new StringBuffer("<h6>");
contentBuffer.append(printMessages.getString("answer_point"));
contentBuffer.append(": ");
contentBuffer.append(item.getItemData().getScore());
contentBuffer.append(" ");
contentBuffer.append(authorMessages.getString("points_lower_case"));
if (!item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CHOICE_SURVEY) &&
!item.getItemData().getTypeId().equals(TypeIfc.AUDIO_RECORDING) &&
!item.getItemData().getTypeId().equals(TypeIfc.FILE_UPLOAD)) {
contentBuffer.append("<br />");
if (item.getItemData().getTypeId().equals(TypeIfc.ESSAY_QUESTION)) {
contentBuffer.append(printMessages.getString("answer_model"));
contentBuffer.append(": ");
}
else {
contentBuffer.append(printMessages.getString("answer_key"));
contentBuffer.append(": ");
}
if (item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_BLANK) ||
item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_NUMERIC) ||
item.getItemData().getTypeId().equals(TypeIfc.MATCHING))
contentBuffer.append(item.getKey());
else if (item.getItemData().getTypeId().equals(TypeIfc.ESSAY_QUESTION)) {
if (item.getKey() != null && !item.getKey().equals("") && !item.getKey().equals("null"))
contentBuffer.append(item.getKey());
else
contentBuffer.append("--------");
}
else
contentBuffer.append(item.getItemData().getAnswerKey());
}
if (printSetting.getShowKeysFeedback().booleanValue()) {
if (item.getItemData().getTypeId().equals(TypeIfc.ESSAY_QUESTION) ||
item.getItemData().getTypeId().equals(TypeIfc.AUDIO_RECORDING) ||
item.getItemData().getTypeId().equals(TypeIfc.FILE_UPLOAD)) {
contentBuffer.append("<br />");
contentBuffer.append(commonMessages.getString("feedback"));
contentBuffer.append(": ");
if (item.getItemData().getGeneralItemFeedback() != null && !item.getItemData().getGeneralItemFeedback().equals(""))
contentBuffer.append(item.getItemData().getGeneralItemFeedback());
else
contentBuffer.append("--------");
}
if (item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CORRECT) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CHOICE) ||
item.getItemData().getTypeId().equals(TypeIfc.MULTIPLE_CORRECT_SINGLE_SELECTION) ||
item.getItemData().getTypeId().equals(TypeIfc.TRUE_FALSE) ||
item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_BLANK) ||
item.getItemData().getTypeId().equals(TypeIfc.FILL_IN_NUMERIC) ||
item.getItemData().getTypeId().equals(TypeIfc.MATCHING)) {
contentBuffer.append("<br />");
contentBuffer.append(printMessages.getString("correct_feedback"));
contentBuffer.append(": ");
if (item.getItemData().getCorrectItemFeedback() != null && !item.getItemData().getCorrectItemFeedback().equals(""))
contentBuffer.append(item.getItemData().getCorrectItemFeedback());
else
contentBuffer.append("--------");
contentBuffer.append("<br />");
contentBuffer.append(printMessages.getString("incorrect_feedback"));
contentBuffer.append(": ");
if (item.getItemData().getInCorrectItemFeedback() != null && !item.getItemData().getInCorrectItemFeedback().equals(""))
contentBuffer.append(item.getItemData().getInCorrectItemFeedback());
else
contentBuffer.append("--------");
}
}
contentBuffer.append("</h6>");
return contentBuffer.toString();
}
public void getPDFAttachment() {
prepDocumentPDF();
ByteArrayOutputStream pdf = getStream();
FacesContext faces = FacesContext.getCurrentInstance();
HttpServletResponse response = (HttpServletResponse)faces.getExternalContext().getResponse();
response.reset();
response.setHeader("Pragma", "public");
response.setHeader("Cache-Control", "public, must-revalidate, post-check=0, pre-check=0, max-age=0");
response.setContentType("application/pdf");
response.setHeader("Content-disposition", "attachment; filename=" + genName());
response.setContentLength(pdf.toByteArray().length);
OutputStream out = null;
try {
out = response.getOutputStream();
out.write(pdf.toByteArray());
out.flush();
}
catch (IOException e) {
log.error(e);
e.printStackTrace();
}
finally {
try {
if (out != null)
out.close();
}
catch (IOException e) {
log.error(e);
e.printStackTrace();
}
}
faces.responseComplete();
}
/**
* Converts all nice new school html into old school
* font tagged up html that HTMLWorker will actually
* parse right
*
* @param input
*/
private String oldschoolIfy(String input) {
if (log.isDebugEnabled())
log.debug("starting oldschoolify with: " + input);
StringBuffer text1 = new StringBuffer("<div><font color='#01a5cb' size='");
int size1 = (int)(baseFontSize * 1.1);
text1.append(size1);
text1.append("'");
input = input.replaceAll("<h1", text1.toString());
input = input.replaceAll("<h2", text1.toString());
StringBuffer text2 = new StringBuffer("<div><font color='#CCCCCC' size='");
int size2 = (int)(baseFontSize * 1);
text2.append(size2);
text2.append("'");
input = input.replaceAll("<h3", text2.toString());
StringBuffer text3 = new StringBuffer("<div><font size='");
int size3 = (int)(baseFontSize * .85);
text3.append(size3);
text3.append("'");
input = input.replaceAll("<h4", text3.toString());
StringBuffer text4 = new StringBuffer("<div><font size='");
int size4 = (int)(baseFontSize * .8);
text4.append(size4);
text4.append("'");
input = input.replaceAll("<h5", text4.toString());
StringBuffer text5 = new StringBuffer("<div><font color='#333333' size='");
int size5 = (int)(baseFontSize * .6);
text5.append(size5);
text5.append("'");
input = input.replaceAll("<h6", text5.toString());
input = input.replaceAll("</h.>", "</font></div>");
return input;
}
/**
* Turns a string into a StringReader with out the fuss of an IOException
*
* @param input
* @return StringReader
*/
private Reader safeReader(String input) {
StringReader output = null;
if (input == null) {
input = "";
}
else {
input = oldschoolIfy(input);
}
try {
output = new StringReader(input + "<br/>");
}
catch(Exception e) {
log.error("could not get StringReader for String " + input + " due to : " + e);
}
return output;
}
public ByteArrayOutputStream getStream() {
ByteArrayOutputStream output = new ByteArrayOutputStream();
try {
if (log.isInfoEnabled())
log.info("starting PDF generation" );
Document document = new Document(PageSize.A4, 20, 20, 20, 20);
PdfWriter docWriter = PdfWriter.getInstance(document, output);
document.open();
document.resetPageCount();
HTMLWorker worker = new HTMLWorker(document);
HashMap props = worker.getInterfaceProps();
if (props == null) {
props = new HashMap();
}
float prevs = 0;
props.put("img_baseurl", ServerConfigurationService.getServerUrl());
worker.setInterfaceProps(props);
//TODO make a real style sheet
StyleSheet style = null;
StringBuffer head = new StringBuffer(printMessages.getString("print_name_form"));
head.append("<br />");
head.append(printMessages.getString("print_score_form"));
head.append("<br /><br /><h1>");
head.append(title);
head.append("</h1><br />");
head.append(intro);
head.append("<br />");
//head = head.replaceAll("[ \t\n\f\r]+", " ");
//parse out the elements from the html
ArrayList elementBuffer = HTMLWorker.parseToList(safeReader(head.toString()), style, props);
float[] singleWidth = {1f};
PdfPTable single = new PdfPTable(singleWidth);
single.setWidthPercentage(100f);
PdfPCell cell = new PdfPCell();
cell.setBorderWidth(0);
for (int k = 0; k < elementBuffer.size(); k++) {
cell.addElement((Element)elementBuffer.get(k));
}
single.addCell(cell);
prevs += single.getTotalHeight() % document.getPageSize().height();
//TODO do we want a new page here ... thus giving the cover page look?
document.add(single);
document.add(Chunk.NEWLINE);
//extract the html and parse it into pdf
ArrayList parts = getHtmlChunks();
for (int i = 0; i < parts.size(); i++) {
//add new page to start each new part
if (i > 0) {
document.newPage();
}
PDFPartBean pBean = (PDFPartBean) parts.get(i);
if (pBean.getIntro() != null && !"".equals(pBean.getIntro())) {
elementBuffer = HTMLWorker.parseToList(safeReader(pBean.getIntro()), style, props);
single = new PdfPTable(singleWidth);
single.setWidthPercentage(100f);
cell = new PdfPCell();
cell.setBorderWidth(0);
for (int k = 0; k < elementBuffer.size(); k++) {
cell.addElement((Element)elementBuffer.get(k));
}
single.addCell(cell);
prevs += single.getTotalHeight() % document.getPageSize().height();
document.add(single);
}
ArrayList items = pBean.getQuestions();
for (int j = 0; j < items.size(); j++) {
PDFItemBean iBean = (PDFItemBean) items.get(j);
float[] widths = {0.1f, 0.9f};
PdfPTable table = new PdfPTable(widths);
table.setWidthPercentage(100f);
PdfPCell leftCell = new PdfPCell();
PdfPCell rightCell = new PdfPCell();
leftCell.setBorderWidth(0);
leftCell.setPadding(0);
leftCell.setLeading(0.00f, 0.00f);
leftCell.setHorizontalAlignment(Element.ALIGN_RIGHT);
leftCell.setVerticalAlignment(Element.ALIGN_TOP);
rightCell.setBorderWidth(0);
elementBuffer = HTMLWorker.parseToList(safeReader(iBean.getMeta()), style, props);
for (int k = 0; k < elementBuffer.size(); k++) {
Element element = (Element)elementBuffer.get(k);
if (element instanceof Paragraph) {
Paragraph p = (Paragraph)element;
p.getFont().setColor(Color.GRAY);
p.setAlignment(Paragraph.ALIGN_CENTER);
}
leftCell.addElement(element);
}
table.addCell(leftCell);
elementBuffer = HTMLWorker.parseToList(safeReader(iBean.getContent()), style, props);
for (int k = 0; k < elementBuffer.size(); k++) {
Element element = (Element)elementBuffer.get(k);
rightCell.addElement(element);
}
table.addCell(rightCell);
if (table.getTotalHeight() + prevs > document.getPageSize().height())
document.newPage();
document.add(table);
document.add(Chunk.NEWLINE);
//TODO add PDFTable and a collumn
//worker.parse(safeReader(iBean.getMeta()));
//TODO column break
//worker.parse(safeReader(iBean.getContent()));
//TODO end column and table
}
}
document.close();
docWriter.close();
}
catch(Exception e) {
e.printStackTrace();
System.err.println("document: " + e.getMessage());
}
return output;
}
public String getBaseFontSize() {
return "" + baseFontSize;
}
public void setBaseFontSize(String baseFontSize) {
this.baseFontSize = Integer.parseInt(baseFontSize);
}
/**
* @return the actionString
*/
public String getActionString() {
return actionString;
}
/**
* @param actionString the actionString to set
*/
public void setActionString(String actionString) {
this.actionString = actionString;
}
public String getSizeDeliveryParts() {
return "" + deliveryParts.size();
}
public String getTotalQuestions() {
int items = 0;
for (int i=0; i<deliveryParts.size(); i++) {
SectionContentsBean section = (SectionContentsBean) deliveryParts.get(i);
items += section.getItemContents().size();
}
return "" + items;
}
}