cancel
Showing results for 
Search instead for 
Did you mean: 

PDF file on my view

Former Member
0 Kudos

I want attach my PDF file on my web dynpro view

I have read in this forum about my problem the using of IFrame element but don't work.

Please help me, thanks

Accepted Solutions (1)

Accepted Solutions (1)

Former Member
0 Kudos

Hi Marco,

yes, you are right!

Store your pdf here:

In the mime repository (in your Web Dynpro project under -> src -> mimes ->Components -> <your Component>).

The application will look for C:
test.pdf on the engine, maybe your engine is installed on a linux server, it never will be found again...

If you store it in the mime repository, the file will be part of your WDproject and can be found whereever your engine is installed

Kind Regards

Stefanie

Former Member
0 Kudos

thanks

I use the string C:\Documents and Settings\mdamiano\Documents\SAP\workspace\pdf\src\mimes\Components\com.pdf.PdfComponent\TEST.pdf

but it don't work.

the IFrame is empity without error.

Can you help me againg?

thanks

Answers (7)

Answers (7)

Former Member
0 Kudos

Very intresting Thread.

I have one additional question: how is the byte data in context handled? If I think about large files and many users. storage in memory could be a problem for the server?

Anybody such detailed technical information?

Former Member
0 Kudos

I guess you could avoid such problems using mapping. Here's some example code, modified from an example:

// Original code from 'Thinking in Java, 3rd ed.' (c) Bruce Eckel 2002

// www.BruceEckel.com. See copyright notice in CopyRight.txt.

import java.io.RandomAccessFile;

import java.nio.MappedByteBuffer;

import java.nio.channels.FileChannel;

static int length = 0x8FFFFFF; // 128 Mb

...

public static void mapThis (String file) throws Exception {

MappedByteBuffer out = new RandomAccessFile(file, "rw")

.getChannel().map(FileChannel.MapMode.READ_WRITE, 0, length);

byte b;

if(!out.isLoaded()) out.load();

for (int i = 0; i < length; i++) {

b = out.get(i);

manipulate(b);

}

}

As for Bertram's solution, couldn't get it to work properly in a dynamic use case - I'm getting the input stream from IResource, and I get a ClassCastException everytime I use something different from InputStream. With that problem comes another one: InputStream.read() consuming the first byte from the file, which is a problem when dealing with PDF and DOC files, for example. Since I know the users are opening PDF files, made a quick-and-dirty workaround by inserting manually the missing byte. Really dirty one, actually - the byte changes with the file format. Below is the code I used - it works, but I'd love to see a different workaround.

public void openFile( )

{

//@@begin openFile()

//KM files are shown in a table

//get index of selected table row

int i = wdContext.nodeTableContent().getLeadSelection();

//get the name of the according object (resource)

String name = wdContext.nodeTableContent().getTableContentElementAt(i).getObjectName();

String path = wdContext.currentContextElement().getPath();

try {

RID pathRID = RID.getRID(path"/"name);

IWDClientUser wdClientUser = WDClientUser.getCurrentUser();

com.sap.security.api.IUser sapUser = wdClientUser.getSAPUser();

IUser ep5User = WPUMFactory.getUserFactory().getEP5User(sapUser);

IResourceContext resourceContext = new ResourceContext(ep5User);

com.sapportals.wcm.repository.IResource resource = ResourceFactory.getInstance().getResource(pathRID, resourceContext);

InputStream in = null;

in = resource.getContent().getInputStream();

int bSize = 10 * 1024;

byte[] bArr = new byte[bSize];

ByteArrayOutputStream baos = new ByteArrayOutputStream ();

int offset = 0;

int data;

//dirty!

String ext = name.substring(name.length()-3);

if("pdf".equalsIgnoreCase(WDWebResourceType.getWebResourceTypeForFileExtension(ext).getFileExtension())) {

byte b = '%';

baos.write(b);

}

while ( (data=in.read(bArr)) != -1)

{

baos.write(bArr);

}

IWDAttributeInfo pdfAttributeInfo = wdContext.getNodeInfo().getAttribute(IPrivateKMBrowserAppCompView.IContextElement.PDF_RESOURCE);

IWDModifiableBinaryType binaryType = (IWDModifiableBinaryType) pdfAttributeInfo.getModifiableSimpleType();

binaryType.setFileName(name);

binaryType.setMimeType(WDWebResourceType.getWebResourceTypeForFileExtension(ext));

wdContext.currentContextElement().setPDFResource(baos.toByteArray());

} catch (Exception e) {

}

//@@end

}

Udo_Ahle
Explorer
0 Kudos

Hello,

i use another method to integrate PDF's into the output. The complete documentation can be found in

BeGanz
Product and Topic Expert
Product and Topic Expert
0 Kudos

Hallo Marco,

Using the IFrame-UI-Element to display your static PDF document is a possible but not a recommended solution.

The IFrame-UI-Element will be deprecated in the next major NetWeaver release:

+This UI element may be withdrawn; with the first new major NetWeaver release it is no longer needed.

This UI element is too broken to be really useful and cannot be fixed.

For integration of non-Web Dynpro applications, please use the Enterprise Portal instead. For embedding (help) texts and the like special UI elements will be provided.+

Proposed Solution



You should better use the

InteractiveForm-UI-Element

, which is also applicable for displaying static (non-interactive) PDF resources.

To use the InteractiveForm-UI-element as a PDF-viewer you must define the following properties:

dataSource: <not bound>, templateSource: <not bound, not set i.e. empty>, <b>mode: usePDF</b>

Bind the property

pdfSource

to a context attribute of type binary, e.g. with attribute name PDFResource.

Controller Code

You must copy the deployed PDF resource (part of your project) to the context attribute PDFResource. This requires some custom code:

  //@@begin javadoc:wdDoInit()
  /** Hook method called to initialize controller. */
  //@@end
  public void wdDoInit()
  {
    //@@begin wdDoInit()

    IWDAttributeInfo attributeInfo =
      wdContext.getNodeInfo().getAttribute(IPrivatePDFDisplayView.IContextElement.PDF_RESOURCE);
    //		 make the context attribute's simple type modifiable.
    //		 Only with this line of code the binary data (stored within the
    //		 context attribute) can be parsed. The Web Dynpro Runtime stores
    //		 the mime-object’s metadata within the attribute’s

    // create a modifiable binary type for the context attribute which stores the MIME-object. 
    IWDModifiableBinaryType binaryType = (IWDModifiableBinaryType) attributeInfo.getModifiableSimpleType();

    // set binary type metadata. Without setting the mime type the client 
    // does not know how to open the downloaded file.        
    binaryType.setFileName(this.PDF_FILE_NAME);
    binaryType.setMimeType(WDWebResourceType.PDF);

    try {
      // The pdf file '<name>.jpg' is deployed with the Web Dynpro project 
      // (under src/mimes/Components...). The resource path (URL) for this mime 
      // objects can be accessed using the WDURLGenerator service.
      String resourcePath =
        WDURLGenerator.getResourcePath(wdComponentAPI.getDeployableObjectPart(), this.PDF_FILE_NAME);

      // retrieve byte array for given resource path and store it 
      // in context value attribute 'FileDownload'
      wdContext.currentContextElement().setPDFResource(this.getByteArrayFromResourcePath(resourcePath));

    } catch (WDAliasResolvingException e) {
      wdComponentAPI.getMessageManager().reportException(e.getLocalizedMessage(), true);
    } catch (Exception e) {
      throw new WDRuntimeException(e);
    }

    //@@end
  }

  /*
   * The following code section can be used for any Java code that is 
   * not to be visible to other controllers/views or that contains constructs
   * currently not supported directly by Web Dynpro (such as inner classes or
   * member variables etc.). </p>
   *
   * Note: The content of this section is in no way managed/controlled
   * by the Web Dynpro Designtime or the Web Dynpro Runtime. 
   */
  //@@begin others

  /**
   * Returns a byte array for a given file resource path
   */
  private byte[] getByteArrayFromResourcePath(String resourcePath)
    throws FileNotFoundException, IOException {
    FileInputStream in = new FileInputStream(new File(resourcePath));
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    int length;
    byte[] part = new byte[10 * 1024];
    while ((length = in.read(part)) != -1) {
      out.write(part, 0, length);
    }
    in.close();
    return out.toByteArray();
  }
  // store image file name in constant FILE_NAME
  private static final String PDF_FILE_NAME = "WD4J_WhatsNew_NW04s.pdf";
  //@@end

Your PDF document will then be displayed in the InteractiveForm-UI-Element.

Best regards, Bertram

Former Member
0 Kudos

thenaks.

My pdf is not static.

The user generate it by pressing a button.

The problem is the refresh of my file

Hi

BeGanz
Product and Topic Expert
Product and Topic Expert
0 Kudos

Hi Marco,

nevertheless my InteractiveForm-based solution should also be applicable for your dynamic use-case. Instead of storing the mime resource within the context attribute PDFResource at startup (wdDoInit()) you just do it within the action event handler.

1) The user presses a button and triggers an action

2) The action event handler delegates to a method generating the dynamic PDF resource

3) The resource is then stored in the context attribute PDFResource

4) The generated PDF should then be displayed on the UI.

As this solution is based on data-binding but not on an IFrame-based display of a cached resource your refresh problem should not occur.

Regards, Bertram

Former Member
0 Kudos

Hi Bertram

what is IPrivatePDFDisplayView?????

help me please

Former Member
0 Kudos

Hi Bertram

in this line :

wdContext.getNodeInfo().getAttribute(IPrivatePDFDisplayView.IContextElement.PDF_RESOURCE);

what is PDF_RESOURCE??

Thanks

BeGanz
Product and Topic Expert
Product and Topic Expert
0 Kudos

HI Marco,

PDF_RESOURCE is a genarated constant for the name of the defined context attribute PDFResource. For every context attribute you define under a certain context node (or root node) the I<node name>Element-API is extended with a corresponding constant.

By using this constant you avoid runtime exceptions based on spelling mistakes for your written attribute names:

wdContext.getNodeInfo().getAttribute("PDFResourZe") can be compiled but leads to a runtime exception.

Regards, Bertram

Former Member
0 Kudos

Hi Marco,

it is enough to say: "TEST.pdf"

Kind Regards

Stefanie

Former Member
0 Kudos

Hi Marco,

I don't know what your problem was. You can just try to specify the source property with the name of your pdf file and check whether it will run.

But if get the url using the code, you have to bind it.

Create a context attribute of type string, maybe you call it "myUrl", bind the source property of your IFrame to this attribute.

Then just set:

wdContext.currentContextElement().setMyUrl(pdfUrl);

Kind Regards

Stefanie

Former Member
0 Kudos

thanks.

i write this code:

pdfUrl =

WDWebResource

.getWebResource(wdComponentAPI.getDeployableObjectPart(), WDWebResourceType.PDF, "c:
TEST.pdf")

.getURL();

wdContext.currentContextElement().setP(pdfUrl);

i crete di binding how you write.

my Iframe is empty.

i think the problem is "c:
TEST.pdf"

thanks

Former Member
0 Kudos

Hi Marco,

If you just want to display a PDF file, you can use IFrame, store your pdf in the mime repository (in your Web Dynpro project under -> src -> mimes ->Components -> <your Component>), and retrieve it using this code:


String pdfUrl = null;
try
{
	pdfUrl =
		WDWebResource
			.getWebResource(wdComponentAPI.getDeployableObjectPart(), WDWebResourceType.PDF, "<pdf file name>.pdf")
			.getURL();
}
catch (Exception e)
{
	IWDMessageManager manager = wdComponentAPI.getMessageManager();
	manager.reportException("could not get WebResourceURL" + e.getMessage(), false);
}}

Bind the source property of your IFrame to a context attribute and set the pdfUrl as value of this context attribute

and try again...

Kind regards

Stefanie

Former Member
0 Kudos

what the meaning of "Bind the source property of your IFrame to a context attribute and set the pdfUrl as value of this context attribute"

I must binding the source property of IFrame whit the context attribute that containing pdfUrl???

please specify this point

Former Member
0 Kudos

Hi Stefanie,

I also have got the same requirement, can you help me out

Where shud i write the code?

Thanks in advance

Former Member
0 Kudos
Former Member
0 Kudos

I don't want use the interactive form to create a PDF.

I have crete it by using Function module standard of sap R3.

I have the PDF file on my desktop as well as a normal PDF file.

I Want attach it on my view

thanks