Bug 353401

Summary: Feature requst: "typewriter" annotation tool
Product: [Applications] okular Reporter: noric <g11072813>
Component: PDF backendAssignee: Okular developers <okular-devel>
Status: RESOLVED FIXED    
Severity: wishlist CC: aacid, any65889, dileepsankhla.ds, efelthauser, haxtibal, lopezibanez, nate, scroogemcduck, simgunz, simonandric5, sombragris, sumit.sahrawat.apm13
Priority: NOR    
Version: unspecified   
Target Milestone: ---   
Platform: Mint (Ubuntu based)   
OS: Linux   
Latest Commit: Version Fixed In: 18.12.0
Sentry Crash Report:
Attachments: QT vs. poppler - RadioButtonEdit form field
Qt vs. poppler - TextAreaEdit

Description noric 2015-10-01 10:37:11 UTC
I find Okular to be quite complete, in regards of annotations, but there's still a missing feature: the "typewriter" tool, which lets you type any kind of text anywhere in the pdf file.

Is this on dev's wishlist, or is it only on mine? :-)

Thanks for your efforts.

Reproducible: Always
Comment 1 Manuel López-Ibáñez 2015-11-05 12:42:58 UTC
I think this can be approximated already with an inline note with white background. The downside is that currently is not possible to remove the border around the note, nor set the background to transparent. If those two things were possible, it would be exactly what is needed (and perhaps it could be provided by default).
Comment 2 Sumit Sahrawat 2015-11-05 16:43:48 UTC
I'm working on making the border width customizable, which when set to 0 removes the border entirely.
Comment 3 Gus Gustafson 2015-11-05 17:33:25 UTC
Some thoughts:
--What if the color of the "page" is not white? User will have to try to match the comment background color to page color, as best as possible. This can be difficult. Transparent background option would be important.
--Also, what will the experience be if there are very many places needing "typewriter"-type function on a page or document, if using inline comments? Have to change background color and border width for every one? That can be very user-unfriendly... Will Okular remember the last-used style setting for comments, and replicate it for next inline comment?
Comment 4 Manuel López-Ibáñez 2015-11-05 18:30:09 UTC
(In reply to Gus Gustafson from comment #3)
> --Also, what will the experience be if there are very many places needing
> "typewriter"-type function on a page or document, if using inline comments?
> Have to change background color and border width for every one? That can be
> very user-unfriendly... Will Okular remember the last-used style setting for
> comments, and replicate it for next inline comment?

You can create customized annotation styles. See the Okular Settings.
Comment 5 noric 2015-11-27 10:08:47 UTC
(In reply to Manuel López-Ibáñez from comment #1)
> I think this can be approximated already with an inline note with white
> background. The downside is that currently is not possible to remove the
> border around the note, nor set the background to transparent. If those two
> things were possible, it would be exactly what is needed (and perhaps it
> could be provided by default).

This is an idea, but it would need several tweaks (don't know if they are taking more work than actually coding an all new typewriter tool).
1) Removing the border (Sumit is already taking care of that).
2) Transparent background. A note with white background overlaps and hides the document's content. The current "opacity" setting won't help here, because it applies to not only the note's background but also to its text.
3) The text color is not adjustable, if I'm not mistaken.
4) It would be convenient to be able to adjust the note's dimensions. At present you are bound to the initial dimensions you set, so if you write a long text it's possible that the last part of that text won't fit in the note and won't display.
Comment 6 Sumit Sahrawat 2015-11-27 22:05:04 UTC
I forgot to mention it here, the review request I made has been merged.

1) There are still some improvements to be made, but the code that was merged works perfectly when it comes to removing borders. Issue #332887.
2-3) They are valid feature requests, and would make for good junior jobs I think. I will see if I can get atleast one of them done.
4) I will work on this in the current season of KDE session. Issue #177778.
Comment 7 Sumit Sahrawat 2015-11-28 00:17:36 UTC
I am willing to work on this, in case no one else is already working/wants to work on it.

Of the points mentioned above, point 4 would have to come later, but I think the feature can still be considered complete without it.
Comment 8 Sumit Sahrawat 2015-11-28 20:25:54 UTC
Seems like I underestimated the issues. 2-3 cannot be implemented without poppler support, sadly.
Comment 9 noric 2015-12-02 14:58:41 UTC
I asked Poppler's devs and they say FreeText is already implemented in Poppler. They say the actual typewriter tool needs to be implemented by Okular (and other readers relying on Poppler).
Comment 10 Sumit Sahrawat 2015-12-02 17:02:13 UTC
Thanks for the info noric. I'm willing to work on this, and will start soon if nobody has already begun.
Comment 11 Sumit Sahrawat 2015-12-03 10:35:45 UTC
I looked through the poppler source once again. I realized that even though the freeText annotation is implemented internally, the poppler-qt4 package doesn't export it.

Specifically, the Annotation class from poppler-qt4 has a SubType enumeration, which contains only 15 values. The Annot class from poppler has an AnnotSubtype enumeration, which contains 27 values. FreeText is one of the values in poppler but not in poppler-qt4.
Comment 12 noric 2015-12-05 11:48:41 UTC
Thanks Sumit, does this mean that Freetext is available only in qt5?
This is the bug I filed about Poppler: https://bugs.freedesktop.org/show_bug.cgi?id=93213. Once I'm sure I understand what you're telling me, I may ask Poppler's devs.
Comment 13 Sumit Sahrawat 2015-12-05 12:04:07 UTC
These are all the annotation subtypes in poppler: http://cgit.freedesktop.org/poppler/poppler/tree/poppler/Annot.h#n504

These are all the annotation subtypes in poppler-qt4: http://cgit.freedesktop.org/poppler/poppler/tree/qt4/src/poppler-annotation.h#n184

As you can see, poppler-qt4 doesn't have the FreeText type visible to the users.
Similarly, poppler-qt5 doesn't have it either.
Comment 14 noric 2015-12-06 22:50:42 UTC
This is where I asked Poppler's devs: https://bugs.freedesktop.org/show_bug.cgi?id=93213
Yesterday I reported your findings to them. Let's see if they can help.
Comment 15 Simone Gaiarin 2016-01-16 10:08:19 UTC
*** Bug 358062 has been marked as a duplicate of this bug. ***
Comment 16 sombragris 2016-06-16 19:46:52 UTC
Second this,. A "Typewriter Tool" equivalent (for an explanation in case it's necessary: http://documentgeek.blogspot.com/2011/01/acrobat-typewriter-tool-just-embrace-it_05.html) is something I sorely need to cut ties with the likes of Acrobat.
Comment 17 sombragris 2017-08-16 13:39:14 UTC
Please keep this in mind and consider implementing it as soon as possible. Thanks!!
Comment 18 Dileep Sankhla 2018-03-24 16:06:35 UTC
On Thu, Mar 22, 2018 at 4:13 AM, Tobias Deiminger <haxtibal@posteo.de> wrote:

Okular already let's you create FreeText annotations. The confusing thing is that they're called "inline notes" in Okulars manual, and they're represented as class TextAnnotation (with m_textType == TextAnnotation::InPlace) in Okular and Popplers QT5 frontend. Under the hood poppler generates a real FreeText annotation:

# qt5/src/poppler-annotation.cc
Annot* TextAnnotationPrivate::createNativeAnnot(::Page *destPage, DocumentData *doc)
{
    // ...
    PDFRectangle rect = boundaryToPdfRectangle(boundary, flags);
    if (textType == TextAnnotation::Linked)
    {
        pdfAnnot = new AnnotText(destPage->getDoc(), &rect);
    }
    else
    {
        GooString * da = toAppearanceString(textFont);
        pdfAnnot = new AnnotFreeText(destPage->getDoc(), &rect, da); // Here it is :-)
        delete da;
    }
    // ...
}

I assume that what really is missing is the FreeTextTypeWriter behavior. You can check the ISO 32000 PDF standard for FreeTextTypeWriter (IT entry of the FreeText object).

You can also fire up okular in gdb and convince yourself

$ gdb okular
(gdb) b AnnotFreeText::AnnotFreeText
(gdb) r

# load document, create inline note => we hit popplers AnnotFreeText::AnnotFreeText constructor

Thread 1 "okular" hit Breakpoint 1, 0x00007fffce304220 in AnnotFreeText::AnnotFreeText(PDFDoc*, PDFRectangle*, GooString*)@plt () from /tmp/usr/lib/libpoppler-qt5.so.1
(gdb) bt
#0  0x00007fffce304220 in AnnotFreeText::AnnotFreeText(PDFDoc*, PDFRectangle*, GooString*)@plt () from /tmp/usr/lib/libpoppler-qt5.so.1
#1  0x00007fffce30d689 in Poppler::TextAnnotationPrivate::createNativeAnnot (
    this=0x7fffdc00ccb0, destPage=<optimized out>, doc=<optimized out>)
    at /home/tobias/workspace/OSScontrib/poppler/qt5/src/poppler-annotation.cc:1880
... backtrace shortened ...
Comment 19 Tobias Deiminger 2018-03-29 07:04:09 UTC
I guess that what I had in mind here https://bugs.kde.org/show_bug.cgi?id=358061#c2 is actually a kind of typewriter too. Is bug 358061 a duplicate?

If so, consider the linked poppler patches there.
Comment 20 Simone Gaiarin 2018-03-29 10:35:47 UTC
I don't think that bug 358061 is a duplicate. 

In my opinion the typewriter tool is to write text without any background anywhere in the file (e.g to fill forms), while inline notes are a different tool to add post-its like notes in the document (with a background). Very similar tools but with different purpose.
Comment 21 Tobias Deiminger 2018-03-31 11:59:39 UTC
> typewriter tool is to write text without any background anywhere (e.g to fill forms)
> inline notes are to add post-its like notes in the document (with a background)

Yeah, nice sum up, thanks!

Can we agree that both are for different user intent, but are technically almost the same? I mean, both are FreeText annotations under the hood (one with IT=FreeText, the other one with IT=FreeTextTypeWriter).

And both share the problem, that if we care for true WYSIWIG live editing we can't simply use a KTextEdit widget, because it could only approximate what we get in the end. We'd need something similar, but generator/poppler has to do the rendering. Such generator-rendered widgets would be a new concept in Okular, and they would need finer grained interaction of Okular <=> Poppler than what's currently possible. Patch [0] is a start, but may still not be enough. Do we care?

[0] https://bugs.freedesktop.org/show_bug.cgi?id=105796
Comment 22 Simone Gaiarin 2018-03-31 19:18:17 UTC
I cannot comment about the technicalities of poppler, but I agree that both TypeWriter and Inline note need a better WYSIWIG than a popup widget.
Comment 23 Tobias Deiminger 2018-04-01 19:13:39 UTC
Created attachment 111769 [details]
QT vs. poppler - RadioButtonEdit form field

Real world example where Qt-rendered radio button overlays poppler-rendered page.
Comment 24 Tobias Deiminger 2018-04-01 19:17:31 UTC
Created attachment 111770 [details]
Qt vs. poppler - TextAreaEdit

Real world example where Qt-rendered TextAreaEdit generates different visual representation compared to poppler-rendered print out of the same field.
Comment 25 Tobias Deiminger 2018-04-01 19:20:25 UTC
> TypeWriter and Inline note need a better WYSIWIG than a popup widget

Full ack. But that's not all, imho. The attachment 111769 [details] and attachment 111770 [details] make clear what I'm afraid of could happen to our typewriter/inline note feature if we go the easy way and just used a KTextEdit (even if it sticked and scrolled with the page). The screenshots are taken with PDF form fields from [0]. Form fields are user editable elements that scroll with the document, and nicely integrate with PageView via FormWidgetIface and QEvent. As thus, a typewriter feature could probably learn interesting things from FormWidget implementation. However FormWidgets have one weakness: They render content on their own by using KTextEdit, QRadioButton and so on - and overlay the page rendered by poppler. Using two different rendering engines with different settings for same purpose, namely Qt vs. poppler, evokes visual inconsistencies. Just see screenshots, or try it yourself.

To avoid those inconsistencies, I'd like to promote the idea of widgets that have a FormWidget-like PageView integration, but use generator/poppler as the one and only render engine.

@all: What do you think of that idea?

[0] http://www.windjack.com/downLoads/WJAnnotExample1.pdf
Comment 26 Albert Astals Cid 2018-04-03 20:41:57 UTC
(In reply to Tobias Deiminger from comment #25)
> To avoid those inconsistencies, I'd like to promote the idea of widgets that
> have a FormWidget-like PageView integration, but use generator/poppler as
> the one and only render engine.

Seems like an interesting idea to explore, just remember that you're going to need more layers of abstraction since okular core doesn't know anything about poppler
Comment 27 Tobias Deiminger 2018-04-05 20:10:29 UTC
> Seems like an interesting idea to explore, just remember that you're going
> to need more layers of abstraction since okular core doesn't know anything
> about poppler
Yes, and I have to relate myself a bit. As this feature request is candidate for a GSoC project, it's better to not put too much experimental ideas in here. Forget about my generator rendered widgets for now. Such exploration still can be done later, maybe together with bug 358061. Implementing an UI similar to existing inline notes will be good for a start. There we use QInputDialog::getMultiLineText for initial input, AnnotWindow for editing, and let the generator render the annotation along with the page (which avoids visual inconsistencies too).
Comment 28 Dileep Sankhla 2018-04-26 16:35:34 UTC
I'm working on this feature request as a GSoC 2018 student and you can find my project here: https://summerofcode.withgoogle.com/projects/#6053164340477952
and my proposal here: https://docs.google.com/document/d/1STBOz7Qcw1Wj6qB7XBg9er-wbsVx3g7Sw945WcHJfWU/edit?usp=sharing
Comments are always welcome and this thread will be updated regularly.
Comment 29 Tobias Deiminger 2018-09-25 20:47:15 UTC
Git commit 6dd7cf662d2335c035e72389978f32ee43dc94f2 by Tobias Deiminger, on behalf of Dileep Sankhla.
Committed on 25/09/2018 at 20:47.
Pushed by tobiasdeiminger into branch 'master'.

Add typewriter annotation tool

Summary:
Typewriter is originally specified by the PDF reference as special FreeText annotation, where Intent=FreeTextTypewriter. It features opaque letters on transparent background, so that users can fill non interactive forms. Herewith typewriter is implemented natively for PDF, and there's also an Okular specific implementation for other document types. The added tool reuses the inline note UI.

This work was done during GSoC 2018. See https://community.kde.org/GSoC/2018/StatusReports/DileepSankhla for details.

Test Plan:
- okularpartrc is generated (if not yet existing) with typewriter as 10th tool
- typewriter tool is also available in Annotation Tools -> Add, Typ "Typewriter"
- selecting the tool and left click into document opens inline note input dialog
- finishing creates an annotation similar to inline note, but with transparent background
- saving into PDF results in /Subtype FreeText /IT /FreeTextTypeWriter
- saving typewriter into archive stores color with alpha channel = 0x00
- opening annotated archive works, if archive was created with old Okular, and opened in patched Okular
- opening annotated archive works, if archive was created with patched Okular, and opened in old Okular

Reviewers: sander

Reviewed By: sander

Subscribers: ngraham, sander, okular-devel

Tags: #okular

Differential Revision: https://phabricator.kde.org/D15204

M  +34   -0    conf/editannottooldialog.cpp
M  +2    -1    conf/editannottooldialog.h
M  +6    -1    ui/annotationpropertiesdialog.cpp
M  +122  -74   ui/annotationwidgets.cpp
M  +28   -8    ui/annotationwidgets.h
M  +9    -1    ui/annotwindow.cpp
M  +2    -0    ui/data/CMakeLists.txt
A  +-    --    ui/data/sources/tool-typewriter-okular-colorizable.svgz
A  +-    --    ui/data/tool-typewriter-okular-colorizable.png
A  +-    --    ui/data/tool-typewriter-okular-colorizable@2x.png
M  +13   -8    ui/data/tools.xml
M  +6    -1    ui/guiutils.cpp
M  +1    -1    ui/pagepainter.cpp
M  +65   -44   ui/pageviewannotator.cpp

https://commits.kde.org/okular/6dd7cf662d2335c035e72389978f32ee43dc94f2
Comment 30 Christoph Feck 2018-11-30 13:11:21 UTC
*** Bug 397991 has been marked as a duplicate of this bug. ***