[jtablet-dev] XInputTabletManager on SVN

14 views
Skip to first unread message

Jason

unread,
Apr 20, 2010, 8:09:29 PM4/20/10
to jtablet-dev
I've just commited changeset 113 which adds the XInputTabletManager
implementation as well as a UNIX build script. There are a number of
problems with it still, but I'm at least seeing tablet info in the
demo applet.

To get the build to work I had to mark XiDevice and XiBus as public --
would somebody mind applying the following patches to the JPen SVN for
me (possibly with a notice similar to the one appearing in the Windows
files?)

Index: src/main/java/jpen/provider/xinput/XiDevice.java
===================================================================
--- src/main/java/jpen/provider/xinput/XiDevice.java (revision 243)
+++ src/main/java/jpen/provider/xinput/XiDevice.java (working copy)
@@ -28,7 +28,7 @@
import jpen.internal.Range;
import jpen.internal.ThreadUtils;

-final class XiDevice{
+public final class XiDevice{
static final Logger L=Logger.getLogger(XiDevice.class.getName());
//static { L.setLevel(Level.ALL); }

@@ -207,4 +207,4 @@
}
private static native int destroy(int cellIndex);
private static native String getError();
-}
\ No newline at end of file
+}
Index: src/main/java/jpen/provider/xinput/XiBus.java
===================================================================
--- src/main/java/jpen/provider/xinput/XiBus.java (revision 243)
+++ src/main/java/jpen/provider/xinput/XiBus.java (working copy)
@@ -23,11 +23,11 @@
import java.util.List;
import jpen.PenManager;

-final class XiBus {
+public final class XiBus {
private final int cellIndex;
private XiDevice xiDevice;

- XiBus() throws Exception {
+ public XiBus() throws Exception {
this.cellIndex=create();
if(cellIndex==-1)
throw new Exception(getError());

--
You received this message because you are subscribed to the Google Groups "jtablet-dev" group.
To post to this group, send email to jtabl...@googlegroups.com.
To unsubscribe from this group, send email to jtablet-dev...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/jtablet-dev?hl=en.

Nicolas Carranza

unread,
Apr 21, 2010, 3:36:58 AM4/21/10
to jtabl...@googlegroups.com

Thor Harald Johansen

unread,
Apr 21, 2010, 8:03:12 AM4/21/10
to jtabl...@googlegroups.com
Nicolas Carranza wrote:
> done :-)
> ( http://jpen.svn.sourceforge.net/viewvc/jpen?view=rev&revision=244 )
>

Nice! What does this mean for JTablet2 on Linux? How close are we?

Thor

Jason Gerecke

unread,
Apr 21, 2010, 3:16:27 PM4/21/10
to jtabl...@googlegroups.com
It depends on how much time I can find, as well as how evil my tablet wants to be ;)

I'd say we're significantly closer to having it work on Linux. I currently see three things that need to be addressed:

* Find out why JTablet2 reports tablet data, but doesn't actually draw anything
* Allow the mouse to work as a tablet when using XInputTabletManager
* Work on install packages

Jason

Marcello Bastéa-Forte

unread,
Apr 21, 2010, 5:14:41 PM4/21/10
to jtabl...@googlegroups.com
Just skimmed through your check-in (I won't pretend to understand all
of it) and noticed:

TabletDevice.Support floatSupport =
TabletDevice.Support.NO; //XInput API limits us here

Then further down you have:
float x =
device.getLevelRange(PLevel.Type.X).getRangedValue(
device.getValue(PLevel.Type.X)
);
float y =
device.getLevelRange(PLevel.Type.Y).getRangedValue(
device.getValue(PLevel.Type.Y)
);

Is the float x/y always an integer?

Looks great so far, though!

I'm guessing nothing is getting drawn because you haven't implemented
buttons yet (so cursorPressed/released events aren't occurring).

Marcello

Jason

unread,
Apr 21, 2010, 6:05:04 PM4/21/10
to jtablet-dev
Whoops!

XInput does only give us integers (which is probably why I gave the
support I did), but also gives us the range that those integers appear
in (which is how I make those floats). I had totally forgotten about
the support line above when I was writing the second chunk of code...
I'll fix that :)

Jason

On Apr 21, 2:14 pm, Marcello Bastéa-Forte <marce...@cellosoft.com>
wrote:
> For more options, visit this group athttp://groups.google.com/group/jtablet-dev?hl=en.

Jason

unread,
Apr 22, 2010, 1:49:17 PM4/22/10
to jtablet-dev
Code is now working properly with both the DemoPanel and the new
version of Sketcher. In addition to the lack of button support (which
I knew about), I was returning the wrong X/Y coordinates. For some
reason I assumed that JTablet wanted the floating-point coordinates in
the range 0.0-1.0 (like pressure), not in screen space.

The button code still needs work though. I was only able to get things
working properly by making a change to JPen that would completely
break their API. Specifically, getLastEventButton() doesn't return a
mask of currently-pressed buttons -- it returns a mask of buttons
which changed state. That would be fine if JPen provided me with
either the type of event I just read or if it reset it to 0 on each
non-button event, but it doesn't appear to.

The higher-up bits of JPen somehow work with the same data I'm using,
but I can't find the necessary code to copy :D Any enlightenment would
be appreciated...

Finally, I have some modifications to the JPen which request
ProximityIn and ProximityOut events and provide a
getLastEventProximity() method. These changes shouldn't be necessary
for JTablet to work, but since it does support proximity events I
figured I would add the necessary code to JPen. Let me know if you're
interested in in the patches.

Jason

Marcello Bastéa-Forte

unread,
Apr 22, 2010, 2:33:16 PM4/22/10
to jtabl...@googlegroups.com
Re: your comment in the code:

//FIXME: Shouldn't this be a bunch of binary ORs
//instead of a switch statement? Furthermore,
//shouldn't this be determined from rawTabletButtonMask?

The raw tablet button mask are the buttons pressed on the tablet and
the button/left/middle/right maps to awt MouseEvents... On Windows/Mac
you can remap the physical buttons in the control panel, so I'm trying
to maintain that mapping in the API.

Marcello

Nicolas Carranza

unread,
Apr 23, 2010, 12:57:11 AM4/23/10
to jtabl...@googlegroups.com
> The higher-up bits of JPen somehow work with the same data I'm using,
> but I can't find the necessary code to copy :D Any enlightenment would
> be appreciated...

JPen is currently not using the xinput/wintab providers to send button events,
it uses the jpen.provider.system provider (which listens the component awt
mouse button events to send jpen button events).

Marcello Bastéa-Forte

unread,
Apr 23, 2010, 11:11:12 AM4/23/10
to jtabl...@googlegroups.com
You don't /have/ to get the mouse events from XInput. On Mac OS X I
have all the data together, and it's easy, I'm using the same
MouseListener approach on JTablet's windows driver (there's no other
choice). There's a possibility of buttons/mouse coordinates being
out-of-sync, but I haven't noticed any problems in practice.

Getting the events from XInput feels more elegant to me (all the data
in one place), but I'm sure you could argue against it. I would say
for a first stab, do whatever is easier/you're more comfortable with.

Marcello

Jason Gerecke

unread,
Apr 28, 2010, 6:14:42 PM4/28/10
to jtabl...@googlegroups.com
I see. Its good to know that I'm not missing some obvious loophole :) I'm still working on also listening for AWT events (since the mouse is useless as a "tablet" without them), which should fix the problem without any changes to JPen.

That said, I was wondering how interested you'd be in the patches I made to JPen. The button patch as listed modifies the "lastEventButton" variable to actually be a button mask instead of a copy of the XDeviceButtonEvent "button" variable (this could, of course, be modified to store the mask in an appropriately-named variable). The proximity patch adds a "getLastEventProximity" method to Java, as well as all necessary support in the C code.

If you decide to apply both patches, I recommend applying button.patch first. Since it only modifies a single line, proximity.patch shouldn't complain if run second.

Jason

On Thu, Apr 22, 2010 at 9:57 PM, Nicolas Carranza <nica...@gmail.com> wrote:
button.patch
proximity.patch

Marcello Bastéa-Forte

unread,
May 3, 2010, 7:04:46 PM5/3/10
to jtabl...@googlegroups.com
What's next? Do you want to touch base on things you have questions
about? (I noticed you put a bunch of questions in your comments.) Do
you want to do an alpha release of the linux build?

Marcello

Nicolas Carranza

unread,
May 4, 2010, 1:59:10 AM5/4/10
to jtabl...@googlegroups.com
Nice patches. I applied them and did a couple of changes: instead of using
lastEventButton to hold the button mask values I created a new
field "lastEventDeviceState", added XiDevice.EventType.PROXIMITY enum values.
I haven't tested this new code jet. Let me know if you find problems. (
http://jpen.svn.sourceforge.net/viewvc/jpen?view=rev&revision=245 )

Nicolas
> > jtablet-dev...@googlegroups.com<jtablet-dev%2Bunsubscribe@google
> >groups.com> .

Jason Gerecke

unread,
May 7, 2010, 6:43:22 PM5/7/10
to jtabl...@googlegroups.com
Thanks again Nicolas! They appear to be working fine, but I must admit "lastEventDeviceState" isn't quite what I was looking for.

I can't seem to find any documentation describing what device_state is supposed to contain, but it isn't a raw button mask. My tablet returns the button mask, but shifted left by 8 bits. My mouse (I removed the filter from Device.c) returns 0 regardless of buttons pressed. Though two datapoints is a mere droplet of information, it looks to me like drivers are free to place any state information they want (in any order) into device_state.

While hijacking lastEventButton in my patch was a bit of a hack, the variable is useless right now. If a user taps a button, lastEventButton changes for the press but not for the release. I see three ways of providing useful data:

1. Track the button mask internally. Whenever a button is pressed or released, XOR the appropriate bit. This is what button.patch did.

2. Provide lastEventType data. If a client sees that there is a button press or release event, it can update its own button mask via lastEventButton.

3. Clear lastEventButton for non-button events. If a client sees that lastEventButton != 0, it knows that it needs to update its own button mask.

I prefer the first solution since it doesn't make much sense to force every client to write identical code to update their own button mask. However, given how closely you maintain the representation of the XInput device and event objects, the latter solutions may be a better fit for the project.

Jason

Jason Gerecke

unread,
May 7, 2010, 6:50:09 PM5/7/10
to jtabl...@googlegroups.com
I'd defiantly like to go over some of the questions I have (and make a few suggestions as well), but they can go into another thread and can wait for the alpha.

I'll post up an alpha release as soon as I get some packages built. Right now they won't have mouse support, but tablets (its all that really matters afterall :D) should be working correctly.

Jason

Nicolas Carranza

unread,
May 11, 2010, 2:10:17 PM5/11/10
to jtabl...@googlegroups.com, Jason Gerecke
Hey Jason,

> I can't seem to find any documentation describing what device_state is
> supposed to contain, but it isn't a raw button mask. My tablet returns the
> button mask, but shifted left by 8 bits. My mouse (I removed the filter
> from Device.c) returns 0 regardless of buttons pressed. Though two
> datapoints is a mere droplet of information, it looks to me like drivers
> are free to place any state information they want (in any order) into
> device_state.
>
> While hijacking lastEventButton in my patch was a bit of a hack, the
> variable is useless right now. If a user taps a button, lastEventButton
> changes for the press but not for the release. I see three ways of
> providing useful data:
>
> 1. Track the button mask internally. Whenever a button is pressed or
> released, XOR the appropriate bit. This is what button.patch did.

I thought that device_state (lastEventDeviceState) could be used directly (and
in place of the hacked lastEventButton) because the proximity.patch did:
+ pDevice->lastEventButton=pEvent->device_state;
on ProximityIn/ProximityOut. But with your findings I think that device_state
is unusable and we better remove it.

>
> 2. Provide lastEventType data. If a client sees that there is a button
> press or release event, it can update its own button mask via
> lastEventButton.
>
> 3. Clear lastEventButton for non-button events. If a client sees that
> lastEventButton != 0, it knows that it needs to update its own button mask.

The lastEventType data is already accessible :-) You can use the
XiDevice.getLastEventType() to know if the event was a button press or
release (XiDevice.EventType.BUTTON_PRESS or BUTTON_RELEASE) and modify a
button mask accordingly.

>
> I prefer the first solution since it doesn't make much sense to force every
> client to write identical code to update their own button mask. However,
> given how closely you maintain the representation of the XInput device and
> event objects, the latter solutions may be a better fit for the project.

We are already on solution 2. Let me know if it is giving you the desired
functionality. I guess it is better to let the client handle the button mask
(in this case the clients are only the jtablet/jpen internal machinery)
because the button states will depend on when the client starts/stops
listening to button events (as device_state is useless and I don't know
another way to initialize the button mask with the real values at any given
time). My 2 cents... on jpen I found too troublesome to handle the buttons
through xinput when almost all client use-cases are well served by taking the
button info from the java awt mouse (and keyboard probably on a next
version).

Cheers!
Nicolas
Reply all
Reply to author
Forward
0 new messages