();
-
- public static String toString(int mode) {
- String name = mNames.get(mode);
- return name != null ? name : "unknown mode";
- }
-
- private static void initialize() {
- mNames.put(AsyncPointer, "AsyncPointer");
- mNames.put(SyncPointer, "SyncPointer");
- mNames.put(ReplayPointer, "ReplayPointer");
- mNames.put(AsyncKeyboard, "AsyncKeyboard");
- mNames.put(SyncKeyboard, "SyncKeyboard");
- mNames.put(ReplayKeyboard, "ReplayKeyboard");
- mNames.put(AsyncBoth, "AsyncBoth");
- mNames.put(SyncBoth, "SyncBoth");
- }
- }
-
- public static final byte CreateWindow = 1;
- public static final byte ChangeWindowAttributes = 2;
- public static final byte GetWindowAttributes = 3;
- public static final byte DestroyWindow = 4;
- public static final byte DestroySubwindows = 5;
- public static final byte ChangeSaveSet = 6;
- public static final byte ReparentWindow = 7;
- public static final byte MapWindow = 8;
- public static final byte MapSubwindows = 9;
- public static final byte UnmapWindow = 10;
- public static final byte UnmapSubwindows = 11;
- public static final byte ConfigureWindow = 12;
- public static final byte CirculateWindow = 13;
- public static final byte GetGeometry = 14;
- public static final byte QueryTree = 15;
- public static final byte InternAtom = 16;
- public static final byte GetAtomName = 17;
- public static final byte ChangeProperty = 18;
- public static final byte DeleteProperty = 19;
- public static final byte GetProperty = 20;
- public static final byte ListProperties = 21;
- public static final byte SetSelectionOwner = 22;
- public static final byte GetSelectionOwner = 23;
- public static final byte ConvertSelection = 24;
- public static final byte SendEvent = 25;
- public static final byte GrabPointer = 26;
- public static final byte UngrabPointer = 27;
- public static final byte GrabButton = 28;
- public static final byte UngrabButton = 29;
- public static final byte ChangeActivePointerGrab = 30;
- public static final byte GrabKeyboard = 31;
- public static final byte UngrabKeyboard = 32;
- public static final byte GrabKey = 33;
- public static final byte UngrabKey = 34;
- public static final byte AllowEvents = 35;
- public static final byte GrabServer = 36;
- public static final byte UngrabServer = 37;
- public static final byte QueryPointer = 38;
- public static final byte GetMotionEvents = 39;
- public static final byte TranslateCoordinates = 40;
- public static final byte WarpPointer = 41;
- public static final byte SetInputFocus = 42;
- public static final byte GetInputFocus = 43;
- public static final byte QueryKeymap = 44;
- public static final byte OpenFont = 45;
- public static final byte CloseFont = 46;
- public static final byte QueryFont = 47;
- public static final byte QueryTextExtents = 48;
- public static final byte ListFonts = 49;
- public static final byte ListFontsWithInfo = 50;
- public static final byte SetFontPath = 51;
- public static final byte GetFontPath = 52;
- public static final byte CreatePixmap = 53;
- public static final byte FreePixmap = 54;
- public static final byte CreateGC = 55;
- public static final byte ChangeGC = 56;
- public static final byte CopyGC = 57;
- public static final byte SetDashes = 58;
- public static final byte SetClipRectangles = 59;
- public static final byte FreeGC = 60;
- public static final byte ClearArea = 61;
- public static final byte CopyArea = 62;
- public static final byte CopyPlane = 63;
- public static final byte PolyPoint = 64;
- public static final byte PolyLine = 65;
- public static final byte PolySegment = 66;
- public static final byte PolyRectangle = 67;
- public static final byte PolyArc = 68;
- public static final byte FillPoly = 69;
- public static final byte PolyFillRectangle = 70;
- public static final byte PolyFillArc = 71;
- public static final byte PutImage = 72;
- public static final byte GetImage = 73;
- public static final byte PolyText8 = 74;
- public static final byte PolyText16 = 75;
- public static final byte ImageText8 = 76;
- public static final byte ImageText16 = 77;
- public static final byte CreateColormap = 78;
- public static final byte FreeColormap = 79;
- public static final byte CopyColormapAndFree = 80;
- public static final byte InstallColormap = 81;
- public static final byte UninstallColormap = 82;
- public static final byte ListInstalledColormaps = 83;
- public static final byte AllocColor = 84;
- public static final byte AllocNamedColor = 85;
- public static final byte AllocColorCells = 86;
- public static final byte AllocColorPlanes = 87;
- public static final byte FreeColors = 88;
- public static final byte StoreColors = 89;
- public static final byte StoreNamedColor = 90;
- public static final byte QueryColors = 91;
- public static final byte LookupColor = 92;
- public static final byte CreateCursor = 93;
- public static final byte CreateGlyphCursor = 94;
- public static final byte FreeCursor = 95;
- public static final byte RecolorCursor = 96;
- public static final byte QueryBestSize = 97;
- public static final byte QueryExtension = 98;
- public static final byte ListExtensions = 99;
- public static final byte ChangeKeyboardMapping = 100;
- public static final byte GetKeyboardMapping = 101;
- public static final byte ChangeKeyboardControl = 102;
- public static final byte GetKeyboardControl = 103;
- public static final byte Bell = 104;
- public static final byte ChangePointerControl = 105;
- public static final byte GetPointerControl = 106;
- public static final byte SetScreenSaver = 107;
- public static final byte GetScreenSaver = 108;
- public static final byte ChangeHosts = 109;
- public static final byte ListHosts = 110;
- public static final byte SetAccessControl = 111;
- public static final byte SetCloseDownMode = 112;
- public static final byte KillClient = 113;
- public static final byte RotateProperties = 114;
- public static final byte ForceScreenSaver = 115;
- public static final byte SetPointerMapping = 116;
- public static final byte GetPointerMapping = 117;
- public static final byte SetModifierMapping = 118;
- public static final byte GetModifierMapping = 119;
- public static final byte NoOperation = 127;
- public static final byte ExtensionStart = -128;
- public static final byte ExtensionEnd = -1;
-
- static {
- AllowEventsMode.initialize();
- }
-}
diff --git a/library/src/main/java/au/com/darkside/xserver/Resource.java b/library/src/main/java/au/com/darkside/xserver/Resource.java
deleted file mode 100644
index ae9614c..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Resource.java
+++ /dev/null
@@ -1,123 +0,0 @@
-package au.com.darkside.xserver;
-
-import java.io.IOException;
-
-/**
- * This class handles details of a server resource.
- *
- * @author Matthew Kwan
- */
-public class Resource {
- public static final int WINDOW = 1;
- public static final int PIXMAP = 2;
- public static final int CURSOR = 3;
- public static final int FONT = 4;
- public static final int GCONTEXT = 5;
- public static final int COLORMAP = 6;
-
- private final int _type;
- protected final int _id;
- protected final XServer _xServer;
- protected Client _client;
- private int _closeDownMode = Client.Destroy;
-
- /**
- * Constructor.
- *
- * @param type The resource type.
- * @param id The resource ID.
- * @param xServer The X server.
- * @param client The client issuing the request.
- */
- protected Resource(int type, int id, XServer xServer, Client client) {
- _type = type;
- _id = id;
- _xServer = xServer;
- _client = client;
- }
-
- /**
- * Return the resource type.
- *
- * @return The resource type.
- */
- public int getType() {
- return _type;
- }
-
- /**
- * Return the resource ID.
- *
- * @return The resource ID.
- */
- public int getId() {
- return _id;
- }
-
- /**
- * Return the client that created the resource.
- *
- * @return The client that created the resource.
- */
- public Client getClient() {
- return _client;
- }
-
- /**
- * Return the resource's close down mode.
- *
- * @return The resource's close down mode.
- */
- public int getCloseDownMode() {
- return _closeDownMode;
- }
-
- /**
- * Set the close down mode of the resource.
- *
- * @param mode The mode used to destroy the resource.
- */
- public void setCloseDownMode(int mode) {
- _closeDownMode = mode;
- }
-
- /**
- * Is the resource a drawable? (Window or Pixmap)
- *
- * @return Whether the resource is a drawable.
- */
- public boolean isDrawable() {
- return (_type == WINDOW || _type == PIXMAP);
- }
-
- /**
- * Is the resource a fontable? (Font or GContext)
- *
- * @return Whether the resource is a fontable.
- */
- public boolean isFontable() {
- return (_type == FONT || _type == GCONTEXT);
- }
-
- /**
- * Destroy the resource.
- * Remove it from the X server's resources, and override this function
- * to handle object-specific removals.
- */
- public void delete() {
- _xServer.freeResource(_id);
- }
-
- /**
- * Process an X request relating to this resource.
- * This is a fallback function that does nothing.
- *
- * @param client The remote client.
- * @param opcode The request's opcode.
- * @param arg Optional first argument.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public void processRequest(Client client, byte opcode, byte arg, int bytesRemaining) throws IOException {
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/ScreenView.java b/library/src/main/java/au/com/darkside/xserver/ScreenView.java
deleted file mode 100644
index 423462a..0000000
--- a/library/src/main/java/au/com/darkside/xserver/ScreenView.java
+++ /dev/null
@@ -1,1834 +0,0 @@
-package au.com.darkside.xserver;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.view.KeyEvent;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ActionMode;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.inputmethod.InputConnection;
-import android.view.inputmethod.EditorInfo;
-import android.text.InputType;
-import android.os.Build;
-import android.content.ClipboardManager;
-import android.content.ClipData;
-import android.app.Instrumentation;
-import android.os.Looper;
-import android.os.Handler;
-import android.view.inputmethod.InputMethodManager;
-import android.app.Service;
-
-import java.io.IOException;
-import java.util.LinkedList;
-import java.util.Queue;
-import java.util.Vector;
-import java.nio.charset.StandardCharsets;
-import java.lang.Math;
-
-/**
- * This class implements an X Windows screen.
- *
- * It also implements the screen's root window.
- *
- *
- * @author Matthew Kwan
- */
-public class ScreenView extends View {
-
- private interface PendingEvent {
- public void run();
- }
-
- private interface PendingPointerEvent extends PendingEvent {
- }
-
- private class PendingGrabButtonNotify implements PendingPointerEvent {
-
- private Window mWindow;
- private boolean mPressed;
- private int mMotionX;
- private int mMotionY;
- private int mButton;
- private int mGrabEventMask;
- private Client mGrabPointerClient;
- private boolean mGrabPointerOwnerEvents;
-
- public PendingGrabButtonNotify(Window w, boolean pressed, int motionX, int motionY, int button, int grabEventMask, Client grabPointerClient, boolean grabPointerOwnerEvents) {
- mWindow = w;
- mPressed = pressed;
- mMotionX = motionX;
- mMotionY = motionY;
- mButton = button;
- mGrabEventMask = grabEventMask;
- mGrabPointerClient = grabPointerClient;
- mGrabPointerOwnerEvents = grabPointerOwnerEvents;
- }
-
- public void run() {
- callGrabButtonNotify(mWindow, mPressed, mMotionX, mMotionY, mButton, mGrabEventMask, mGrabPointerClient, mGrabPointerOwnerEvents);
- }
- }
-
- private class PendingGrabMotionNotify implements PendingPointerEvent {
-
- private Window mWindow;
- private int mX;
- private int mY;
- private int mButtons;
- private int mGrabEventMask;
- private Client mGrabPointerClient;
- private boolean mGrabPointerOwnerEvents;
-
- public PendingGrabMotionNotify(Window w, int x, int y, int buttons, int grabEventMask, Client grabPointerClient, boolean grabPointerOwnerEvents) {
- mWindow = w;
- mX = x;
- mY = y;
- mButtons = buttons;
- mGrabEventMask = grabEventMask;
- mGrabPointerClient = grabPointerClient;
- mGrabPointerOwnerEvents = grabPointerOwnerEvents;
- }
-
- public void run() {
- callGrabMotionNotify(mWindow, mX, mY, mButtons, mGrabEventMask, mGrabPointerClient, mGrabPointerOwnerEvents);
- }
- }
-
- private interface PendingKeyboardEvent extends PendingEvent {
- }
-
- private class PendingGrabKeyNotify implements PendingKeyboardEvent {
-
- private Window mWindow;
- private boolean mPressed;
- private int mMotionX;
- private int mMotionY;
- private int mKeycode;
- private Client mGrabKeyboardClient;
- private boolean mGrabKeyboardOwnerEvents;
-
- public PendingGrabKeyNotify(Window w, boolean pressed, int motionX, int motionY, int keycode, Client grabKeyboardClient, boolean grabKeyboardOwnerEvents) {
- mWindow = w;
- mPressed = pressed;
- mMotionX = motionX;
- mMotionY = motionY;
- mKeycode = keycode;
- mGrabKeyboardClient = grabKeyboardClient;
- mGrabKeyboardOwnerEvents = grabKeyboardOwnerEvents;
- }
-
- public void run() {
- callGrabKeyNotify(mWindow, mPressed, mMotionX, mMotionY, mKeycode, mGrabKeyboardClient, mGrabKeyboardOwnerEvents);
- }
- }
-
- private static class PendingEventQueue {
-
- private Queue mQueue = new LinkedList();
-
- public void add(T event) {
- if (mQueue.offer(event)) {
- return;
- }
- }
-
- public T next() {
- return mQueue.poll();
- }
- }
-
- private final XServer _xServer;
- private final int _rootId;
- private Window _rootWindow = null;
- private Window _sharedClipboardWindow = null;
- private Property _sharedClipboardProperty = null;
- private Property _sharedClipboardPrimaryProperty = null;
- private Colormap _defaultColormap = null;
- private final Vector _installedColormaps;
- private final float _pixelsPerMillimeter;
-
- private Cursor _currentCursor;
- private int _currentCursorX;
- private int _currentCursorY;
- private Cursor _drawnCursor = null;
- private int _drawnCursorX;
- private int _drawnCursorY;
- private Window _motionWindow = null;
- private int _motionX;
- private int _motionY;
- private int _buttons = 0;
- private boolean _isBlanked = false;
- private boolean _arrowsAsButtons = false;
- private boolean _inhibitBackButton = false;
- private boolean _enableTouchClicks = true;
- private boolean _sharedClipboard = true;
- private Paint _paint;
-
- private Client _grabPointerClient = null;
- private Window _grabPointerWindow = null;
- private int _grabPointerTime = 0;
- private boolean _grabPointerOwnerEvents = false;
- private boolean _grabPointerSynchronous = false;
- private boolean _grabPointerPassive = false;
- private boolean _grabPointerAutomatic = false;
- private boolean _grabPointerFreezeNextEvent = false;
- private Client _grabKeyboardClient = null;
- private Window _grabKeyboardWindow = null;
- private int _grabKeyboardTime = 0;
- private boolean _grabKeyboardOwnerEvents = false;
- private boolean _grabKeyboardSynchronous = false;
- private boolean _grabKeyboardFreezeNextEvent = false;
- private Cursor _grabCursor = null;
- private Window _grabConfineWindow = null;
- private int _grabEventMask = 0;
- private PassiveKeyGrab _grabKeyboardPassiveGrab = null;
-
- private Window _focusWindow = null;
- private byte _focusRevertTo = 0; // 0=None, 1=Root, 2=Parent.
- private int _focusLastChangeTime = 0;
-
- private PendingEventQueue mPendingPointerEvents;
- private PendingEventQueue mPendingKeyboardEvents;
-
- private boolean _ignoreLongPress = false;
-
- private static final int ACTION_CANCEL = 0;
- private static final int ACTION_CTRL_C = 1;
- private static final int ACTION_CTRL_V = 2;
- private static final int ACTION_CTRL_X = 3;
- private static final int ACTION_CTRL_A = 4;
- private static final int ACTION_R_CLICK = 5;
- private static final int ACTION_M_CLICK = 6;
- private static final int ACTION_ESC = 7;
- private static final int ACTION_KEYBOARD = 8;
-
- // -- helpers for movement thresholding, works around phones with cheap touch screens
- private double _totalMove = 0;
- private double _xPrec = 0;
- private double _yPrec = 0;
-
- /**
- * Constructor.
- *
- * @param c The application context.
- * @param xServer The X server.
- * @param rootId The ID of the root window, to be created later.
- * @param pixelsPerMillimeter Screen resolution.
- */
- public ScreenView(Context c, XServer xServer, int rootId, float pixelsPerMillimeter) {
- super(c);
-
- setFocusable(true);
- setFocusableInTouchMode(true);
-
- _xServer = xServer;
- _rootId = rootId;
- _installedColormaps = new Vector();
- _pixelsPerMillimeter = pixelsPerMillimeter;
- _paint = new Paint();
-
- mPendingPointerEvents = new PendingEventQueue();
- mPendingKeyboardEvents = new PendingEventQueue();
-
- // ---- Listeners for touch input ----
- setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- // do nothing
- }
- });
-
- setOnTouchListener(new View.OnTouchListener() {
- @Override
- public boolean onTouch(View v, MotionEvent event) {
- synchronized (_xServer) {
- if (_rootWindow == null) return false;
-
- blank(false); // Reset the screen saver.
- updatePointerPosition((int) event.getX(), (int) event.getY(), 0);
-
- if(_enableTouchClicks){
- if(event.getActionMasked() == MotionEvent.ACTION_DOWN && event.getActionIndex() == 0)
- updatePointerButtons (1, true);
- if(event.getActionMasked() == MotionEvent.ACTION_UP && event.getActionIndex() == 0)
- updatePointerButtons (1, false);
- if(event.getActionMasked() == MotionEvent.ACTION_POINTER_DOWN && event.getActionIndex() == 1)
- updatePointerButtons (3, true);
- if((event.getActionMasked() == MotionEvent.ACTION_POINTER_UP || event.getActionMasked() == MotionEvent.ACTION_CANCEL) && event.getActionIndex() == 1)
- updatePointerButtons (3, false);
- }
- }
-
- if(event.getActionMasked() == MotionEvent.ACTION_DOWN){
- _totalMove = 0;
- _xPrec = event.getX();
- _yPrec = event.getY();
- }
- else if (event.getActionMasked() == MotionEvent.ACTION_MOVE){
- final double dx = event.getX() - _xPrec;
- final double dy = event.getY() - _yPrec;
- final double dl = Math.sqrt(dx * dx + dy * dy);
- _totalMove += dl;
- _xPrec = event.getX();
- _yPrec = event.getY();
- }
-
-
- if(_totalMove < 20){ // -- workaround for phones with cheap touchscreens (which will constantly trigger ACTION_MOVE events)
- _ignoreLongPress = false;
- return false; // make longClick Listeners work!
- }
-
- _ignoreLongPress = true;
- return true;
- }
- });
-
- setOnLongClickListener(new View.OnLongClickListener() {
- @Override
- public boolean onLongClick(View v) {
- if(_ignoreLongPress)
- return true;
-
- ActionMode.Callback cb = new ActionMode.Callback(){
- @Override
- public boolean onCreateActionMode(ActionMode mode, Menu menu) {
- menu.add(0, ACTION_CTRL_C, 0, "CTRL+C");
- menu.add(0, ACTION_CTRL_V, 0, "CTRL+V");
- menu.add(0, ACTION_CTRL_X, 0, "CTRL+X");
- menu.add(0, ACTION_CTRL_A, 0, "CTRL+A");
- menu.add(0, ACTION_ESC, 0, "ESC");
- menu.add(0, ACTION_R_CLICK, 0, "M-Click");
- menu.add(0, ACTION_R_CLICK, 0, "R-Click");
- menu.add(0, ACTION_KEYBOARD, 0, "Keyboard");
- menu.add(0, ACTION_CANCEL, 0, "Cancel");
- return true;
- }
-
- @Override
- public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
- return false; // Return false if nothing is done
- }
-
- @Override
- public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
- switch (item.getItemId()) {
- case ACTION_CTRL_C:
- onKeyDown(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_CTRL_LEFT));
- onKeyDown(KeyEvent.KEYCODE_C, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_C));
- onKeyUp(KeyEvent.KEYCODE_C, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_C));
- onKeyUp(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_CTRL_LEFT));
- mode.finish();
- return true;
- case ACTION_CTRL_V:
- if (_sharedClipboard) {
- Selection.setSelectionOwner(_xServer, _xServer.findAtom("CLIPBOARD"), _sharedClipboardWindow); // override owner to point to our clipboardwindow
- Selection.setSelectionOwner(_xServer, _xServer.findAtom("PRIMARY"), _sharedClipboardWindow);
- ClipboardManager clipboard = (ClipboardManager) _xServer.getContext().getSystemService(Context.CLIPBOARD_SERVICE);
- ClipData.Item clipitem = clipboard.getPrimaryClip().getItemAt(0);
-
- _sharedClipboardProperty.setData(clipitem.getText().toString());
- _sharedClipboardPrimaryProperty.setData(clipitem.getText().toString());
- }
-
- onKeyDown(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_CTRL_LEFT));
- onKeyDown(KeyEvent.KEYCODE_V, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_V));
- onKeyUp(KeyEvent.KEYCODE_V, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_V));
- onKeyUp(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_CTRL_LEFT));
- mode.finish();
- return true;
- case ACTION_CTRL_X:
- onKeyDown(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_CTRL_LEFT));
- onKeyDown(KeyEvent.KEYCODE_X, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_X));
- onKeyUp(KeyEvent.KEYCODE_X, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_X));
- onKeyUp(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_CTRL_LEFT));
- mode.finish();
- return true;
- case ACTION_CTRL_A:
- onKeyDown(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_CTRL_LEFT));
- onKeyDown(KeyEvent.KEYCODE_A, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_A));
- onKeyUp(KeyEvent.KEYCODE_A, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_A));
- onKeyUp(KeyEvent.KEYCODE_CTRL_LEFT, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_CTRL_LEFT));
- mode.finish();
- return true;
- case ACTION_R_CLICK:
- if (_sharedClipboard) {
- Selection.setSelectionOwner(_xServer, _xServer.findAtom("CLIPBOARD"), _sharedClipboardWindow); // override owner to point to our clipboardwindow
- Selection.setSelectionOwner(_xServer, _xServer.findAtom("PRIMARY"), _sharedClipboardWindow);
- ClipboardManager clipboard = (ClipboardManager) _xServer.getContext().getSystemService(Context.CLIPBOARD_SERVICE);
- ClipData.Item clipitem = clipboard.getPrimaryClip().getItemAt(0);
-
- _sharedClipboardProperty.setData(clipitem.getText().toString());
- _sharedClipboardPrimaryProperty.setData(clipitem.getText().toString());
- }
- updatePointerButtons(3, true);
- updatePointerButtons(3, false);
- mode.finish();
- return true;
- case ACTION_M_CLICK:
- if (_sharedClipboard) {
- Selection.setSelectionOwner(_xServer, _xServer.findAtom("CLIPBOARD"), _sharedClipboardWindow); // override owner to point to our clipboardwindow
- Selection.setSelectionOwner(_xServer, _xServer.findAtom("PRIMARY"), _sharedClipboardWindow);
- ClipboardManager clipboard = (ClipboardManager) _xServer.getContext().getSystemService(Context.CLIPBOARD_SERVICE);
- ClipData.Item clipitem = clipboard.getPrimaryClip().getItemAt(0);
-
- _sharedClipboardProperty.setData(clipitem.getText().toString());
- _sharedClipboardPrimaryProperty.setData(clipitem.getText().toString());
- }
- updatePointerButtons(2, true);
- updatePointerButtons(2, false);
- mode.finish();
- return true;
- case ACTION_ESC:
- onKeyDown(KeyEvent.KEYCODE_ESCAPE, new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_ESCAPE));
- onKeyUp(KeyEvent.KEYCODE_ESCAPE, new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_ESCAPE));
- mode.finish();
- return true;
- case ACTION_KEYBOARD:
- InputMethodManager imm = (InputMethodManager) _xServer.getContext().getSystemService(Service.INPUT_METHOD_SERVICE);
- requestFocus();
- imm.hideSoftInputFromWindow(getWindowToken(), 0);
- imm.toggleSoftInput(InputMethodManager.SHOW_FORCED, 0);
- mode.finish();
- return true;
- case ACTION_CANCEL:
- mode.finish();
- return true;
- default:
- mode.finish();
- return false;
- }
- }
-
- // Called when the user exits the action mode
- @Override
- public void onDestroyActionMode(ActionMode mode) {
- mode = null;
- }
- };
-
- // use floating mode on newer android versions
- if(Build.VERSION.SDK_INT >= 23){
- startActionMode(cb, ActionMode.TYPE_FLOATING);
- }
- else{
- startActionMode(cb);
- }
-
- return false;
- }
- });
- requestFocus();
- }
-
- /**
- * needed make softkeyboard work in landscape mode and to capture backspace.
- */
- @Override
- public InputConnection onCreateInputConnection(EditorInfo outAttrs){
- outAttrs.inputType = InputType.TYPE_TEXT_VARIATION_NORMAL;
- outAttrs.imeOptions = EditorInfo.IME_ACTION_NONE | EditorInfo.IME_FLAG_NO_FULLSCREEN;
- return null;
- }
-
-
- /**
- * Placeholder constructor to prevent a compiler warning.
- *
- * @param c
- */
- public ScreenView(Context c) {
- super(c);
-
- _xServer = null;
- _rootId = 0;
- _installedColormaps = null;
- _pixelsPerMillimeter = 0;
- }
-
- /**
- * Return the screen's root window.
- *
- * @return The screen's root window.
- */
- public Window getRootWindow() {
- return _rootWindow;
- }
-
- /**
- * Return the screen's default colormap.
- *
- * @return The screen's default colormap.
- */
- public Colormap getDefaultColormap() {
- return _defaultColormap;
- }
-
- /**
- * Return the current cursor.
- *
- * @return The current cursor.
- */
- public Cursor getCurrentCursor() {
- return _currentCursor;
- }
-
- /**
- * Return the current pointer X coordinate.
- *
- * @return The current pointer X coordinate.
- */
- public int getPointerX() {
- return _currentCursorX;
- }
-
- /**
- * Return the current pointer Y coordinate.
- *
- * @return The current pointer Y coordinate.
- */
- public int getPointerY() {
- return _currentCursorY;
- }
-
- /**
- * Return a mask indicating the current state of the pointer and
- * modifier buttons.
- *
- * @return A mask indicating the current state of the buttons.
- */
- public int getButtons() {
- return _buttons;
- }
-
- /**
- * Return the window that has input focus. Can be null.
- *
- * @return The window that has input focus.
- */
- public Window getFocusWindow() {
- return _focusWindow;
- }
-
- /**
- * Blank/unblank the screen.
- *
- * @param flag If true, blank the screen. Otherwise unblank it.
- */
- public void blank(boolean flag) {
- if (_isBlanked == flag) return;
-
- _isBlanked = flag;
- postInvalidate();
-
- if (!_isBlanked) _xServer.resetScreenSaver();
- }
-
- /**
- * Add an installed colormap.
- *
- * @param cmap The colormap to add.
- */
- public void addInstalledColormap(Colormap cmap) {
- _installedColormaps.add(cmap);
- if (_defaultColormap == null) _defaultColormap = cmap;
- }
-
- /**
- * Remove an installed colormap.
- *
- * @param cmap The colormap to remove.
- */
- public void removeInstalledColormap(Colormap cmap) {
- _installedColormaps.remove(cmap);
- if (_defaultColormap == cmap) {
- if (_installedColormaps.size() == 0) _defaultColormap = null;
- else _defaultColormap = _installedColormaps.firstElement();
- }
- }
-
- /**
- * Remove all colormaps except the default one.
- */
- public void removeNonDefaultColormaps() {
- if (_installedColormaps.size() < 2) return;
-
- _installedColormaps.clear();
- if (_defaultColormap != null) _installedColormaps.add(_defaultColormap);
- }
-
- /**
- * Called when a window is deleted, usually due to a client disconnecting.
- * Removes all references to the window.
- *
- * @param w The window being deleted.
- */
- public void deleteWindow(Window w) {
- if (_grabPointerWindow == w || _grabConfineWindow == w) {
- _grabPointerClient = null;
- _grabPointerWindow = null;
- _grabCursor = null;
- _grabConfineWindow = null;
- updatePointer(2);
- } else {
- updatePointer(0);
- }
-
- revertFocus(w);
- }
-
- /**
- * Called when the window is unmapped.
- * If the window had keyboard focus, update the focus window.
- *
- * @param w
- */
- public void revertFocus(Window w) {
- if (w == _grabKeyboardWindow) {
- Window pw = _rootWindow.windowAtPoint(_motionX, _motionY);
-
- Window.focusInOutNotify(_grabKeyboardWindow, _focusWindow, pw, _rootWindow, 2);
- _grabKeyboardClient = null;
- _grabKeyboardWindow = null;
- }
-
- if (w == _focusWindow) {
- Window pw = _rootWindow.windowAtPoint(_motionX, _motionY);
-
- if (_focusRevertTo == 0) {
- _focusWindow = null;
- } else if (_focusRevertTo == 1) {
- _focusWindow = _rootWindow;
- } else {
- _focusWindow = w.getParent();
- while (!_focusWindow.isViewable()) _focusWindow = _focusWindow.getParent();
- }
-
- _focusRevertTo = 0;
- Window.focusInOutNotify(w, _focusWindow, pw, _rootWindow, _grabKeyboardWindow == null ? 0 : 3);
- }
- }
-
- /**
- * Called when the view needs drawing.
- *
- * @param canvas The canvas on which the view will be drawn.
- */
- @Override
- protected void onDraw(Canvas canvas) {
- if (_rootWindow == null) {
- super.onDraw(canvas);
- return;
- }
-
- synchronized (_xServer) {
- if (_isBlanked) {
- canvas.drawColor(0xff000000);
- return;
- }
-
- _paint.reset();
- _rootWindow.draw(canvas, _paint);
- canvas.drawBitmap(_currentCursor.getBitmap(), _currentCursorX - _currentCursor.getHotspotX(), _currentCursorY - _currentCursor.getHotspotY(), null);
-
- _drawnCursor = _currentCursor;
- _drawnCursorX = _currentCursorX;
- _drawnCursorY = _currentCursorY;
- }
- }
-
- /**
- * Called when the size changes.
- * Create the root window.
- *
- * @param width The new width.
- * @param height The new height.
- * @param oldWidth The old width.
- * @param oldHeight The old height.
- */
- @Override
- protected void onSizeChanged(int width, int height, int oldWidth, int oldHeight) {
- super.onSizeChanged(width, height, oldWidth, oldHeight);
-
- _rootWindow = new Window(_rootId, _xServer, null, this, null, 0, 0, width, height, 0, false, true);
- _sharedClipboardWindow = new Window(_xServer.nextFreeResourceId()+1, _xServer, null, this, _rootWindow, -1, -1, 1, 1, 0, true, false); // hidden window managing android <-> xServer clipboard
- _sharedClipboardWindow.setIsServerWindow(true); // flag as functional server only window (there is a urgent need to introduce interfaces..)
- _sharedClipboardProperty = new Property(_xServer.findAtom("CLIPBOARD").getId(), _xServer.findAtom("CLIPBOARD").getId(), (byte)32); // property which will hold the clipboard data
- _sharedClipboardPrimaryProperty = new Property(_xServer.findAtom("PRIMARY").getId(), _xServer.findAtom("PRIMARY").getId(), (byte)32); // property which will hold the clipboard data
-
- Property.OnPropertyChangedListener cb = new Property.OnPropertyChangedListener(){ // -- executed on a per client thread basis
- @Override
- public void onPropertyChanged(byte[] data, Atom type){
- switch(type.getName()){
- case "UTF8_STRING":
- String s = new String(data, StandardCharsets.UTF_8); // convert to UTF8 string
-
- // create task for UI thread
- class OneShotTask implements Runnable {
- private String d;
- OneShotTask(String s) { d = s; }
- public void run() {
- ClipboardManager clipboard = (ClipboardManager) _xServer.getContext().getSystemService(Context.CLIPBOARD_SERVICE);
- ClipData clip = ClipData.newPlainText("cb", d);
- clipboard.setPrimaryClip(clip); // store to clipboard
- }
- }
- new Handler(Looper.getMainLooper()).post(new OneShotTask(s));
- break;
- default: // different types can be implemented here (binary etc.)
- break;
- }
- }
- };
-
-
- // capture data changes on this property
- _sharedClipboardProperty.setOnPropertyChangedListener(cb);
- _sharedClipboardPrimaryProperty.setOnPropertyChangedListener(cb);
-
- _sharedClipboardWindow.addProperty(_sharedClipboardPrimaryProperty);
- _sharedClipboardWindow.addProperty(_sharedClipboardProperty);
-
- _xServer.addResource(_rootWindow);
- _xServer.addResource(_sharedClipboardWindow);
-
- _currentCursor = _rootWindow.getCursor();
- _currentCursorX = width / 2;
- _currentCursorY = height / 2;
- _drawnCursorX = _currentCursorX;
- _drawnCursorY = _currentCursorY;
- _motionX = _currentCursorX;
- _motionY = _currentCursorY;
- _motionWindow = _rootWindow;
- _focusWindow = _rootWindow;
-
- // Everything set up, so start listening for clients.
- _xServer.start();
- }
-
- /**
- * Move the pointer on the screen.
- *
- * @param x New X coordinate.
- * @param y New Y coordinate.
- * @param cursor The cursor to draw.
- */
- private void movePointer(int x, int y, Cursor cursor) {
- if (_drawnCursor != null) {
- int left = _drawnCursorX - _drawnCursor.getHotspotX();
- int top = _drawnCursorY - _drawnCursor.getHotspotY();
- Bitmap bm = _drawnCursor.getBitmap();
-
- postInvalidate(left, top, left + bm.getWidth(), top + bm.getHeight());
- _drawnCursor = null;
- }
-
- _currentCursor = cursor;
- _currentCursorX = x;
- _currentCursorY = y;
-
- int left = x - cursor.getHotspotX();
- int top = y - cursor.getHotspotY();
- Bitmap bm = cursor.getBitmap();
-
- postInvalidate(left, top, left + bm.getWidth(), top + bm.getHeight());
- }
-
- /**
- * Update the location of the pointer.
- *
- * @param x New X coordinate.
- * @param y New Y coordinate.
- * @param mode 0=Normal, 1=Grab, 2=Ungrab
- */
- public void updatePointerPosition(int x, int y, int mode) {
- Window w;
- Cursor c;
-
- if (_grabConfineWindow != null) {
- Rect rect = _grabConfineWindow.getIRect();
-
- if (x < rect.left) x = rect.left;
- else if (x >= rect.right) x = rect.right - 1;
-
- if (y < rect.top) y = rect.top;
- else if (y >= rect.bottom) y = rect.bottom - 1;
- }
-
- if (_grabPointerWindow != null) w = _grabPointerWindow;
- else w = _rootWindow.windowAtPoint(x, y);
-
- if (_grabCursor != null) c = _grabCursor;
- else c = w.getCursor();
-
- if (c != _currentCursor || x != _currentCursorX || y != _currentCursorY)
- movePointer(x, y, c);
-
- if (w != _motionWindow) {
- _motionWindow.leaveEnterNotify(x, y, w, mode);
- _motionWindow = w;
- _motionX = x;
- _motionY = y;
- } else if (x != _motionX || y != _motionY) {
- if (_grabPointerWindow == null) {
- w.motionNotify(x, y, _buttons & 0xff00, null);
- } else if (!_grabPointerSynchronous) {
- callGrabMotionNotify(w, x, y, _buttons, _grabEventMask, _grabPointerClient, _grabPointerOwnerEvents);
- } else {
- PendingPointerEvent e;
- e = new PendingGrabMotionNotify(w, x, y, _buttons, _grabEventMask, _grabPointerClient, _grabPointerOwnerEvents);
- mPendingPointerEvents.add(e);
- }
-
- _motionX = x;
- _motionY = y;
- }
- }
-
- /**
- * Update the pointer in case its glyph has changed.
- *
- * @param mode 0=Normal, 1=Grab, 2=Ungrab
- */
- public void updatePointer(int mode) {
- updatePointerPosition(_currentCursorX, _currentCursorY, mode);
- }
-
- /**
- * Called when a pointer button is pressed/released.
- *
- * @param button The button that was pressed/released.
- * @param pressed True if the button was pressed.
- */
- public void updatePointerButtons(int button, boolean pressed) {
- Pointer p = _xServer.getPointer();
-
- button = p.mapButton(button);
- if (button == 0) return;
-
- int mask = 0x80 << button;
-
- if (pressed) {
- if ((_buttons & mask) != 0) return;
-
- _buttons |= mask;
- } else {
- if ((_buttons & mask) == 0) return;
-
- _buttons &= ~mask;
- }
-
- if (_grabPointerWindow == null) {
- Window w = _rootWindow.windowAtPoint(_motionX, _motionY);
- PassiveButtonGrab pbg = null;
-
- if (pressed) pbg = w.findPassiveButtonGrab(_buttons, null);
-
- if (pbg != null) {
- _grabPointerClient = pbg.getGrabClient();
- _grabPointerWindow = pbg.getGrabWindow();
- _grabPointerPassive = true;
- _grabPointerAutomatic = false;
- _grabPointerTime = _xServer.getTimestamp();
- _grabConfineWindow = pbg.getConfineWindow();
- _grabEventMask = pbg.getEventMask();
- _grabPointerOwnerEvents = pbg.getOwnerEvents();
- _grabPointerSynchronous = pbg.getPointerSynchronous();
- _grabKeyboardSynchronous = pbg.getKeyboardSynchronous();
-
- _grabCursor = pbg.getCursor();
- if (_grabCursor == null) _grabCursor = _grabPointerWindow.getCursor();
-
- updatePointer(1);
- } else {
- int timestamp = _xServer.getTimestamp();
- Window ew = w.buttonNotify(pressed, _motionX, _motionY, button, timestamp, null);
- reflectPointerFreezeNextEvent();
- Client c = null;
-
- if (pressed && ew != null) {
- Vector sc;
-
- sc = ew.getSelectingClients(EventCode.MaskButtonPress);
- if (sc != null) c = sc.firstElement();
- }
-
- // Start an automatic key grab.
- if (c != null) {
- int em = ew.getClientEventMask(c);
-
- _grabPointerClient = c;
- _grabPointerWindow = ew;
- _grabPointerPassive = false;
- _grabPointerAutomatic = true;
- _grabPointerTime = timestamp;
- _grabCursor = ew.getCursor();
- _grabConfineWindow = null;
- _grabEventMask = em & EventCode.MaskAllPointer;
- _grabPointerOwnerEvents = (em & EventCode.MaskOwnerGrabButton) != 0;
- _grabPointerSynchronous = false;
- _grabKeyboardSynchronous = false;
- updatePointer(1);
- }
- }
- } else {
- if (!_grabPointerSynchronous) {
- callGrabButtonNotify(_grabPointerWindow, pressed, _motionX, _motionY, button, _grabEventMask, _grabPointerClient, _grabPointerOwnerEvents);
- } else {
- PendingPointerEvent e;
- e = new PendingGrabButtonNotify(_grabPointerWindow, pressed, _motionX, _motionY, button, _grabEventMask, _grabPointerClient, _grabPointerOwnerEvents);
- mPendingPointerEvents.add(e);
- }
-
- if (_grabPointerAutomatic && !pressed && (_buttons & 0xff00) == 0) {
- _grabPointerClient = null;
- _grabPointerWindow = null;
- _grabCursor = null;
- _grabConfineWindow = null;
- updatePointer(2);
- }
- }
- }
-
- /**
- * Updates keycodes for modifier keys (i.e. shift/alt).
- */
- private void updateModifiers() {
- int mask = 0;
-
- Keyboard kb = _xServer.getKeyboard();
- mask = kb.getState();
-
- _buttons = (_buttons & 0xff00) | mask;
- }
-
- /**
- * Called when a key is pressed or released.
- *
- * @param keycode Keycode of the key.
- * @param pressed True if pressed, false if released.
- */
- public void notifyKeyPressedReleased(int keycode, boolean pressed) {
- if (_grabKeyboardWindow == null && _focusWindow == null) return;
-
- Keyboard kb = _xServer.getKeyboard();
-
- keycode = kb.translateToXKeycode(keycode);
-
- if (pressed && _grabKeyboardWindow == null) {
- PassiveKeyGrab pkg = _focusWindow.findPassiveKeyGrab(keycode, _buttons & 0xff, null);
-
- if (pkg == null) {
- Window w = _rootWindow.windowAtPoint(_motionX, _motionY);
-
- if (w.isAncestor(_focusWindow))
- pkg = w.findPassiveKeyGrab(keycode, _buttons & 0xff, null);
- }
-
- if (pkg != null) {
- _grabKeyboardPassiveGrab = pkg;
- _grabKeyboardClient = pkg.getGrabClient();
- _grabKeyboardWindow = pkg.getGrabWindow();
- _grabKeyboardTime = _xServer.getTimestamp();
- _grabKeyboardOwnerEvents = pkg.getOwnerEvents();
- _grabPointerSynchronous = pkg.getPointerSynchronous();
- _grabKeyboardSynchronous = pkg.getKeyboardSynchronous();
- }
- }
-
- if (_grabKeyboardWindow == null) {
- Window w = _rootWindow.windowAtPoint(_motionX, _motionY);
-
- if (w.isAncestor(_focusWindow)) w.keyNotify(pressed, _motionX, _motionY, keycode, null);
- else _focusWindow.keyNotify(pressed, _motionX, _motionY, keycode, null);
- reflectKeyboardFreezeNextEvent();
- } else if (!_grabKeyboardSynchronous) {
- callGrabKeyNotify(_grabKeyboardWindow, pressed, _motionX, _motionY, keycode, _grabKeyboardClient, _grabKeyboardOwnerEvents);
- } else {
- PendingKeyboardEvent e;
- e = new PendingGrabKeyNotify(_grabKeyboardWindow, pressed, _motionX, _motionY, keycode, _grabKeyboardClient, _grabKeyboardOwnerEvents);
- mPendingKeyboardEvents.add(e);
- }
-
- kb.updateKeymap(keycode, pressed);
-
- if (!pressed && _grabKeyboardPassiveGrab != null) {
- int rk = _grabKeyboardPassiveGrab.getKey();
-
- if (rk == 0 || rk == keycode) {
- _grabKeyboardPassiveGrab = null;
- _grabKeyboardClient = null;
- _grabKeyboardWindow = null;
- }
- }
- }
-
- /**
- * Called when there is a key down event.
- *
- * @param keycode The value in event.getKeyCode().
- * @param event The key event.
- * @return True if the event was handled.
- */
- @Override
- public boolean onKeyDown(int keycode, KeyEvent event) {
- synchronized (_xServer) {
- if (_rootWindow == null) return false;
-
- blank(false); // Reset the screen saver.
-
- boolean sendEvent = false;
-
- if (_arrowsAsButtons) {
- switch (keycode) {
- case KeyEvent.KEYCODE_DPAD_LEFT:
- case KeyEvent.KEYCODE_DPAD_CENTER:
- updatePointerButtons (1, true);
- return true;
- case KeyEvent.KEYCODE_DPAD_UP:
- case KeyEvent.KEYCODE_DPAD_DOWN:
- updatePointerButtons (2, true);
- return true;
- case KeyEvent.KEYCODE_DPAD_RIGHT:
- updatePointerButtons (3, true);
- return true;
- }
- }
-
- switch (keycode) {
- case KeyEvent.KEYCODE_BACK:
- if (! _inhibitBackButton)
- return false;
- keycode = 128 - _xServer.getKeyboard().getMinimumKeycodeDiff(); // Special keycode since keycode value 5 is out of range
- sendEvent = true;
- break;
- case KeyEvent.KEYCODE_MENU:
- return false;
- case KeyEvent.KEYCODE_VOLUME_UP:
- updatePointerButtons (1, true);
- break;
- case KeyEvent.KEYCODE_VOLUME_DOWN:
- updatePointerButtons (3, true);
- break;
- default:
- sendEvent = true;
- break;
- }
-
- updateModifiers();
- if (sendEvent) notifyKeyPressedReleased(keycode, true);
- }
-
- return true;
- }
-
- /**
- * Called when there is a key up event.
- *
- * @param keycode The value in event.getKeyCode().
- * @param event The key event.
- * @return True if the event was handled.
- */
- @Override
- public boolean onKeyUp(int keycode, KeyEvent event) {
- synchronized (_xServer) {
- if (_rootWindow == null) return false;
-
- blank(false); // Reset the screen saver.
-
- boolean sendEvent = false;
-
- if (_arrowsAsButtons) {
- switch (keycode) {
- case KeyEvent.KEYCODE_DPAD_LEFT:
- case KeyEvent.KEYCODE_DPAD_CENTER:
- updatePointerButtons (1, false);
- return true;
- case KeyEvent.KEYCODE_DPAD_UP:
- case KeyEvent.KEYCODE_DPAD_DOWN:
- updatePointerButtons (2, false);
- return true;
- case KeyEvent.KEYCODE_DPAD_RIGHT:
- updatePointerButtons (3, false);
- return true;
- }
- }
-
- switch (keycode) {
- case KeyEvent.KEYCODE_BACK:
- if (! _inhibitBackButton)
- return false;
- keycode = 128 - _xServer.getKeyboard().getMinimumKeycodeDiff(); // Special keycode since keycode value 5 is out of range
- sendEvent = true;
- break;
- case KeyEvent.KEYCODE_MENU:
- return false;
- case KeyEvent.KEYCODE_VOLUME_UP:
- updatePointerButtons (1, false);
- break;
- case KeyEvent.KEYCODE_VOLUME_DOWN:
- updatePointerButtons (3, false);
- break;
- default:
- sendEvent = true;
- break;
- }
-
- updateModifiers();
- if (sendEvent) notifyKeyPressedReleased(keycode, false);
- }
-
- return true;
- }
-
- /**
- * Write details of the screen.
- *
- * @param io The input/output stream.
- * @throws IOException
- */
- public void write(InputOutput io) throws IOException {
- Visual vis = _xServer.getRootVisual();
-
- io.writeInt(_rootWindow.getId()); // Root window ID.
- io.writeInt(_defaultColormap.getId()); // Default colormap ID.
- io.writeInt(_defaultColormap.getWhitePixel()); // White pixel.
- io.writeInt(_defaultColormap.getBlackPixel()); // Black pixel.
- io.writeInt(0); // Current input masks.
- io.writeShort((short) getWidth()); // Width in pixels.
- io.writeShort((short) getHeight()); // Height in pixels.
- io.writeShort((short) (getWidth() / _pixelsPerMillimeter)); // Width in millimeters.
- io.writeShort((short) (getHeight() / _pixelsPerMillimeter)); // Height in millimeters.
- io.writeShort((short) 1); // Minimum installed maps.
- io.writeShort((short) 1); // Maximum installed maps.
- io.writeInt(vis.getId()); // Root visual ID.
- io.writeByte(vis.getBackingStoreInfo());
- io.writeByte((byte) (vis.getSaveUnder() ? 1 : 0));
- io.writeByte((byte) vis.getDepth()); // Root depth.
- io.writeByte((byte) 1); // Number of allowed depths.
-
- // Write the only allowed depth.
- io.writeByte((byte) vis.getDepth()); // Depth.
- io.writeByte((byte) 0); // Unused.
- io.writeShort((short) 1); // Number of visuals with this depth.
- io.writePadBytes(4); // Unused.
- vis.write(io); // The visual at this depth.
- }
-
- /**
- * Write the screen's installed colormaps.
- *
- * @param client The remote client.
- * @throws IOException
- */
- public void writeInstalledColormaps(Client client) throws IOException {
- InputOutput io = client.getInputOutput();
- int n = _installedColormaps.size();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 0);
- io.writeInt(n); // Reply length.
- io.writeShort((short) n); // Number of colormaps.
- io.writePadBytes(22); // Unused.
-
- for (Colormap cmap : _installedColormaps)
- io.writeInt(cmap.getId());
- }
- io.flush();
- }
-
- /**
- * Process a screen-related request.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param opcode The request's opcode.
- * @param arg Optional first argument.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public void processRequest(XServer xServer, Client client, byte opcode, byte arg, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- switch (opcode) {
- case RequestCode.SendEvent:
- if (bytesRemaining != 40) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- processSendEventRequest(_xServer, client, arg == 1);
- }
- break;
- case RequestCode.GrabPointer:
- if (bytesRemaining != 20) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- processGrabPointerRequest(_xServer, client, arg == 1);
- }
- break;
- case RequestCode.UngrabPointer:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int time = io.readInt(); // Time.
- int now = _xServer.getTimestamp();
-
- if (time == 0) time = now;
-
- if (time >= _grabPointerTime && time <= now && _grabPointerClient == client) {
- _grabPointerClient = null;
- _grabPointerWindow = null;
- _grabCursor = null;
- _grabConfineWindow = null;
- updatePointer(2);
- }
- }
- break;
- case RequestCode.GrabButton:
- if (bytesRemaining != 20) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- processGrabButtonRequest(_xServer, client, arg == 1);
- }
- break;
- case RequestCode.UngrabButton:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int wid = io.readInt(); // Grab window.
- int modifiers = io.readShort(); // Modifiers.
- Resource r = _xServer.getResource(wid);
-
- io.readSkip(2); // Unused.
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, opcode, wid);
- } else {
- Window w = (Window) r;
-
- w.removePassiveButtonGrab(arg, modifiers);
- }
- }
- break;
- case RequestCode.ChangeActivePointerGrab:
- if (bytesRemaining != 12) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int cid = io.readInt(); // Cursor.
- int time = io.readInt(); // Time.
- int mask = io.readShort(); // Event mask.
- Cursor c = null;
-
- io.readSkip(2); // Unused.
-
- if (cid != 0) {
- Resource r = _xServer.getResource(cid);
-
- if (r == null || r.getType() != Resource.CURSOR)
- ErrorCode.write(client, ErrorCode.Cursor, opcode, 0);
- else c = (Cursor) r;
- }
-
- int now = _xServer.getTimestamp();
-
- if (time == 0) time = now;
-
- if (_grabPointerWindow != null && !_grabPointerPassive && _grabPointerClient == client && time >= _grabPointerTime && time <= now && (cid == 0 || c != null)) {
- _grabEventMask = mask;
- if (c != null) _grabCursor = c;
- else _grabCursor = _grabPointerWindow.getCursor();
- }
- }
- break;
- case RequestCode.GrabKeyboard:
- if (bytesRemaining != 12) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- processGrabKeyboardRequest(_xServer, client, arg == 1);
- }
- break;
- case RequestCode.UngrabKeyboard:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int time = io.readInt(); // Time.
- int now = _xServer.getTimestamp();
-
- if (time == 0) time = now;
-
- if (time >= _grabKeyboardTime && time <= now) {
- Window pw = _rootWindow.windowAtPoint(_motionX, _motionY);
-
- Window.focusInOutNotify(_grabKeyboardWindow, _focusWindow, pw, _rootWindow, 2);
- _grabKeyboardClient = null;
- _grabKeyboardWindow = null;
- }
- }
- break;
- case RequestCode.GrabKey:
- if (bytesRemaining != 12) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- processGrabKeyRequest(_xServer, client, arg == 1);
- }
- break;
- case RequestCode.UngrabKey:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int wid = io.readInt(); // Grab window.
- int modifiers = io.readShort(); // Modifiers.
- Resource r = _xServer.getResource(wid);
-
- io.readSkip(2); // Unused.
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, opcode, wid);
- } else {
- Window w = (Window) r;
-
- w.removePassiveKeyGrab(arg, modifiers);
- }
- }
- break;
- case RequestCode.AllowEvents:
- processAllowEvents(client, opcode, io, bytesRemaining, arg);
- break;
- case RequestCode.SetInputFocus:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- processSetInputFocusRequest(_xServer, client, arg);
- }
- break;
- case RequestCode.GetInputFocus:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int wid;
-
- if (_focusWindow == null) wid = 0;
- else if (_focusWindow == _rootWindow) wid = 1;
- else wid = _focusWindow.getId();
-
- synchronized (io) {
- Util.writeReplyHeader(client, _focusRevertTo);
- io.writeInt(0); // Reply length.
- io.writeInt(wid); // Focus window.
- io.writePadBytes(20); // Unused.
- }
- io.flush();
- }
- break;
- }
- }
-
- private void processAllowEvents(Client client, byte opcode, InputOutput io, int bytesRemaining, byte mode) throws IOException {
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- return;
- }
-
- int t = io.readInt();
- int now = _xServer.getTimestamp();
- int time = t == 0 ? now : t;
- if ((now < time) || (time < _grabPointerTime) || (time < _grabKeyboardTime)) {
- return;
- }
-
- String message;
- switch (mode) {
- case RequestCode.AllowEventsMode.AsyncPointer:
- flushPendingPointerEvents();
- _grabPointerSynchronous = false;
- _grabPointerFreezeNextEvent = false;
- break;
- case RequestCode.AllowEventsMode.SyncPointer:
- flushPendingPointerEvents();
- _grabPointerSynchronous = false;
- _grabPointerFreezeNextEvent = true;
- break;
- case RequestCode.AllowEventsMode.AsyncKeyboard:
- flushPendingKeyboardEvents();
- _grabKeyboardSynchronous = false;
- _grabKeyboardFreezeNextEvent = false;
- break;
- case RequestCode.AllowEventsMode.SyncKeyboard:
- flushPendingKeyboardEvents();
- _grabKeyboardSynchronous = false;
- _grabKeyboardFreezeNextEvent = true;
- break;
- case RequestCode.AllowEventsMode.AsyncBoth:
- case RequestCode.AllowEventsMode.SyncBoth:
- case RequestCode.AllowEventsMode.ReplayPointer:
- case RequestCode.AllowEventsMode.ReplayKeyboard:
- String fmt = "unsupported AllowEvents mode: %d (%s)";
- String name = RequestCode.AllowEventsMode.toString(mode);
- message = String.format(fmt, mode, name);
- reportError(client, ErrorCode.Implementation, opcode, message);
- break;
- default:
- message = String.format("unknown AllowEvents mode: %d", mode);
- reportError(client, ErrorCode.Value, opcode, message);
- break;
- }
- }
-
- private void reportError(Client client, byte error, byte opcode, String message) throws IOException {
- ErrorCode.write(client, error, opcode, 0);
- }
-
- /**
- * Toggle Arrows As Buttons.
- *
- * Switch between key and button events for arrow keys
- *
- * @return new state of switch
- */
- public boolean toggleArrowsAsButtons() {
- _arrowsAsButtons = !_arrowsAsButtons;
- return _arrowsAsButtons;
- }
-
- /**
- * Toggle shared clipboard. Shared clipboard works when using the long press
- * action shortcuts.
- *
- * @return new state of switch
- */
- public boolean toggleSharedClipboard() {
- _sharedClipboard = !_sharedClipboard;
- return _sharedClipboard;
- }
-
- /**
- * Toggle Inhibit Back Button.
- *
- * @return new state of switch
- */
- public boolean toggleInhibitBackButton() {
- _inhibitBackButton = !_inhibitBackButton;
- return _inhibitBackButton;
- }
-
- /**
- * Toggle touchscreen mouse click emulation.
- *
- * @return new state of switch
- */
- public boolean toggleEnableTouchClicks() {
- _enableTouchClicks = !_enableTouchClicks;
- return _enableTouchClicks;
- }
-
- /**
- * Process a SendEvent request.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param propagate Propagate flag.
- * @throws IOException
- */
- private void processSendEventRequest(XServer xServer, Client client, boolean propagate) throws IOException {
- InputOutput io = client.getInputOutput();
- int wid = io.readInt(); // Destination window.
- int mask = io.readInt(); // Event mask.
- byte[] event = new byte[32];
- Window w;
-
- io.readBytes(event, 0, 32); // Event.
-
- if (wid == 0) { // Pointer window.
- w = _rootWindow.windowAtPoint(_motionX, _motionY);
- } else if (wid == 1) { // Input focus.
- if (_focusWindow == null) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.SendEvent, wid);
- return;
- }
-
- Window pw = _rootWindow.windowAtPoint(_motionX, _motionY);
-
- if (pw.isAncestor(_focusWindow)) w = pw;
- else w = _focusWindow;
- } else {
- Resource r = _xServer.getResource(wid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.SendEvent, wid);
- return;
- } else w = (Window) r;
- }
-
- Vector dc = null;
-
- if (mask == 0) {
- dc = new Vector();
- dc.add(w.getClient());
- } else if (!propagate) {
- dc = w.getSelectingClients(mask);
- } else {
- for (; ; ) {
- if ((dc = w.getSelectingClients(mask)) != null) break;
-
- mask &= ~w.getDoNotPropagateMask();
- if (mask == 0) break;
-
- w = w.getParent();
- if (w == null) break;
- if (wid == 1 && w == _focusWindow) break;
- }
- }
-
- if (dc == null) return;
-
- for (Client c : dc) {
- if (c == null) continue;
- InputOutput dio = c.getInputOutput();
-
- synchronized (dio) {
- dio.writeByte((byte) (event[0] | 128));
-
- if (event[0] == EventCode.KeymapNotify) {
- dio.writeBytes(event, 1, 31);
- } else {
- dio.writeByte(event[1]);
- dio.writeShort((short) (c.getSequenceNumber() & 0xffff));
- dio.writeBytes(event, 4, 28);
- }
- }
- dio.flush();
- }
- }
-
- /**
- * Process a GrabPointer request.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param ownerEvents Owner-events flag.
- * @throws IOException
- */
- private void processGrabPointerRequest(XServer xServer, Client client, boolean ownerEvents) throws IOException {
- InputOutput io = client.getInputOutput();
- int wid = io.readInt(); // Grab window.
- int mask = io.readShort(); // Event mask.
- boolean psync = (io.readByte() == 0); // Pointer mode.
- boolean ksync = (io.readByte() == 0); // Keyboard mode.
- int cwid = io.readInt(); // Confine-to.
- int cid = io.readInt(); // Cursor.
- int time = io.readInt(); // Time.
- Resource r = _xServer.getResource(wid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.GrabPointer, wid);
- return;
- }
-
- Window w = (Window) r;
- Cursor c = null;
- Window cw = null;
-
- if (cwid != 0) {
- r = _xServer.getResource(cwid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.GrabPointer, cwid);
- return;
- }
- cw = (Window) r;
- }
-
- if (cid != 0) {
- r = _xServer.getResource(cid);
- if (r != null && r.getType() != Resource.CURSOR) {
- ErrorCode.write(client, ErrorCode.Cursor, RequestCode.GrabPointer, cid);
- return;
- }
-
- c = (Cursor) r;
- }
-
- if (c == null) c = w.getCursor();
-
- byte status = 0; // Success.
- int now = _xServer.getTimestamp();
-
- if (time == 0) time = now;
-
- if (time < _grabPointerTime || time > now) {
- status = 2; // Invalid time.
- } else if (_grabPointerWindow != null && _grabPointerClient != client) {
- status = 1; // Already grabbed.
- } else {
- _grabPointerClient = client;
- _grabPointerWindow = w;
- _grabPointerPassive = false;
- _grabPointerAutomatic = false;
- _grabPointerTime = time;
- _grabCursor = c;
- _grabConfineWindow = cw;
- _grabEventMask = mask;
- _grabPointerOwnerEvents = ownerEvents;
- _grabPointerSynchronous = psync;
- _grabKeyboardSynchronous = ksync;
- }
-
- synchronized (io) {
- Util.writeReplyHeader(client, status);
- io.writeInt(0); // Reply length.
- io.writePadBytes(24); // Unused.
- }
- io.flush();
-
- if (status == 0) updatePointer(1);
- }
-
- /**
- * Process a GrabButton request.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param ownerEvents Owner-events flag.
- * @throws IOException
- */
- private void processGrabButtonRequest(XServer xServer, Client client, boolean ownerEvents) throws IOException {
- InputOutput io = client.getInputOutput();
- int wid = io.readInt(); // Grab window.
- int mask = io.readShort(); // Event mask.
- boolean psync = (io.readByte() == 0); // Pointer mode.
- boolean ksync = (io.readByte() == 0); // Keyboard mode.
- int cwid = io.readInt(); // Confine-to.
- int cid = io.readInt(); // Cursor.
- byte button = (byte) io.readByte(); // Button.
- int modifiers;
- Resource r = _xServer.getResource(wid);
-
- io.readSkip(1); // Unused.
- modifiers = io.readShort(); // Modifiers.
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.GrabPointer, wid);
- return;
- }
-
- Window w = (Window) r;
- Cursor c = null;
- Window cw = null;
-
- if (cwid != 0) {
- r = _xServer.getResource(cwid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.GrabPointer, cwid);
- return;
- }
- cw = (Window) r;
- }
-
- if (cid != 0) {
- r = _xServer.getResource(cid);
-
- if (r != null && r.getType() != Resource.CURSOR) {
- ErrorCode.write(client, ErrorCode.Cursor, RequestCode.GrabPointer, cid);
- return;
- }
- c = (Cursor) r;
- }
-
- w.addPassiveButtonGrab(new PassiveButtonGrab(client, w, button, modifiers, ownerEvents, mask, psync, ksync, cw, c));
- }
-
- /**
- * Process a GrabKeyboard request.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param ownerEvents Owner-events flag.
- * @throws IOException
- */
- private void processGrabKeyboardRequest(XServer xServer, Client client, boolean ownerEvents) throws IOException {
- InputOutput io = client.getInputOutput();
- int wid = io.readInt(); // Grab window.
- int time = io.readInt(); // Time.
- boolean psync = (io.readByte() == 0); // Pointer mode.
- boolean ksync = (io.readByte() == 0); // Keyboard mode.
- Resource r = _xServer.getResource(wid);
-
- io.readSkip(2); // Unused.
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.GrabKeyboard, wid);
- return;
- }
-
- Window w = (Window) r;
- byte status = 0; // Success.
- int now = _xServer.getTimestamp();
-
- if (time == 0) time = now;
-
- if (time < _grabKeyboardTime || time > now) {
- status = 2; // Invalid time.
- } else if ((_grabKeyboardWindow != null) && (_grabKeyboardClient != client)) {
- status = 1; // Already grabbed.
- } else {
- _grabKeyboardClient = client;
- _grabKeyboardWindow = w;
- _grabKeyboardTime = time;
- _grabKeyboardOwnerEvents = ownerEvents;
- _grabPointerSynchronous = psync;
- _grabKeyboardSynchronous = ksync;
- }
-
- synchronized (io) {
- Util.writeReplyHeader(client, status);
- io.writeInt(0); // Reply length.
- io.writePadBytes(24); // Unused.
- }
- io.flush();
-
- if (status == 0)
- Window.focusInOutNotify(_focusWindow, w, _rootWindow.windowAtPoint(_motionX, _motionY), _rootWindow, 1);
- }
-
- /**
- * Process a GrabKey request.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param ownerEvents Owner-events flag.
- * @throws IOException
- */
- private void processGrabKeyRequest(XServer xServer, Client client, boolean ownerEvents) throws IOException {
- InputOutput io = client.getInputOutput();
- int wid = io.readInt(); // Grab window.
- int modifiers = io.readShort(); // Modifiers.
- byte keycode = (byte) io.readByte(); // Key.
- boolean psync = (io.readByte() == 0); // Pointer mode.
- boolean ksync = (io.readByte() == 0); // Keyboard mode.
- Resource r = _xServer.getResource(wid);
-
- io.readSkip(3); // Unused.
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.GrabPointer, wid);
- return;
- }
-
- Window w = (Window) r;
-
- w.addPassiveKeyGrab(new PassiveKeyGrab(client, w, keycode, modifiers, ownerEvents, psync, ksync));
- }
-
- /**
- * Process a SetInputFocus request.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param revertTo 0=None, 1=Root, 2=Parent.
- * @throws IOException
- */
- private void processSetInputFocusRequest(XServer xServer, Client client, byte revertTo) throws IOException {
- InputOutput io = client.getInputOutput();
- int wid = io.readInt(); // Focus window.
- int time = io.readInt(); // Time.
- Window w;
-
- if (wid == 0) {
- w = null;
- revertTo = 0;
- } else if (wid == 1) {
- w = _rootWindow;
- revertTo = 0;
- } else {
- Resource r = xServer.getResource(wid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.GrabPointer, wid);
- return;
- }
-
- w = (Window) r;
- }
-
- int now = xServer.getTimestamp();
-
- if (time == 0) time = now;
-
- if (time < _focusLastChangeTime || time > now) return;
-
- Window.focusInOutNotify(_focusWindow, w, _rootWindow.windowAtPoint(_motionX, _motionY), _rootWindow, _grabKeyboardWindow == null ? 0 : 3);
-
- _focusWindow = w;
- _focusRevertTo = revertTo;
- _focusLastChangeTime = time;
- }
-
- private void reflectPointerFreezeNextEvent() {
- _grabPointerSynchronous = _grabPointerFreezeNextEvent;
- }
-
- private void reflectKeyboardFreezeNextEvent() {
- _grabKeyboardSynchronous = _grabKeyboardFreezeNextEvent;
- }
-
- private void callGrabButtonNotify(Window w, boolean pressed, int motionX, int motionY, int button, int grabEventMask, Client grabPointerClient, boolean grabPointerOwnerEvents) {
- w.grabButtonNotify(pressed, motionX, motionY, button, grabEventMask, grabPointerClient, grabPointerOwnerEvents);
- reflectPointerFreezeNextEvent();
- }
-
- private void callGrabMotionNotify(Window w, int x, int y, int buttons, int grabEventMask, Client grabPointerClient, boolean grabPointerOwnerEvents) {
- w.grabMotionNotify(x, y, buttons & 0xff00, grabEventMask, grabPointerClient, grabPointerOwnerEvents);
- }
-
- private void callGrabKeyNotify(Window w, boolean pressed, int motionX, int motionY, int keycode, Client grabKeyboardClient, boolean grabKeyboardOwnerEvents) {
- w.grabKeyNotify(pressed, motionX, motionY, keycode, grabKeyboardClient, grabKeyboardOwnerEvents);
- reflectKeyboardFreezeNextEvent();
- }
-
- private void flushPendingPointerEvents() {
- flushPendingEvents(mPendingPointerEvents);
- }
-
- private void flushPendingKeyboardEvents() {
- flushPendingEvents(mPendingKeyboardEvents);
- }
-
- private void flushPendingEvents(PendingEventQueue q) {
- PendingEvent e;
- while ((e = q.next()) != null) {
- e.run();
- }
- }
-
- /**
- * @return true if shared clipboard is enabled, false otherwise.
- */
- public boolean hasSharedClipboard() {
- return _sharedClipboard;
- }
-
- /**
- * @return Window used for shared clipboard.
- */
- public Window getSharedClipboardWindow(){
- return _sharedClipboardWindow;
- }
-}
diff --git a/library/src/main/java/au/com/darkside/xserver/Selection.java b/library/src/main/java/au/com/darkside/xserver/Selection.java
deleted file mode 100644
index 16c7e2f..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Selection.java
+++ /dev/null
@@ -1,297 +0,0 @@
-package au.com.darkside.xserver;
-
-import java.io.IOException;
-
-
-/**
- * This class implements a selection.
- *
- * @author Matthew KWan
- */
-public class Selection {
- private final int _id;
- private Client _owner = null;
- private Window _ownerWindow = null;
- private int _lastChangeTime = 0;
-
- /**
- * Constructor.
- *
- * @param id The selection's ID.
- */
- public Selection(int id) {
- _id = id;
- }
-
- /**
- * Return the selection's atom ID.
- *
- * @return The selection's atom ID.
- */
- public int getId() {
- return _id;
- }
-
- /**
- * If the selection is owned by the client, clear it.
- * This occurs when a client disconnects.
- *
- * @param client The disconnecting client.
- */
- public void clearClient(Client client) {
- if (_owner == client) {
- _owner = null;
- _ownerWindow = null;
- }
- }
-
- /**
- * Allows transfering a selection to a (window-)property.
- * @param xServer xServer to perform this action on.
- * @param fromSelectionAtom Atom associated with the source selection. (i.e. "CLIPBOARD")
- * @param toPropertyAtom Atom associated with the target property (i.e. "CLIPBOARD" of target window).
- * @param toWindow Window holding toPropertyAtom. (the propertyAtom can be reused, so we need to specify the window which holds the property this atom is associated with)
- * @param transferTypeAtom Atom describing the clipboard type (i.e. "UTF8_STRING").
- */
- public static void transferSelectionRequest(XServer xServer, Atom fromSelectionAtom, Atom toPropertyAtom, Window toWindow, Atom transferTypeAtom){
- Selection srcSelection = xServer.getSelection(fromSelectionAtom.getId());
- if(srcSelection == null)
- return; // selection not owned by any client
- try{
- if(srcSelection._owner != null) {
- EventCode.sendSelectionRequest(srcSelection._owner, xServer.getTimestamp(), srcSelection._ownerWindow, toWindow, fromSelectionAtom, transferTypeAtom, toPropertyAtom);
- }
- }
- catch (IOException e){
- // silently fail
- }
- }
-
- /**
- * Allows changing/setting the owner of a selection.
- * @param xServer xServer to perform this action on.
- * @param selectionAtom Atom associated with the selection. (i.e. "CLIPBOARD")
- * @param owner New owner window.
- */
- public static void setSelectionOwner(XServer xServer, Atom selectionAtom, Window owner) {
- Selection sel = xServer.getSelection(selectionAtom.getId());
-
- if (sel == null) {
- sel = new Selection(selectionAtom.getId());
- xServer.addSelection(sel);
- }
-
- // remove old owner
- if (sel._owner != null && sel._owner != owner.getClient()){
- try{
- EventCode.sendSelectionClear(sel._owner, sel._lastChangeTime, owner, selectionAtom);
- }
- catch (IOException e){
- // silently fail
- }
- }
- sel._lastChangeTime = xServer.getTimestamp();
- sel._ownerWindow = owner;
- sel._owner = owner.getClient();
- }
-
- /**
- * Process an X request relating to selections.
- *
- * @param xServer The X server.
- * @param client The client issuing the request.
- * @param opcode The request's opcode.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public static void processRequest(XServer xServer, Client client, byte opcode, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- switch (opcode) {
- case RequestCode.SetSelectionOwner:
- processSetSelectionOwnerRequest(xServer, client, bytesRemaining);
- break;
- case RequestCode.GetSelectionOwner:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int aid = io.readInt(); // Selection atom.
-
- if (!xServer.atomExists(aid)) {
- ErrorCode.write(client, ErrorCode.Atom, RequestCode.SetSelectionOwner, aid);
- } else {
- int wid = 0;
- Selection sel = xServer.getSelection(aid);
-
- if (sel != null && sel._ownerWindow != null) wid = sel._ownerWindow.getId();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 0);
- io.writeInt(0); // Reply length.
- io.writeInt(wid); // Owner.
- io.writePadBytes(20); // Unused.
- }
- io.flush();
- }
- }
- break;
- case RequestCode.ConvertSelection:
- processConvertSelectionRequest(xServer, client, bytesRemaining);
- break;
- default:
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Implementation, opcode, 0);
- break;
- }
- }
-
- /**
- * Process a SetSelectionOwner request.
- * Change the owner of the specified selection.
- *
- * @param xServer The X server.
- * @param client The client issuing the request.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public static void processSetSelectionOwnerRequest(XServer xServer, Client client, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- if (bytesRemaining != 12) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.SetSelectionOwner, 0);
- return;
- }
-
- int wid = io.readInt(); // Owner window.
- int aid = io.readInt(); // Selection atom.
- int time = io.readInt(); // Timestamp.
- Window w = null;
-
- if (wid != 0) {
- Resource r = xServer.getResource(wid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.SetSelectionOwner, wid);
- return;
- }
-
- w = (Window) r;
- }
-
- Atom a = xServer.getAtom(aid);
-
- if (a == null) {
- ErrorCode.write(client, ErrorCode.Atom, RequestCode.SetSelectionOwner, aid);
- return;
- }
-
- Selection sel = xServer.getSelection(aid);
-
- if (sel == null) {
- sel = new Selection(aid);
- xServer.addSelection(sel);
- }
-
- int now = xServer.getTimestamp();
-
- if (time != 0) {
- if (time < sel._lastChangeTime || time >= now) return;
- } else {
- time = now;
- }
-
- sel._lastChangeTime = time;
- sel._ownerWindow = w;
-
- if (sel._owner != null && sel._owner != client)
- EventCode.sendSelectionClear(sel._owner, time, w, a);
-
- sel._owner = (w != null) ? client : null;
- if (xServer.getScreen().hasSharedClipboard() && aid == xServer.findAtom("CLIPBOARD").getId())
- transferSelectionRequest(xServer, xServer.findAtom("CLIPBOARD"), xServer.findAtom("CLIPBOARD"), xServer.getScreen().getSharedClipboardWindow() , xServer.findAtom("UTF8_STRING"));
- else if (xServer.getScreen().hasSharedClipboard() && aid == xServer.findAtom("PRIMARY").getId())
- transferSelectionRequest(xServer, xServer.findAtom("PRIMARY"), xServer.findAtom("PRIMARY"), xServer.getScreen().getSharedClipboardWindow() , xServer.findAtom("UTF8_STRING"));
-
-
- }
-
- /**
- * Process a ConvertSelection request.
- *
- * @param xServer The X server.
- * @param client The client issuing the request.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public static void processConvertSelectionRequest(XServer xServer, Client client, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- if (bytesRemaining != 20) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.ConvertSelection, 0);
- return;
- }
-
- int wid = io.readInt(); // Requestor.
- int sid = io.readInt(); // Selection.
- int tid = io.readInt(); // Target.
- int pid = io.readInt(); // Property.
- int time = io.readInt(); // Time.
- Resource r = xServer.getResource(wid);
- Window w;
- Atom selectionAtom, targetAtom, propertyAtom;
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.ConvertSelection, wid);
- return;
- } else {
- w = (Window) r;
- }
-
- selectionAtom = xServer.getAtom(sid);
- if (selectionAtom == null) {
- ErrorCode.write(client, ErrorCode.Atom, RequestCode.ConvertSelection, sid);
- return;
- }
-
- targetAtom = xServer.getAtom(tid);
- if (targetAtom == null) {
- ErrorCode.write(client, ErrorCode.Atom, RequestCode.ConvertSelection, tid);
- return;
- }
-
- propertyAtom = null;
- if (pid != 0 && (propertyAtom = xServer.getAtom(pid)) == null) {
- ErrorCode.write(client, ErrorCode.Atom, RequestCode.ConvertSelection, pid);
- return;
- }
-
- Client owner = null;
- Selection sel = xServer.getSelection(sid);
-
- if (sel != null) owner = sel._owner;
-
- Window ownerWindow = sel != null ? sel._ownerWindow : null;
- // move the property to the client the dirty way,... some interfaces would make sense here
- if(ownerWindow != null && ownerWindow.isServerWindow() && owner == null){
- Property target = w.getProperty(pid);
- if(target == null){
- target = new Property(pid, tid, (byte)8);
- w.addProperty(target);
- }
- target.setData(sel._ownerWindow.getProperty(sid).getData());
- target.setType(tid);
- }
-
- if (owner != null) {
- try {
- EventCode.sendSelectionRequest(owner, time, sel._ownerWindow, w, selectionAtom, targetAtom, propertyAtom);
- } catch (IOException e) {
- }
- } else {
- EventCode.sendSelectionNotify(client, time, w, selectionAtom, targetAtom, propertyAtom);
- }
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/Util.java b/library/src/main/java/au/com/darkside/xserver/Util.java
deleted file mode 100644
index 9d99819..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Util.java
+++ /dev/null
@@ -1,43 +0,0 @@
-package au.com.darkside.xserver;
-
-import java.io.IOException;
-
-/**
- * Utility functions.
- *
- * @author Matthew Kwan
- */
-public class Util {
- /**
- * Count the number of bits in an integer.
- *
- * @param n The integer containing the bits.
- * @return The number of bits in the integer.
- */
- public static int bitcount(int n) {
- int c = 0;
-
- while (n != 0) {
- c += n & 1;
- n >>= 1;
- }
-
- return c;
- }
-
- /**
- * Write the header of a reply.
- *
- * @param client The remote client.
- * @param arg Optional argument.
- * @throws IOException
- */
- public static void writeReplyHeader(Client client, byte arg) throws IOException {
- InputOutput io = client.getInputOutput();
- short sn = (short) (client.getSequenceNumber() & 0xffff);
-
- io.writeByte((byte) 1); // Reply.
- io.writeByte(arg);
- io.writeShort(sn);
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/Visual.java b/library/src/main/java/au/com/darkside/xserver/Visual.java
deleted file mode 100644
index f979239..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Visual.java
+++ /dev/null
@@ -1,87 +0,0 @@
-package au.com.darkside.xserver;
-
-import java.io.IOException;
-
-
-/**
- * An X visual. This is always 32-bit TrueColor.
- *
- * @author Matthew Kwan
- */
-public class Visual {
- public final static byte BackingStoreNever = 0;
- public final static byte BackingStoreWhenMapped = 1;
- public final static byte BackingStoreAlways = 2;
-
- public final static byte StaticGray = 0;
- public final static byte GrayScale = 1;
- public final static byte StaticColor = 2;
- public final static byte PseudoColor = 3;
- public final static byte TrueColor = 4;
- public final static byte DirectColor = 5;
-
- private final int _id;
-
- /**
- * Constructor.
- *
- * @param id The visual ID.
- */
- public Visual(int id) {
- _id = id;
- }
-
- /**
- * Return the visual's ID.
- *
- * @return The visual's ID.
- */
- public int getId() {
- return _id;
- }
-
- /**
- * Return whether the visual supports a backing store.
- *
- * @return Whether a backing store is supported.
- */
- public byte getBackingStoreInfo() {
- return BackingStoreAlways;
- }
-
- /**
- * Return whether the visual supports save-under.
- *
- * @return Whether save-under is supported.
- */
- public boolean getSaveUnder() {
- return false;
- }
-
- /**
- * Return the depth of the visual.
- * Under Android this is always 32.
- *
- * @return The depth of the visual, in bits.
- */
- public byte getDepth() {
- return 32;
- }
-
- /**
- * Write details of the visual.
- *
- * @param io The input/output stream.
- * @throws IOException
- */
- public void write(InputOutput io) throws IOException {
- io.writeInt(_id); // Visual ID.
- io.writeByte(TrueColor); // Class.
- io.writeByte((byte) 8); // Bits per RGB value.
- io.writeShort((short) (1 << 8)); // Colormap entries.
- io.writeInt(0x00ff0000); // Red mask.
- io.writeInt(0x0000ff00); // Green mask.
- io.writeInt(0x000000ff); // Blue mask.
- io.writePadBytes(4); // Unused.
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/Window.java b/library/src/main/java/au/com/darkside/xserver/Window.java
deleted file mode 100644
index b74efc3..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Window.java
+++ /dev/null
@@ -1,2891 +0,0 @@
-package au.com.darkside.xserver;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.Region;
-
-import java.io.IOException;
-import java.util.HashSet;
-import java.util.Hashtable;
-import java.util.Iterator;
-import java.util.Set;
-import java.util.Stack;
-import java.util.Vector;
-
-import au.com.darkside.xserver.Xext.XShape;
-import au.com.darkside.xserver.Xext.Extensions;
-
-/**
- * This class implements an X window.
- *
- * @author Matthew Kwan
- */
-public class Window extends Resource {
- private final ScreenView _screen;
- private Window _parent;
- private Rect _orect;
- private Rect _irect;
- private Region _boundingShapeRegion = null;
- private Region _clipShapeRegion = null;
- private Region _inputShapeRegion = null;
- private Vector _shapeSelectInput;
- private Drawable _drawable;
- private Colormap _colormap;
- private Cursor _cursor = null;
- private int[] _attributes;
- private int _borderWidth;
- private final boolean _inputOnly;
- private boolean _overrideRedirect;
- private boolean _isServerWindow = false;
- private boolean _hardwareAccelerated = false;
- private final Vector _children;
- private final Hashtable _properties;
- private final Set _passiveButtonGrabs;
- private final Set _passiveKeyGrabs;
- private boolean _isMapped = false;
- private boolean _exposed = false;
- private int _visibility = NotViewable;
- private Bitmap _backgroundBitmap = null;
- private int _eventMask = 0;
- private final Hashtable _clientMasks;
-
- private static final int Unobscured = 0;
- private static final int PartiallyObscured = 1;
- private static final int FullyObscured = 2;
- private static final int NotViewable = 3;
-
- private static final int AttrBackgroundPixmap = 0;
- private static final int AttrBackgroundPixel = 1;
- private static final int AttrBorderPixmap = 2;
- private static final int AttrBorderPixel = 3;
- private static final int AttrBitGravity = 4;
- private static final int AttrWinGravity = 5;
- private static final int AttrBackingStore = 6;
- private static final int AttrBackingPlanes = 7;
- private static final int AttrBackingPixel = 8;
- private static final int AttrOverrideRedirect = 9;
- private static final int AttrSaveUnder = 10;
- private static final int AttrEventMask = 11;
- private static final int AttrDoNotPropagateMask = 12;
- private static final int AttrColormap = 13;
- private static final int AttrCursor = 14;
-
- private static final int WinGravityUnmap = 0;
- private static final int WinGravityNorthWest = 1;
- private static final int WinGravityNorth = 2;
- private static final int WinGravityNorthEast = 3;
- private static final int WinGravityWest = 4;
- private static final int WinGravityCenter = 5;
- private static final int WinGravityEast = 6;
- private static final int WinGravitySouthWest = 7;
- private static final int WinGravitySouth = 8;
- private static final int WinGravitySouthEast = 9;
- private static final int WinGravityStatic = 10;
-
- /**
- * Constructor.
- *
- * @param id The window's ID.
- * @param xServer The X server.
- * @param client The client issuing the request.
- * @param screen The window's screen.
- * @param parent The window's parent.
- * @param x X position relative to parent.
- * @param y Y position relative to parent.
- * @param width Width of the window.
- * @param height Height of the window.
- * @param borderWidth Width of the window's border.
- * @param inputOnly Is this an InputOnly window?
- * @param isRoot Is this the root window?
- */
- public Window(int id, XServer xServer, Client client, ScreenView screen, Window parent, int x, int y, int width, int height, int borderWidth, boolean inputOnly, boolean isRoot) {
- super(WINDOW, id, xServer, client);
-
- _screen = screen;
- _parent = parent;
- _borderWidth = borderWidth;
- _colormap = _screen.getDefaultColormap();
- _inputOnly = inputOnly;
-
- if (isRoot) {
- _orect = new Rect(0, 0, width, height);
- _irect = new Rect(0, 0, width, height);
- } else {
- final int left = _parent._orect.left + _parent._borderWidth + x;
- final int top = _parent._orect.top + _parent._borderWidth + y;
- final int border = 2 * borderWidth;
-
- _orect = new Rect(left, top, left + width + border, top + height + border);
- if (_borderWidth == 0) _irect = new Rect(_orect);
- else
- _irect = new Rect(left + borderWidth, top + borderWidth, _orect.right - borderWidth, _orect.bottom - borderWidth);
- }
-
- _attributes = new int[]{0, // background-pixmap = None
- 0, // background-pixel = zero
- 0, // border-pixmap = CopyFromParent
- 0, // border-pixel = zero
- 0, // bit-gravity = Forget
- WinGravityNorthWest, // win-gravity = NorthWest
- 0, // backing-store = NotUseful
- 0xffffffff, // backing-planes = all ones
- 0, // backing-pixel = zero
- 0, // override-redirect = False
- 0, // save-under = False
- 0, // event-mask = empty set
- 0, // do-not-propogate-mask = empty set
- 0, // colormap = CopyFromParent
- 0 // cursor = None
- };
-
- if (isRoot) {
- _attributes[AttrBackgroundPixel] = 0xffc0c0c0;
- _isMapped = true;
- _cursor = (Cursor) _xServer.getResource(2); // X cursor.
- _drawable = new Drawable(width, height, 32, null, _attributes[AttrBackgroundPixel]);
- _drawable.clear();
- } else {
- _attributes[AttrBackgroundPixel] = 0xff000000;
- _drawable = new Drawable(width, height, 32, null, _attributes[AttrBackgroundPixel]);
- }
-
- _children = new Vector();
- _properties = new Hashtable();
- _passiveButtonGrabs = new HashSet();
- _passiveKeyGrabs = new HashSet();
- _clientMasks = new Hashtable();
- _shapeSelectInput = new Vector();
- }
-
- /**
- * Is this a functional server only window?
- *
- * @return True if this is a hidden server only window.
- */
- public boolean isServerWindow() {
- return _isServerWindow;
- }
-
- /**
- * Flag this window as server only.
- *
- * @param b True if this is a hidden server only window.
- */
- public void setIsServerWindow(boolean b) {
- _isServerWindow = b;
- }
-
- /**
- * Is the clip region shaped?
- *
- * @return True if the clip region is shaped.
- */
- public boolean isClipShaped() {
- return _clipShapeRegion != null;
- }
-
- /**
- * Is the bounding region shaped?
- *
- * @return True if the bounding region is shaped.
- */
- public boolean isBoundingShaped() {
- return _boundingShapeRegion != null;
- }
-
- /**
- * Send a shape notify to all interested clients.
- *
- * @param shapeKind The kind of shape.
- */
- public void sendShapeNotify(byte shapeKind) {
- Region r = getShapeRegion(shapeKind);
- boolean shaped = (r != null);
- Rect rect;
-
- if (r != null) rect = r.getBounds();
- else if (shapeKind == XShape.KindClip) rect = _irect;
- else rect = _orect;
-
- for (Client client : _shapeSelectInput) {
- if (client == null) continue;
- try {
- InputOutput io = client.getInputOutput();
-
- synchronized (io) {
- io.writeByte(XShape.EventBase);
- io.writeByte((byte) shapeKind);
- io.writeShort((short) (client.getSequenceNumber() & 0xffff));
- io.writeInt(_id);
- io.writeShort((short) (rect.left - _irect.left));
- io.writeShort((short) (rect.top - _irect.left));
- io.writeShort((short) rect.width());
- io.writeShort((short) rect.height());
- io.writeInt(1);
- io.writeByte((byte) (shaped ? 1 : 0));
- io.writePadBytes(11);
- }
- io.flush();
- } catch (IOException e) {
- }
- }
- }
-
- /**
- * Add a client to the shape select input.
- *
- * @param client The client to add.
- */
- public void addShapeSelectInput(Client client) {
- _shapeSelectInput.add(client);
- }
-
- /**
- * Remove a client from the shape select input.
- *
- * @param client The client to remove.
- */
- public void removeShapeSelectInput(Client client) {
- _shapeSelectInput.remove(client);
- }
-
- /**
- * Does the client is the shape select input list?
- *
- * @param client The client to check.
- * @return True if the client is in the shape select input list.
- */
- public boolean shapeSelectInputEnabled(Client client) {
- return _shapeSelectInput.contains(client);
- }
-
- /**
- * Return a shape region.
- *
- * @param shapeKind The kind of shape to return.
- * @return The shape region.
- */
- public Region getShapeRegion(byte shapeKind) {
- switch (shapeKind) {
- case XShape.KindBounding:
- return _boundingShapeRegion;
- case XShape.KindClip:
- return _clipShapeRegion;
- case XShape.KindInput:
- return _inputShapeRegion;
- }
-
- return null;
- }
-
- /**
- * Set a shape region.
- *
- * @param shapeKind The kind of shape to set.
- * @param r The shape region.
- */
- public void setShapeRegion(byte shapeKind, Region r) {
- switch (shapeKind) {
- case XShape.KindBounding:
- _boundingShapeRegion = r;
- break;
- case XShape.KindClip:
- _clipShapeRegion = r;
- break;
- case XShape.KindInput:
- _inputShapeRegion = r;
- break;
- }
- }
-
- /**
- * Return the window's parent.
- *
- * @return The window's parent.
- */
- public Window getParent() {
- return _parent;
- }
-
- /**
- * Return the window's screen.
- *
- * @return The window's screen.
- */
- public ScreenView getScreen() {
- return _screen;
- }
-
- /**
- * Return the window's drawable.
- *
- * @return The window's drawable.
- */
- public Drawable getDrawable() {
- return _drawable;
- }
-
- /**
- * Return the window's cursor.
- *
- * @return The window's cursor.
- */
- public Cursor getCursor() {
- if (_cursor == null) return _parent.getCursor();
- else return _cursor;
- }
-
- /**
- * Return the window's inner rectangle.
- *
- * @return The window's inner rectangle.
- */
- public Rect getIRect() {
- return _irect;
- }
-
- /**
- * Return the window's outer rectangle.
- *
- * @return The window's outer rectangle.
- */
- public Rect getORect() {
- return _orect;
- }
-
- /**
- * Return the window's cumulative event mask.
- *
- * @return The window's event mask.
- */
- public int getEventMask() {
- return _eventMask;
- }
-
- /**
- * Return the list of clients selecting on the events.
- *
- * @param mask The event mask.
- * @return List of clients, or null if none selecting.
- */
- public Vector getSelectingClients(int mask) {
- if ((mask & _eventMask) == 0) return null;
-
- Vector rc = new Vector();
- Set sc = _clientMasks.keySet();
-
- for (Client c : sc) {
- if (c == null) continue;
- if ((_clientMasks.get(c) & mask) != 0) rc.add(c);
- }
-
- return rc;
- }
-
- /**
- * Remove a client from the event selection list.
- * Usually occurs after an I/O error on the client.
- *
- * @param client The client to remove.
- */
- private void removeSelectingClient(Client client) {
- _clientMasks.remove(client);
-
- Set sc = _clientMasks.keySet();
-
- _eventMask = 0;
- for (Client c : sc) {
- if (c == null) continue;
- _eventMask |= _clientMasks.get(c);
- }
- }
-
- /**
- * Return the event mask that the client is selecting on.
- *
- * @param client The client selecting on the events.
- * @return The event mask, or zero if the client is selecting.
- */
- public int getClientEventMask(Client client) {
- if (_clientMasks.containsKey(client)) return _clientMasks.get(client);
- else return 0;
- }
-
- /**
- * Return the window's do-not-propagate mask.
- *
- * @return The window's do-not-propagate mask.
- */
- public int getDoNotPropagateMask() {
- return _attributes[AttrDoNotPropagateMask];
- }
-
- /**
- * Is the window an inferior of this window?
- *
- * @param w The window being tested.
- * @return True if the window is a inferior of this window.
- */
- public boolean isInferior(Window w) {
- for (; ; ) {
- if (w._parent == this) return true;
- else if (w._parent == null) return false;
- else w = w._parent;
- }
- }
-
- /**
- * Is the window an ancestor of this window?
- *
- * @param w The window being tested.
- * @return True if the window is an ancestor of this window.
- */
- public boolean isAncestor(Window w) {
- return w.isInferior(this);
- }
-
- /**
- * Is the window viewable? It and all its ancestors must be mapped.
- *
- * @return True if the window is viewable.
- */
- public boolean isViewable() {
- for (Window w = this; w != null; w = w._parent)
- if (!w._isMapped) return false;
-
- return true;
- }
-
- /**
- * Draw the window and its mapped children.
- *
- * @param canvas The canvas to draw to.
- * @param paint A paint to draw with.
- */
- public void draw(Canvas canvas, Paint paint) {
- if (!_isMapped) return;
-
- if (_boundingShapeRegion != null) {
- canvas.save();
-
- if (!_hardwareAccelerated) {
- try {
- canvas.clipRect(_boundingShapeRegion.getBounds());
- } catch (UnsupportedOperationException e) {
- _hardwareAccelerated = true;
- }
- }
-
- paint.setColor(_attributes[AttrBorderPixel] | 0xff000000);
- paint.setStyle(Paint.Style.FILL);
- canvas.drawRect(_orect, paint);
- } else if (_borderWidth != 0) {
- if (!Rect.intersects(_orect, canvas.getClipBounds())) return;
-
- float hbw = 0.5f * _borderWidth;
-
- paint.setColor(_attributes[AttrBorderPixel] | 0xff000000);
- paint.setStrokeWidth(_borderWidth);
- paint.setStyle(Paint.Style.STROKE);
-
- canvas.drawRect(_orect.left + hbw, _orect.top + hbw, _orect.right - hbw, _orect.bottom - hbw, paint);
- }
-
- canvas.save();
-
- boolean clipIntersect;
-
- if (_clipShapeRegion != null && !_hardwareAccelerated) {
- try {
- clipIntersect = canvas.clipRect(_clipShapeRegion.getBounds());
- } catch (UnsupportedOperationException e) {
- _hardwareAccelerated = true;
- clipIntersect = canvas.clipRect(_irect);
- }
- } else {
- clipIntersect = canvas.clipRect(_irect);
- }
-
- if (clipIntersect) {
- if (!_inputOnly)
- canvas.drawBitmap(_drawable.getBitmap(), _irect.left, _irect.top, paint);
- for (Window w : _children)
- w.draw(canvas, paint);
- }
-
- canvas.restore();
- if (_boundingShapeRegion != null) canvas.restore();
- }
-
- /**
- * Return the mapped window whose input area contains the specified point.
- *
- * @param x X coordinate of the point.
- * @param y Y coordinate of the point.
- * @return The mapped window containing the point.
- */
- public Window windowAtPoint(int x, int y) {
- for (int i = _children.size() - 1; i >= 0; i--) {
- Window w = _children.elementAt(i);
-
- if (!w._isMapped) continue;
-
- if (w._inputShapeRegion != null) {
- if (w._inputShapeRegion.contains(x, y)) return w.windowAtPoint(x, y);
- } else if (w._orect.contains(x, y)) {
- return w.windowAtPoint(x, y);
- }
- }
-
- return this;
- }
-
- /**
- * Find a passive button grab on this window or its ancestors.
- *
- * @param buttons The pointer buttons and modifiers currently pressed.
- * @param highestPbg Highest pointer grab found so far.
- * @return The passive pointer grab from the highest ancestor.
- */
- public PassiveButtonGrab findPassiveButtonGrab(int buttons, PassiveButtonGrab highestPbg) {
- for (PassiveButtonGrab pbg : _passiveButtonGrabs) {
- if (pbg.matchesEvent(buttons)) {
- highestPbg = pbg;
- break;
- }
- }
-
- if (_parent == null) return highestPbg;
- else return _parent.findPassiveButtonGrab(buttons, highestPbg);
- }
-
- /**
- * Add a passive button grab.
- *
- * @param pbg The passive button grab.
- */
- public void addPassiveButtonGrab(PassiveButtonGrab pbg) {
- removePassiveButtonGrab(pbg.getButton(), pbg.getModifiers());
- _passiveButtonGrabs.add(pbg);
- }
-
- /**
- * Remove all passive button grabs that match the button and modifiers
- * combination.
- *
- * @param button The button, or 0 for any button.
- * @param modifiers The modifier mask, or 0x8000 for any.
- */
- public void removePassiveButtonGrab(byte button, int modifiers) {
- Iterator it = _passiveButtonGrabs.iterator();
-
- while (it.hasNext()) {
- PassiveButtonGrab pbg = it.next();
-
- if (pbg.matchesGrab(button, modifiers)) it.remove();
- }
- }
-
- /**
- * Find a passive key grab on this window or its ancestors.
- *
- * @param key The key that was pressed.
- * @param modifiers The modifiers currently pressed.
- * @param highestPkg Highest key grab found so far.
- * @return The passive key grab from the highest ancestor.
- */
- public PassiveKeyGrab findPassiveKeyGrab(int key, int modifiers, PassiveKeyGrab highestPkg) {
- for (PassiveKeyGrab pkg : _passiveKeyGrabs) {
- if (pkg.matchesEvent(key, modifiers)) {
- highestPkg = pkg;
- break;
- }
- }
-
- if (_parent == null) return highestPkg;
- else return _parent.findPassiveKeyGrab(key, modifiers, highestPkg);
- }
-
- /**
- * Add a passive key grab.
- *
- * @param pkg The passive key grab.
- */
- public void addPassiveKeyGrab(PassiveKeyGrab pkg) {
- removePassiveKeyGrab(pkg.getKey(), pkg.getModifiers());
- _passiveKeyGrabs.add(pkg);
- }
-
- /**
- * Remove all passive key grabs that match the key and modifiers
- * combination.
- *
- * @param key The key, or 0 for any key.
- * @param modifiers The modifier mask, or 0x8000 for any.
- */
- public void removePassiveKeyGrab(byte key, int modifiers) {
- Iterator it = _passiveKeyGrabs.iterator();
-
- while (it.hasNext()) {
- PassiveKeyGrab pkg = it.next();
-
- if (pkg.matchesGrab(key, modifiers)) it.remove();
- }
- }
-
- /**
- * Process a CreateWindow.
- * Create a window with the specified ID, with this window as parent.
- *
- * @param io The input/output stream.
- * @param client The client issuing the request.
- * @param sequenceNumber The request sequence number.
- * @param id The ID of the window to create.
- * @param depth The window depth.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @return True if the window was created successfully.
- * @throws IOException
- */
- public boolean processCreateWindowRequest(InputOutput io, Client client, int sequenceNumber, int id, int depth, int bytesRemaining) throws IOException {
- int x = (short) io.readShort(); // X position.
- int y = (short) io.readShort(); // Y position.
- int width = io.readShort(); // Window width.
- int height = io.readShort(); // Window height.
- int borderWidth = io.readShort(); // Border width.
- int wclass = io.readShort(); // Window class.
- Window w;
- boolean inputOnly;
-
- io.readInt(); // Visual.
- bytesRemaining -= 16;
-
- if (wclass == 0) // Copy from parent.
- inputOnly = _inputOnly;
- else if (wclass == 1) // Input/output.
- inputOnly = false;
- else inputOnly = true;
-
- try {
- w = new Window(id, _xServer, client, _screen, this, x, y, width, height, borderWidth, inputOnly, false);
- } catch (OutOfMemoryError e) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Alloc, RequestCode.CreateWindow, 0);
- return false;
- }
-
- if (!w.processWindowAttributes(client, RequestCode.CreateWindow, bytesRemaining))
- return false;
-
- w._drawable.clear();
-
- _xServer.addResource(w);
- client.addResource(w);
- _children.add(w);
-
- Vector sc;
-
- if ((sc = getSelectingClients(EventCode.MaskSubstructureNotify)) != null) {
- for (Client c : sc) {
- if (c == null) continue;
- EventCode.sendCreateNotify(c, this, w, x, y, width, height, borderWidth, _overrideRedirect);
- }
- }
-
- return true;
- }
-
- /**
- * Request a redraw of the window.
- */
- public void invalidate() {
- _screen.postInvalidate(_orect.left, _orect.top, _orect.right, _orect.bottom);
- }
-
- /**
- * Request a redraw of a region of the window.
- *
- * @param x X coordinate of the region.
- * @param y Y coordinate of the region.
- * @param width Width of the region.
- * @param height Height of the region.
- */
- public void invalidate(int x, int y, int width, int height) {
- _screen.postInvalidate(_irect.left + x, _irect.top + y, _irect.left + x + width, _irect.top + y + height);
- }
-
- /**
- * Delete this window from its parent.
- * Used when a client disconnects.
- */
- @Override
- public void delete() {
- Vector psc, sc;
-
- // Send unmap and destroy notification to any other clients that
- // are listening.
- removeSelectingClient(_client);
- _parent.removeSelectingClient(_client);
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- psc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
-
- if (_isMapped) {
- _screen.revertFocus(this);
- _isMapped = false;
-
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendUnmapNotify(c, this, this, false);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- if (psc != null) {
- for (Client c : psc) {
- if (c == null) continue;
- try {
- EventCode.sendUnmapNotify(c, _parent, this, false);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- updateAffectedVisibility();
- invalidate();
- }
-
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendDestroyNotify(c, this, this);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- if (psc != null) {
- for (Client c : psc) {
- if (c == null) continue;
- try {
- EventCode.sendDestroyNotify(c, _parent, this);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- _screen.deleteWindow(this);
-
- if (_parent != null) _parent._children.remove(this);
-
- super.delete();
- }
-
- /**
- * Process a list of window attributes.
- *
- * @param client The remote client.
- * @param opcode The opcode being processed.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @return True if the window is successfully created.
- * @throws IOException
- */
- private boolean processWindowAttributes(Client client, byte opcode, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- if (bytesRemaining < 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- return false;
- }
-
- int valueMask = io.readInt(); // Value mask.
- int n = Util.bitcount(valueMask);
-
- bytesRemaining -= 4;
- if (bytesRemaining != n * 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- return false;
- }
-
- for (int i = 0; i < 15; i++)
- if ((valueMask & (1 << i)) != 0) processValue(io, i);
-
- if (opcode == RequestCode.CreateWindow) // Apply all values on create.
- valueMask = 0xffffffff;
-
- return applyValues(client, opcode, valueMask);
- }
-
- /**
- * Process a single window attribute value.
- *
- * @param io The input/output stream.
- * @param maskBit The mask bit of the attribute.
- * @throws IOException
- */
- private void processValue(InputOutput io, int maskBit) throws IOException {
- switch (maskBit) {
- case AttrBackgroundPixmap:
- case AttrBackgroundPixel:
- case AttrBorderPixmap:
- case AttrBorderPixel:
- case AttrBackingPlanes:
- case AttrBackingPixel:
- case AttrEventMask:
- case AttrDoNotPropagateMask:
- case AttrColormap:
- case AttrCursor:
- _attributes[maskBit] = io.readInt();
- break;
- case AttrBitGravity:
- case AttrWinGravity:
- case AttrBackingStore:
- case AttrOverrideRedirect:
- case AttrSaveUnder:
- _attributes[maskBit] = io.readByte();
- io.readSkip(3);
- break;
- }
- }
-
- /**
- * Apply the attribute values to the window.
- *
- * @param client The remote client.
- * @param opcode The opcode being processed.
- * @param mask Bit mask of the attributes that have changed.
- * @return True if the values are all valid.
- * @throws IOException
- */
- private boolean applyValues(Client client, byte opcode, int mask) throws IOException {
- boolean ok = true;
-
- if ((mask & (1 << AttrBackgroundPixmap)) != 0) {
- int pmid = _attributes[AttrBackgroundPixmap];
-
- if (pmid == 0) { // None.
- _backgroundBitmap = null;
- _drawable.setBackgroundBitmap(null);
- } else if (pmid == 1) { // ParentRelative.
- _backgroundBitmap = _parent._backgroundBitmap;
- _attributes[AttrBackgroundPixel] = _parent._attributes[AttrBackgroundPixel];
- _drawable.setBackgroundBitmap(_backgroundBitmap);
- _drawable.setBackgroundColor(_attributes[AttrBackgroundPixel] | 0xff000000);
- } else {
- Resource r = _xServer.getResource(pmid);
-
- if (r != null && r.getType() == PIXMAP) {
- Pixmap p = (Pixmap) r;
- Drawable d = p.getDrawable();
-
- _backgroundBitmap = d.getBitmap();
- _drawable.setBackgroundBitmap(_backgroundBitmap);
- } else {
- ErrorCode.write(client, ErrorCode.Colormap, opcode, pmid);
- ok = false;
- }
- }
- }
-
- if ((mask & (1 << AttrBackgroundPixel)) != 0)
- _drawable.setBackgroundColor(_attributes[AttrBackgroundPixel] | 0xff000000);
-
- if ((mask & (1 << AttrColormap)) != 0) {
- int cid = _attributes[AttrColormap];
-
- if (cid != 0) {
- Resource r = _xServer.getResource(cid);
-
- if (r != null && r.getType() == COLORMAP) {
- _colormap = (Colormap) r;
- } else {
- ErrorCode.write(client, ErrorCode.Colormap, opcode, cid);
- ok = false;
- }
- } else if (_parent != null) {
- _colormap = _parent._colormap;
- }
- }
-
- if ((mask & (1 << AttrEventMask)) != 0) {
- _clientMasks.put(client, _attributes[AttrEventMask]);
-
- Set sc = _clientMasks.keySet();
-
- _eventMask = 0;
- for (Client c : sc){
- if (c == null) continue;
- _eventMask |= _clientMasks.get(c);
- }
- }
-
- if ((mask & (1 << AttrOverrideRedirect)) != 0)
- _overrideRedirect = (_attributes[AttrOverrideRedirect] == 1);
-
- if ((mask & (1 << AttrCursor)) != 0) {
- int cid = _attributes[AttrCursor];
-
- if (cid != 0) {
- Resource r = _xServer.getResource(cid);
-
- if (r != null && r.getType() == CURSOR) {
- _cursor = (Cursor) r;
- } else {
- ErrorCode.write(client, ErrorCode.Cursor, opcode, cid);
- ok = false;
- }
- } else {
- _cursor = null;
- }
- }
-
- return ok;
- }
-
- /**
- * Notify that the pointer has entered this window.
- *
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param detail 0=Ancestor, 1=Virtual, 2=Inferior, 3=Nonlinear,
- * 4=NonlinearVirtual.
- * @param toWindow Window containing pointer.
- * @param mode 0=Normal, 1=Grab, 2=Ungrab.
- */
- private void enterNotify(int x, int y, int detail, Window toWindow, int mode) {
- if (!_isMapped) return;
-
- Vector sc;
-
- if ((sc = getSelectingClients(EventCode.MaskEnterWindow)) == null) return;
-
- Window child = (toWindow._parent == this) ? toWindow : null;
- Window fw = _screen.getFocusWindow();
- boolean focus = false;
-
- if (fw != null) focus = (fw == this) || isAncestor(fw);
-
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendEnterNotify(c, _xServer.getTimestamp(), detail, _screen.getRootWindow(), this, child, x, y, x - _irect.left, y - _irect.top, _screen.getButtons(), mode, focus);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
-
- sc = getSelectingClients(EventCode.MaskKeymapState);
- if (sc != null) {
- Keyboard kb = _xServer.getKeyboard();
-
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendKeymapNotify(c, kb.getKeymap());
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
- }
-
- /**
- * Notify that the pointer has left this window.
- *
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param detail 0=Ancestor, 1=Virtual, 2=Inferior, 3=Nonlinear, 4=NonlinearVirtual.
- * @param fromWindow Window previously containing pointer.
- * @param mode 0=Normal, 1=Grab, 2=Ungrab.
- */
- private void leaveNotify(int x, int y, int detail, Window fromWindow, int mode) {
- if (!_isMapped) return;
-
- Vector sc;
-
- if ((sc = getSelectingClients(EventCode.MaskLeaveWindow)) == null) return;
-
- Window child = (fromWindow._parent == this) ? fromWindow : null;
- Window fw = _screen.getFocusWindow();
- boolean focus = false;
-
- if (fw != null) focus = (fw == this) || isAncestor(fw);
-
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendLeaveNotify(c, _xServer.getTimestamp(), detail, _screen.getRootWindow(), this, child, x, y, x - _irect.left, y - _irect.top, _screen.getButtons(), mode, focus);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- /**
- * Called when the pointer leaves this window and enters another.
- *
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param ew The window being entered.
- * @param mode 0=Normal, 1=Grab, 2=Ungrab.
- */
- public void leaveEnterNotify(int x, int y, Window ew, int mode) {
- if (ew.isInferior(this)) {
- leaveNotify(x, y, 0, this, mode);
-
- for (Window w = _parent; w != ew; w = w._parent)
- w.leaveNotify(x, y, 1, this, 0);
-
- ew.enterNotify(x, y, 2, ew, mode);
- } else if (isInferior(ew)) {
- leaveNotify(x, y, 2, this, mode);
-
- Stack stack = new Stack();
-
- for (Window w = ew._parent; w != this; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.enterNotify(x, y, 1, ew, mode);
- }
-
- ew.enterNotify(x, y, 0, ew, mode);
- } else {
- leaveNotify(x, y, 3, this, 0);
-
- Window lca = null;
- Stack stack = new Stack();
-
- for (Window w = _parent; w != ew; w = w._parent) {
- if (w.isInferior(ew)) {
- lca = w;
- break;
- } else {
- w.leaveNotify(x, y, 4, this, mode);
- }
- }
-
- for (Window w = ew._parent; w != lca; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.enterNotify(x, y, 4, ew, mode);
- }
-
- ew.enterNotify(x, y, 3, ew, mode);
- }
- }
-
- /**
- * Notify that this window has gained keyboard focus.
- *
- * @param detail 0=Ancestor, 1=Virtual, 2=Inferior, 3=Nonlinear,
- * 4=NonlinearVirtual, 5=Pointer, 6=PointerRoot, 7=None.
- * @param mode 0=Normal, 1=Grab, 2=Ungrab, 3=WhileGrabbed.
- */
- private void focusInNotify(int detail, int mode) {
- if (!_isMapped) return;
-
- Vector sc;
-
- if ((sc = getSelectingClients(EventCode.MaskFocusChange)) == null) return;
-
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendFocusIn(c, _xServer.getTimestamp(), detail, this, mode);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
-
- sc = getSelectingClients(EventCode.MaskKeymapState);
- if (sc != null) {
- Keyboard kb = _xServer.getKeyboard();
-
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendKeymapNotify(c, kb.getKeymap());
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
- }
-
- /**
- * Notify that this window has lost keyboard focus.
- *
- * @param detail 0=Ancestor, 1=Virtual, 2=Inferior, 3=Nonlinear,
- * 4=NonlinearVirtual, 5=Pointer, 6=PointerRoot, 7=None.
- * @param mode 0=Normal, 1=Grab, 2=Ungrab, 3=WhileGrabbed.
- */
- private void focusOutNotify(int detail, int mode) {
- if (!_isMapped) return;
-
- Vector sc;
-
- if ((sc = getSelectingClients(EventCode.MaskFocusChange)) == null) return;
-
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendFocusOut(c, _xServer.getTimestamp(), detail, this, mode);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- /**
- * Called when keyboard focus changes from one window to another.
- * Handles the FocusIn and FocusOut events.
- *
- * @param wlose The window that is losing focus.
- * @param wgain The window that is gaining focus.
- * @param wp The window containing the pointer.
- * @param wroot The root window.
- * @param mode 0=Normal, 1=Grab, 2=Ungrab, 3=WhileGrabbed.
- */
- public static void focusInOutNotify(Window wlose, Window wgain, Window wp, Window wroot, int mode) {
- if (wlose == wgain) return;
-
- if (wlose == null) {
- wroot.focusOutNotify(7, mode);
-
- if (wgain == wroot) {
- wroot.focusInNotify(6, mode);
-
- Stack stack = new Stack();
-
- for (Window w = wp; w != null; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(5, mode);
- }
- } else {
- Stack stack = new Stack();
-
- for (Window w = wgain._parent; w != null; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(4, mode);
- }
-
- wgain.focusInNotify(3, mode);
-
- if (wgain.isInferior(wp)) {
- for (Window w = wp; w != wgain; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(5, mode);
- }
- }
- }
- } else if (wlose == wroot) {
- for (Window w = wp; w != null; w = w._parent)
- w.focusOutNotify(5, mode);
-
- wroot.focusOutNotify(6, mode);
-
- if (wgain == null) {
- wroot.focusInNotify(7, mode);
- } else {
- Stack stack = new Stack();
-
- for (Window w = wgain._parent; w != null; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(4, mode);
- }
-
- wgain.focusInNotify(3, mode);
-
- if (wgain.isInferior(wp)) {
- for (Window w = wp; w != wgain; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(5, mode);
- }
- }
- }
- } else if (wgain == null) {
- if (wlose.isInferior(wp)) for (Window w = wp; w != wlose; w = w._parent)
- w.focusOutNotify(5, mode);
-
- wlose.focusOutNotify(3, mode);
- for (Window w = wlose._parent; w != null; w = w._parent)
- w.focusOutNotify(4, mode);
- wroot.focusInNotify(7, mode);
- } else if (wgain == wroot) {
- if (wlose.isInferior(wp)) for (Window w = wp; w != wlose; w = w._parent)
- w.focusOutNotify(5, mode);
-
- wlose.focusOutNotify(3, mode);
- for (Window w = wlose._parent; w != null; w = w._parent)
- w.focusOutNotify(4, mode);
- wroot.focusInNotify(6, mode);
-
- Stack stack = new Stack();
-
- for (Window w = wp; w != null; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(5, mode);
- }
- } else if (wgain.isInferior(wlose)) {
- wlose.focusOutNotify(0, mode);
-
- for (Window w = wlose._parent; w != wgain; w = w._parent)
- w.focusOutNotify(1, mode);
-
- wgain.focusInNotify(2, mode);
-
- if (wgain.isInferior(wp) && (wp != wlose && !wp.isInferior(wlose) && !wp.isAncestor(wlose))) {
- Stack stack = new Stack();
-
- for (Window w = wp; w != wgain; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(5, mode);
- }
- }
- } else if (wlose.isInferior(wgain)) {
- if (wlose.isInferior(wp) && (wp != wgain && !wp.isInferior(wgain) && !wp.isAncestor(wgain))) {
- for (Window w = wp; w != wlose; w = w._parent)
- w.focusOutNotify(5, mode);
- }
-
- wlose.focusOutNotify(2, mode);
-
- Stack stack = new Stack();
-
- for (Window w = wgain._parent; w != wlose; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(1, mode);
- }
-
- wgain.focusInNotify(0, mode);
- } else {
- if (wlose.isInferior(wp)) for (Window w = wp; w != wlose; w = w._parent)
- w.focusOutNotify(5, mode);
-
- wlose.focusOutNotify(3, 0);
-
- Window lca = null;
- Stack stack = new Stack();
-
- for (Window w = wlose._parent; w != wgain; w = w._parent) {
- if (w.isInferior(wgain)) {
- lca = w;
- break;
- } else {
- w.focusOutNotify(4, mode);
- }
- }
-
- for (Window w = wgain._parent; w != lca; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(4, mode);
- }
-
- wgain.focusInNotify(3, mode);
-
- if (wgain.isInferior(wp)) {
- for (Window w = wp; w != wgain; w = w._parent)
- stack.push(w);
-
- while (!stack.empty()) {
- Window w = stack.pop();
-
- w.focusInNotify(5, mode);
- }
- }
- }
- }
-
- /**
- * Called when a button is pressed or released in this window.
- *
- * @param pressed Whether the button was pressed or released.
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param button Button that was pressed/released.
- * @param grabClient Only send to this client if it isn't null.
- * @return The window it was sent to, or null if not sent.
- */
- public Window buttonNotify(boolean pressed, int x, int y, int button, int timestamp, Client grabClient) {
- Window evw = this;
- Window child = null;
- int mask = pressed ? EventCode.MaskButtonPress : EventCode.MaskButtonRelease;
- Vector sc;
-
- for (; ; ) {
- if (evw._isMapped) {
- sc = evw.getSelectingClients(mask);
- if (sc != null) break;
- }
-
- if (evw._parent == null) return null;
-
- if ((evw._attributes[AttrDoNotPropagateMask] & mask) != 0) return null;
-
- child = evw;
- evw = evw._parent;
- }
-
- Window sentWindow = null;
-
- for (Client c : sc) {
- if (c == null) continue;
- if (grabClient != null && grabClient != c) continue;
-
- try {
- if (pressed)
- EventCode.sendButtonPress(c, timestamp, button, _screen.getRootWindow(), evw, child, x, y, x - evw._irect.left, y - evw._irect.top, _screen.getButtons());
- else
- EventCode.sendButtonRelease(c, timestamp, button, _screen.getRootWindow(), evw, child, x, y, x - evw._irect.left, y - evw._irect.top, _screen.getButtons());
- sentWindow = evw;
- } catch (IOException e) {
- evw.removeSelectingClient(c);
- }
- }
-
- return sentWindow;
- }
-
- /**
- * Called when a button is pressed or released while grabbed by this
- * window.
- *
- * @param pressed Whether the button was pressed or released.
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param button Button that was pressed/released.
- * @param eventMask The events the window is interested in.
- * @param grabClient The grabbing client.
- * @param ownerEvents Owner-events flag.
- */
- public void grabButtonNotify(boolean pressed, int x, int y, int button, int eventMask, Client grabClient, boolean ownerEvents) {
- if (ownerEvents) {
- Window w = _screen.getRootWindow().windowAtPoint(x, y);
-
- if (w.buttonNotify(pressed, x, y, button, _xServer.getTimestamp(), grabClient) != null)
- return;
- }
-
- int mask = pressed ? EventCode.MaskButtonPress : EventCode.MaskButtonRelease;
-
- if ((eventMask & mask) == 0) return;
-
- try {
- if (pressed)
- EventCode.sendButtonPress(grabClient, _xServer.getTimestamp(), button, _screen.getRootWindow(), this, null, x, y, x - _irect.left, y - _irect.top, _screen.getButtons());
- else
- EventCode.sendButtonRelease(grabClient, _xServer.getTimestamp(), button, _screen.getRootWindow(), this, null, x, y, x - _irect.left, y - _irect.top, _screen.getButtons());
- } catch (IOException e) {
- removeSelectingClient(grabClient);
- }
- }
-
- /**
- * Called when a key is pressed or released in this window.
- *
- * @param pressed Whether the key was pressed or released.
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param keycode Keycode of the key.
- * @param grabClient Only notify this client if it isn't null.
- * @return True if an event is sent.
- */
- public boolean keyNotify(boolean pressed, int x, int y, int keycode, Client grabClient) {
- Window evw = this;
- Window child = null;
- int mask = pressed ? EventCode.MaskKeyPress : EventCode.MaskKeyRelease;
- Vector sc;
-
- for (; ; ) {
- if (evw._isMapped) {
- sc = evw.getSelectingClients(mask);
- if (sc != null) break;
- }
-
- if (evw._parent == null) return false;
-
- if ((evw._attributes[AttrDoNotPropagateMask] & mask) != 0) return false;
-
- child = evw;
- evw = evw._parent;
- }
-
- boolean sent = false;
-
- for (Client c : sc) {
- if (c == null) continue;
- if (grabClient != null && grabClient != c) continue;
-
- try {
- if (pressed)
- EventCode.sendKeyPress(c, _xServer.getTimestamp(), keycode, _screen.getRootWindow(), evw, child, x, y, x - evw._irect.left, y - evw._irect.top, _screen.getButtons());
- else
- EventCode.sendKeyRelease(c, _xServer.getTimestamp(), keycode, _screen.getRootWindow(), evw, child, x, y, x - evw._irect.left, y - evw._irect.top, _screen.getButtons());
- sent = true;
- } catch (IOException e) {
- evw.removeSelectingClient(c);
- }
- }
-
- return sent;
- }
-
- /**
- * Called when a key is pressed or released while grabbed by this window.
- *
- * @param pressed Whether the key was pressed or released.
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param keycode Keycode of the key.
- * @param grabClient The grabbing client.
- * @param ownerEvents Owner-events flag.
- */
- public void grabKeyNotify(boolean pressed, int x, int y, int keycode, Client grabClient, boolean ownerEvents) {
- if (ownerEvents) {
- Window w = _screen.getRootWindow().windowAtPoint(x, y);
-
- if (w.keyNotify(pressed, x, y, keycode, grabClient)) return;
- }
-
- try {
- if (pressed)
- EventCode.sendKeyPress(grabClient, _xServer.getTimestamp(), keycode, _screen.getRootWindow(), this, null, x, y, x - _irect.left, y - _irect.top, _screen.getButtons());
- else
- EventCode.sendKeyRelease(grabClient, _xServer.getTimestamp(), keycode, _screen.getRootWindow(), this, null, x, y, x - _irect.left, y - _irect.top, _screen.getButtons());
- } catch (IOException e) {
- removeSelectingClient(grabClient);
- }
- }
-
- /**
- * Return the event mask that would select on the buttons.
- *
- * @param buttonMask Currently pressed pointer buttons.
- * @return The event mask that would select on the buttons.
- */
- private int buttonEventMask(int buttonMask) {
- int mask = EventCode.MaskPointerMotion | EventCode.MaskPointerMotionHint;
-
- if ((buttonMask & 0x700) == 0) return mask;
-
- mask |= EventCode.MaskButtonMotion;
- if ((buttonMask & 0x100) != 0) mask |= EventCode.MaskButton1Motion;
- if ((buttonMask & 0x200) != 0) mask |= EventCode.MaskButton2Motion;
- if ((buttonMask & 0x400) != 0) mask |= EventCode.MaskButton3Motion;
-
- return mask;
- }
-
- /**
- * Called when the pointer moves within this window.
- *
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param buttonMask Currently pressed pointer buttons.
- * @param grabClient Only send notify this client if it isn't null.
- * @return True if an event is sent.
- */
- public boolean motionNotify(int x, int y, int buttonMask, Client grabClient) {
- Window evw = this;
- Window child = null;
- int mask = buttonEventMask(buttonMask);
- Vector sc;
-
- for (; ; ) {
- if (evw._isMapped) {
- sc = evw.getSelectingClients(mask);
- if (sc != null) break;
- }
-
- if (evw._parent == null) return false;
-
- if ((evw._attributes[AttrDoNotPropagateMask] & EventCode.MaskPointerMotion) != 0)
- return false;
-
- child = evw;
- evw = evw._parent;
- }
-
- boolean sent = false;
-
- for (Client c : sc) {
- if (c == null) continue;
- if (grabClient != null && grabClient != c) continue;
-
- int detail = 0; // Normal.
- int em = evw.getClientEventMask(c);
-
- if ((em & EventCode.MaskPointerMotionHint) != 0 && (em & EventCode.MaskPointerMotion) == 0)
- detail = 1; // Hint.
-
- try {
- EventCode.sendMotionNotify(c, _xServer.getTimestamp(), detail, _screen.getRootWindow(), evw, child, x, y, x - evw._irect.left, y - evw._irect.top, buttonMask);
- } catch (IOException e) {
- evw.removeSelectingClient(c);
- }
- }
-
- return sent;
- }
-
- /**
- * Called when the pointer moves while grabbed by this window.
- *
- * @param x Pointer X coordinate.
- * @param y Pointer Y coordinate.
- * @param buttonMask Currently pressed pointer buttons.
- * @param eventMask The events the window is interested in.
- * @param grabClient The grabbing client.
- * @param ownerEvents Owner-events flag.
- */
- public void grabMotionNotify(int x, int y, int buttonMask, int eventMask, Client grabClient, boolean ownerEvents) {
- if (ownerEvents) {
- Window w = _screen.getRootWindow().windowAtPoint(x, y);
-
- if (w.motionNotify(x, y, buttonMask, grabClient)) return;
- }
-
- int em = buttonEventMask(buttonMask) & eventMask;
-
- if (em != 0) {
- int detail = 0; // Normal.
-
- if ((em & EventCode.MaskPointerMotionHint) != 0 && (em & EventCode.MaskPointerMotion) == 0)
- detail = 1; // Hint.
-
- try {
- EventCode.sendMotionNotify(grabClient, _xServer.getTimestamp(), detail, _screen.getRootWindow(), this, null, x, y, x - _irect.left, y - _irect.top, buttonMask);
- } catch (IOException e) {
- removeSelectingClient(grabClient);
- }
- }
- }
-
- /**
- * Map the window.
- *
- * @param client The remote client.
- * @throws IOException
- */
- private void map(Client client) throws IOException {
- if (_isMapped) return;
-
- Vector sc;
-
- if (!_overrideRedirect) {
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureRedirect);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- if (c != client) {
- EventCode.sendMapRequest(c, _parent, this);
- return;
- }
- }
- }
- }
-
- _isMapped = true;
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendMapNotify(c, this, this, _overrideRedirect);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendMapNotify(c, _parent, this, _overrideRedirect);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- updateAffectedVisibility();
-
- if (!_exposed) {
- sc = getSelectingClients(EventCode.MaskExposure);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendExpose(c, this, 0, 0, _drawable.getWidth(), _drawable.getHeight(), 0);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
- _exposed = true;
- }
- }
-
- /**
- * Map the children of this window.
- *
- * @param client The remote client.
- * @throws IOException
- */
- private void mapSubwindows(Client client) throws IOException {
- for (Window w : _children) {
- w.map(client);
- w.mapSubwindows(client);
- }
- }
-
- /**
- * Unmap the window.
- *
- * @throws IOException
- */
- private void unmap() throws IOException {
- if (!_isMapped) return;
-
- _isMapped = false;
-
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendUnmapNotify(c, this, this, false);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendUnmapNotify(c, _parent, this, false);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- updateAffectedVisibility();
- _screen.revertFocus(this);
- }
-
- /**
- * Unmap the children of this window.
- *
- * @throws IOException
- */
- private void unmapSubwindows() throws IOException {
- for (Window w : _children) {
- w.unmap();
- w.unmapSubwindows();
- }
- }
-
- /**
- * Destroy the window and all its children.
- *
- * @param removeFromParent If true, remove it from its parent.
- * @throws IOException
- */
- private void destroy(boolean removeFromParent) throws IOException {
- if (_parent == null) // No effect on root window.
- return;
-
- _xServer.freeResource(_id);
- if (_isMapped) unmap();
-
- for (Window w : _children)
- w.destroy(false);
-
- _children.clear();
-
- if (removeFromParent) _parent._children.remove(this);
-
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendDestroyNotify(c, this, this);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendDestroyNotify(c, _parent, this);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- _drawable.getBitmap().recycle();
- }
-
- /**
- * Change the window's parent.
- *
- * @param client The remote client.
- * @param parent New parent.
- * @param x New X position relative to new parent.
- * @param y New Y position relative to new parent.
- * @throws IOException
- */
- private void reparent(Client client, Window parent, int x, int y) throws IOException {
- boolean mapped = _isMapped;
-
- if (mapped) unmap();
-
- Rect orig = new Rect(_orect);
- int dx = parent._irect.left + x - _orect.left;
- int dy = parent._irect.top + y - _orect.top;
-
- _orect.left += dx;
- _orect.top += dy;
- _orect.right += dx;
- _orect.bottom += dy;
- _irect.left += dx;
- _irect.top += dy;
- _irect.right += dx;
- _irect.bottom += dy;
-
- _parent._children.remove(this);
- parent._children.add(this);
-
- if (dx != 0 || dy != 0) for (Window w : _children)
- w.move(dx, dy, 0, 0);
-
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendReparentNotify(c, this, this, parent, x, y, _overrideRedirect);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendReparentNotify(c, _parent, this, parent, x, y, _overrideRedirect);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- sc = parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendReparentNotify(c, parent, this, parent, x, y, _overrideRedirect);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- _parent = parent;
- if (mapped) {
- map(client);
- if (!_inputOnly) _screen.postInvalidate(orig.left, orig.top, orig.right, orig.bottom);
- }
- }
-
- /**
- * Circulate occluded windows.
- *
- * @param client The remote client.
- * @param direction 0=RaiseLowest, 1=LowerHighest.
- * @return True if a window is restacked.
- * @throws IOException
- */
- private boolean circulate(Client client, int direction) throws IOException {
- Window sw = null;
-
- if (direction == 0) { // Raise lowest occluded.
- for (Window w : _children) {
- if (occludes(null, w)) {
- sw = w;
- break;
- }
- }
- } else { // Lower highest occluding.
- for (int i = _children.size() - 1; i >= 0; i--) {
- Window w = _children.elementAt(i);
-
- if (occludes(w, null)) {
- sw = w;
- break;
- }
- }
- }
-
- if (sw == null) return false;
-
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskSubstructureRedirect);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- if (c != client) {
- try {
- EventCode.sendCirculateRequest(c, this, sw, direction);
- return false;
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
- }
-
- if (direction == 0) {
- _children.remove(sw);
- _children.add(sw);
- } else {
- _children.remove(sw);
- _children.add(0, sw);
- }
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendCirculateNotify(c, this, sw, direction);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendCirculateNotify(c, _parent, sw, direction);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- updateAffectedVisibility();
-
- return true;
- }
-
- /**
- * Does the first window occlude the second?
- * If the first window is null, does any window occlude w2?
- * If the second window is null, is any window occluded by w1?
- *
- * @param w1 First window.
- * @param w2 Second window.
- * @return True if occlusion occurs.
- */
- private boolean occludes(Window w1, Window w2) {
- if (w1 == null) {
- if (w2 == null || !w2._isMapped) return false;
-
- // Does anything occlude w2?
- Rect r = w2._orect;
- boolean above = false;
-
- for (Window w : _children) {
- if (above) {
- if (w._isMapped && Rect.intersects(w._orect, r)) return true;
- } else {
- if (w == w2) above = true;
- }
- }
- } else {
- if (w2 == null) { // Does w1 occlude anything?
- if (!w1._isMapped) return false;
-
- Rect r = w1._orect;
-
- for (Window w : _children) {
- if (w == w1) return false;
- else if (w._isMapped && Rect.intersects(w._orect, r)) return true;
- }
- } else { // Does w1 occlude w2?
- if (!w1._isMapped || !w2._isMapped) return false;
- if (!Rect.intersects(w1._orect, w2._orect)) return false;
-
- return _children.indexOf(w1) > _children.indexOf(w2);
- }
- }
-
- return false;
- }
-
- /**
- * Move the window and its children.
- *
- * @param dx X distance to move.
- * @param dy Y distance to move.
- * @param dw The change in the parent's width.
- * @param dh The change in the parent's height.
- * @throws IOException
- */
- private void move(int dx, int dy, int dw, int dh) throws IOException {
- if (dw != 0 || dh != 0) {
- switch (_attributes[AttrWinGravity]) {
- case WinGravityUnmap:
- unmap();
- break;
- case WinGravityNorthWest:
- break; // No change.
- case WinGravityNorth:
- dx += dw / 2;
- break;
- case WinGravityNorthEast:
- dx += dw;
- break;
- case WinGravityWest:
- dy += dh / 2;
- break;
- case WinGravityCenter:
- dx += dw / 2;
- dy += dh / 2;
- break;
- case WinGravityEast:
- dx += dw;
- dy += dh / 2;
- break;
- case WinGravitySouthWest:
- dy += dh;
- break;
- case WinGravitySouth:
- dx += dw / 2;
- dy += dh;
- break;
- case WinGravitySouthEast:
- dx += dw;
- dy += dh;
- break;
- case WinGravityStatic:
- dx = 0;
- dy = 0;
- break;
- }
-
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendGravityNotify(c, this, this, _orect.left + dx - _parent._irect.left, _orect.top + dy - _parent._irect.top);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendGravityNotify(c, _parent, this, _orect.left + dx - _parent._irect.left, _orect.top + dy - _parent._irect.top);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
- }
-
- if (dx == 0 && dy == 0) return;
-
- _irect.left += dx;
- _irect.right += dx;
- _irect.top += dy;
- _irect.bottom += dy;
- _orect.left += dx;
- _orect.right += dx;
- _orect.top += dy;
- _orect.bottom += dy;
-
- for (Window w : _children)
- w.move(dx, dy, 0, 0);
- }
-
- /**
- * Process a ConfigureWindow request.
- *
- * @param client The remote client.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @return True if the window needs to be redrawn.
- * @throws IOException
- */
- private boolean processConfigureWindow(Client client, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- if (bytesRemaining < 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.ConfigureWindow, 0);
- return false;
- }
-
- int mask = io.readShort(); // Value mask.
- int n = Util.bitcount(mask);
-
- io.readSkip(2); // Unused.
- bytesRemaining -= 4;
- if (bytesRemaining != 4 * n) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.ConfigureWindow, 0);
- return false;
- } else if (_parent == null) { // No effect on root window.
- io.readSkip(bytesRemaining);
- return false;
- }
-
- int oldLeft = _irect.left;
- int oldTop = _irect.top;
- int oldWidth = _irect.right - _irect.left;
- int oldHeight = _irect.bottom - _irect.top;
- int oldX = _orect.left - _parent._irect.left;
- int oldY = _orect.top - _parent._irect.top;
- int width = oldWidth;
- int height = oldHeight;
- int x = oldX;
- int y = oldY;
- int borderWidth = _borderWidth;
- int stackMode = 0;
- boolean changed = false;
- Window sibling = null;
- Rect dirty = null;
-
- if ((mask & 0x01) != 0) {
- x = (short) io.readShort(); // X.
- io.readSkip(2); // Unused.
- }
- if ((mask & 0x02) != 0) {
- y = (short) io.readShort(); // Y.
- io.readSkip(2); // Unused.
- }
- if ((mask & 0x04) != 0) {
- width = (short) io.readShort(); // Width.
- io.readSkip(2); // Unused.
- }
- if ((mask & 0x08) != 0) {
- height = (short) io.readShort(); // Height.
- io.readSkip(2); // Unused.
- }
- if ((mask & 0x10) != 0) {
- borderWidth = (short) io.readShort(); // Border width.
- io.readSkip(2); // Unused.
- }
- if ((mask & 0x20) != 0) {
- int id = io.readInt(); // Sibling.
- Resource r = _xServer.getResource(id);
-
- if (r == null || r.getType() != WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, RequestCode.ConfigureWindow, id);
- io.readSkip(bytesRemaining);
- return false;
- } else {
- sibling = (Window) r;
- }
- }
- if ((mask & 0x40) != 0) {
- stackMode = io.readByte(); // Stack mode.
- io.readSkip(3); // Unused.
- }
-
- if (!_overrideRedirect) {
- Vector sc;
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureRedirect);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- if (c != client) {
- EventCode.sendConfigureRequest(c, stackMode, _parent, this, sibling, x, y, width, height, borderWidth, mask);
- return false;
- }
- }
- }
- }
-
- if (width != oldWidth || height != oldHeight) {
- if (width <= 0 || height <= 0) {
- ErrorCode.write(client, ErrorCode.Value, RequestCode.ConfigureWindow, 0);
- return false;
- }
-
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskResizeRedirect);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- if (c != client) {
- EventCode.sendResizeRequest(c, this, width, height);
- width = oldWidth;
- height = oldHeight;
- break;
- }
- }
- }
- }
-
- if (x != oldX || y != oldY || width != oldWidth || height != oldHeight || borderWidth != _borderWidth) {
- if (width != oldWidth || height != oldHeight) {
- try {
- _drawable = new Drawable(width, height, 32, _backgroundBitmap, _attributes[AttrBackgroundPixel] | 0xff000000);
- } catch (OutOfMemoryError e) {
- ErrorCode.write(client, ErrorCode.Alloc, RequestCode.ConfigureWindow, 0);
- return false;
- }
-
- _drawable.clear();
- _exposed = false;
- }
-
- dirty = new Rect(_orect);
- _borderWidth = borderWidth;
- _orect.left = _parent._irect.left + x;
- _orect.top = _parent._irect.top + y;
- _orect.right = _orect.left + width + 2 * borderWidth;
- _orect.bottom = _orect.top + height + 2 * borderWidth;
- _irect.left = _orect.left + borderWidth;
- _irect.top = _orect.top + borderWidth;
- _irect.right = _orect.right - borderWidth;
- _irect.bottom = _orect.bottom - borderWidth;
- changed = true;
- }
-
- if ((mask & 0x60) != 0) {
- if (sibling != null && sibling._parent != _parent) {
- ErrorCode.write(client, ErrorCode.Match, RequestCode.ConfigureWindow, 0);
- return false;
- }
-
- if (sibling == null) {
- switch (stackMode) {
- case 0: // Above.
- _parent._children.remove(this);
- _parent._children.add(this);
- changed = true;
- break;
- case 1: // Below.
- _parent._children.remove(this);
- _parent._children.add(0, this);
- changed = true;
- break;
- case 2: // TopIf.
- if (_parent.occludes(null, this)) {
- _parent._children.remove(this);
- _parent._children.add(this);
- changed = true;
- }
- break;
- case 3: // BottomIf.
- if (_parent.occludes(this, null)) {
- _parent._children.remove(this);
- _parent._children.add(0, this);
- changed = true;
- }
- break;
- case 4: // Opposite.
- if (_parent.occludes(null, this)) {
- _parent._children.remove(this);
- _parent._children.add(this);
- changed = true;
- } else if (_parent.occludes(this, null)) {
- _parent._children.remove(this);
- _parent._children.add(0, this);
- changed = true;
- }
- break;
- }
- } else {
- int pos;
-
- switch (stackMode) {
- case 0: // Above.
- _parent._children.remove(this);
- pos = _parent._children.indexOf(sibling);
- _parent._children.add(pos + 1, this);
- changed = true;
- break;
- case 1: // Below.
- _parent._children.remove(this);
- pos = _parent._children.indexOf(sibling);
- _parent._children.add(pos, this);
- changed = true;
- break;
- case 2: // TopIf.
- if (_parent.occludes(sibling, this)) {
- _parent._children.remove(this);
- _parent._children.add(this);
- changed = true;
- }
- break;
- case 3: // BottomIf.
- if (_parent.occludes(this, sibling)) {
- _parent._children.remove(this);
- _parent._children.add(0, this);
- changed = true;
- }
- break;
- case 4: // Opposite.
- if (_parent.occludes(sibling, this)) {
- _parent._children.remove(this);
- _parent._children.add(this);
- changed = true;
- } else if (_parent.occludes(this, sibling)) {
- _parent._children.remove(this);
- _parent._children.add(0, this);
- changed = true;
- }
- break;
- }
- }
- }
-
- if (changed) {
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskStructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- EventCode.sendConfigureNotify(c, this, this, null, x, y, width, height, _borderWidth, _overrideRedirect);
- }
- }
-
- sc = _parent.getSelectingClients(EventCode.MaskSubstructureNotify);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- EventCode.sendConfigureNotify(c, _parent, this, null, x, y, width, height, _borderWidth, _overrideRedirect);
- }
- }
-
- if (_irect.left != oldLeft || _irect.top != oldTop || width != oldWidth || height != oldHeight)
- for (Window w : _children)
- w.move(_irect.left - oldLeft, _irect.top - oldTop, width - oldWidth, height - oldHeight);
-
- updateAffectedVisibility();
- }
-
- if (!_exposed) {
- Vector sc;
-
- if ((sc = getSelectingClients(EventCode.MaskExposure)) != null) {
- for (Client c : sc) {
- if (c == null) continue;
- EventCode.sendExpose(c, this, 0, 0, _drawable.getWidth(), _drawable.getHeight(), 0);
- }
- }
- _exposed = true;
- }
-
- if (dirty != null && _isMapped && !_inputOnly)
- _screen.postInvalidate(dirty.left, dirty.top, dirty.right, dirty.bottom);
-
- return changed;
- }
-
- /**
- * Process an X request relating to this window.
- *
- * @param client The remote client.
- * @param opcode The request's opcode.
- * @param arg Optional first argument.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- @Override
- public void processRequest(Client client, byte opcode, byte arg, int bytesRemaining) throws IOException {
- boolean redraw = false;
- boolean updatePointer = false;
- InputOutput io = client.getInputOutput();
-
- switch (opcode) {
- case RequestCode.ChangeWindowAttributes:
- redraw = processWindowAttributes(client, RequestCode.ChangeWindowAttributes, bytesRemaining);
- updatePointer = true;
- break;
- case RequestCode.GetWindowAttributes:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int vid = _xServer.getRootVisual().getId();
- byte mapState = (byte) (_isMapped ? 0 : 2);
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 2);
- io.writeInt(3); // Reply length.
- io.writeInt(vid); // Visual.
- io.writeShort((short) (_inputOnly ? 2 : 1)); // Class.
- io.writeByte((byte) _attributes[AttrBitGravity]);
- io.writeByte((byte) _attributes[AttrWinGravity]);
- io.writeInt(_attributes[AttrBackingPlanes]);
- io.writeInt(_attributes[AttrBackingPixel]);
- io.writeByte((byte) _attributes[AttrSaveUnder]);
- io.writeByte((byte) 1); // Map is installed.
- io.writeByte(mapState); // Map-state.
- io.writeByte((byte) (_overrideRedirect ? 1 : 0));
- io.writeInt(_colormap.getId()); // Colormap.
- io.writeInt(_attributes[AttrEventMask]);
- io.writeInt(_attributes[AttrEventMask]);
- io.writeShort((short) _attributes[AttrDoNotPropagateMask]);
- io.writePadBytes(2); // Unused.
- }
- io.flush();
- }
- break;
- case RequestCode.DestroyWindow:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- destroy(true);
- redraw = true;
- updatePointer = true;
- }
- break;
- case RequestCode.DestroySubwindows:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- for (Window w : _children)
- w.destroy(false);
- _children.clear();
- redraw = true;
- updatePointer = true;
- }
- break;
- case RequestCode.ChangeSaveSet:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- // Do nothing.
- }
- break;
- case RequestCode.ReparentWindow:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int id = io.readInt(); // Parent.
- int x = (short) io.readShort(); // X.
- int y = (short) io.readShort(); // Y.
- Resource r = _xServer.getResource(id);
-
- if (r == null || r.getType() != WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, opcode, id);
- } else {
- reparent(client, (Window) r, x, y);
- redraw = true;
- updatePointer = true;
- }
- }
- break;
- case RequestCode.MapWindow:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- map(client);
- redraw = true;
- updatePointer = true;
- }
- break;
- case RequestCode.MapSubwindows:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- mapSubwindows(client);
- redraw = true;
- updatePointer = true;
- }
- break;
- case RequestCode.UnmapWindow:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- unmap();
- redraw = true;
- updatePointer = true;
- }
- break;
- case RequestCode.UnmapSubwindows:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- unmapSubwindows();
- redraw = true;
- updatePointer = true;
- }
- break;
- case RequestCode.ConfigureWindow:
- redraw = processConfigureWindow(client, bytesRemaining);
- updatePointer = true;
- break;
- case RequestCode.CirculateWindow:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- redraw = circulate(client, arg);
- updatePointer = true;
- }
- break;
- case RequestCode.GetGeometry:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int rid = _screen.getRootWindow().getId();
- byte depth = _xServer.getRootVisual().getDepth();
- int x, y;
- int width = _irect.right - _irect.left;
- int height = _irect.bottom - _irect.top;
-
- if (_parent == null) {
- x = _orect.left;
- y = _orect.top;
- } else {
- x = _orect.left - _parent._irect.left;
- y = _orect.top - _parent._irect.top;
- }
-
- synchronized (io) {
- Util.writeReplyHeader(client, depth);
- io.writeInt(0); // Reply length.
- io.writeInt(rid); // Root.
- io.writeShort((short) x); // X.
- io.writeShort((short) y); // Y.
- io.writeShort((short) width); // Width.
- io.writeShort((short) height); // Height.
- io.writeShort((short) _borderWidth); // Border wid.
- io.writePadBytes(10); // Unused.
- }
- io.flush();
- }
- break;
- case RequestCode.QueryTree:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int rid = _screen.getRootWindow().getId();
- int pid = (_parent == null) ? 0 : _parent.getId();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 0);
- io.writeInt(_children.size()); // Reply length.
- io.writeInt(rid); // Root.
- io.writeInt(pid); // Parent.
- // Number of children.
- io.writeShort((short) _children.size());
- io.writePadBytes(14); // Unused.
-
- for (Window w : _children)
- io.writeInt(w.getId());
- }
- io.flush();
- }
- break;
- case RequestCode.ChangeProperty:
- case RequestCode.GetProperty:
- case RequestCode.RotateProperties:
- Property.processRequest(_xServer, client, arg, opcode, bytesRemaining, this, _properties);
- break;
- case RequestCode.DeleteProperty:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int id = io.readInt(); // Property.
- Atom a = _xServer.getAtom(id);
-
- if (a == null) {
- ErrorCode.write(client, ErrorCode.Atom, opcode, id);
- } else if (_properties.containsKey(id)) {
- Vector sc = getSelectingClients(EventCode.MaskPropertyChange);
-
- _properties.remove(id);
- if (sc != null) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendPropertyNotify(c, this, a, _xServer.getTimestamp(), 1);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
- }
- }
- break;
- case RequestCode.ListProperties:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int n = _properties.size();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 0);
- io.writeInt(n); // Reply length.
- io.writeShort((short) n); // Num atoms.
- io.writePadBytes(22); // Unused.
-
- for (Property p : _properties.values())
- io.writeInt(p.getId());
- }
- io.flush();
- }
- break;
- case RequestCode.QueryPointer:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int rid = _screen.getRootWindow().getId();
- int rx = _screen.getPointerX();
- int ry = _screen.getPointerY();
- int mask = _screen.getButtons();
- int wx = rx - _irect.left;
- int wy = ry - _irect.top;
- Window w = windowAtPoint(rx, ry);
- int cid = 0;
-
- if (w._parent == this) cid = w.getId();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 1);
- io.writeInt(0); // Reply length.
- io.writeInt(rid); // Root.
- io.writeInt(cid); // Child.
- io.writeShort((short) rx); // Root X.
- io.writeShort((short) ry); // Root Y.
- io.writeShort((short) wx); // Win X.
- io.writeShort((short) wy); // Win Y.
- io.writeShort((short) mask); // Mask.
- io.writePadBytes(6); // Unused.
- }
- io.flush();
- }
- break;
- case RequestCode.GetMotionEvents:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int numEvents = 0; // Do nothing.
-
- io.readInt(); // Start time.
- io.readInt(); // Stop time.
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 0);
- io.writeInt(numEvents * 2); // Reply length.
- io.writeInt(numEvents); // Number of events.
- io.writePadBytes(20); // Unused.
- }
- io.flush();
- }
- break;
- case RequestCode.TranslateCoordinates:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int id = io.readInt(); // Destination window.
- int x = (short) io.readShort(); // Source X.
- int y = (short) io.readShort(); // Source Y.
- Resource r = _xServer.getResource(id);
-
- if (r == null || r.getType() != WINDOW) {
- ErrorCode.write(client, ErrorCode.Window, opcode, id);
- } else {
- Window w = (Window) r;
- int dx = _irect.left + x - w._irect.left;
- int dy = _irect.top + y - w._irect.top;
- int child = 0;
-
- for (Window c : w._children)
- if (c._isMapped && c._irect.contains(x, y)) child = c._id;
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 1);
- io.writeInt(0); // Reply length.
- io.writeInt(child); // Child.
- io.writeShort((short) dx); // Dest X.
- io.writeShort((short) dy); // Dest Y.
- io.writePadBytes(16); // Unused.
- }
- io.flush();
- }
- }
- break;
- case RequestCode.ClearArea:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int x = (short) io.readShort(); // Source X.
- int y = (short) io.readShort(); // Source Y.
- int width = io.readShort(); // Width.
- int height = io.readShort(); // Height.
-
- if (width == 0) width = _drawable.getWidth() - x;
- if (height == 0) height = _drawable.getHeight() - y;
- _drawable.clearArea(x, y, width, height);
- invalidate(x, y, width, height);
-
- if (arg == 1) {
- Vector sc;
-
- sc = getSelectingClients(EventCode.MaskExposure);
- if (sc != null) for (Client c : sc){
- if (c == null) continue;
- EventCode.sendExpose(c, this, x, y, width, height, 0);
- }
- }
- }
- break;
- case RequestCode.CopyArea:
- case RequestCode.CopyPlane:
- case RequestCode.PolyPoint:
- case RequestCode.PolyLine:
- case RequestCode.PolySegment:
- case RequestCode.PolyRectangle:
- case RequestCode.PolyArc:
- case RequestCode.FillPoly:
- case RequestCode.PolyFillRectangle:
- case RequestCode.PolyFillArc:
- case RequestCode.PutImage:
- case RequestCode.GetImage:
- case RequestCode.PolyText8:
- case RequestCode.PolyText16:
- case RequestCode.ImageText8:
- case RequestCode.ImageText16:
- case RequestCode.QueryBestSize:
- redraw = _drawable.processRequest(_xServer, client, _id, opcode, arg, bytesRemaining);
- break;
- case RequestCode.ListInstalledColormaps:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- _screen.writeInstalledColormaps(client);
- }
- break;
- default:
- if(opcode<0) {
- redraw = false;
- Extensions.processRequest(_xServer, client, opcode, arg, bytesRemaining);
- }
- else{
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Implementation, opcode, 0);
- }
- break;
- }
-
- if (redraw) {
- invalidate();
- if (updatePointer) _screen.updatePointer(0);
- }
- }
-
- /**
- * Calculate a window's visibility.
- *
- * @return The window's visibility.
- */
- private int calculateVisibility() {
- if (_inputOnly) return NotViewable;
-
- int result = Unobscured;
-
- for (Window aw = this; aw._parent != null; aw = aw._parent) {
- if (!_isMapped) return NotViewable; // All ancestors must be mapped.
-
- if (result == FullyObscured) continue; // Keep checking in case ancestor is unmapped.
-
- boolean above = false;
-
- for (Window w : aw._parent._children) {
- if (!w._isMapped) continue;
-
- if (above) {
- if (Rect.intersects(w._orect, _orect)) {
- if (w._orect.contains(_orect)) {
- result = FullyObscured;
- break;
- }
-
- result = PartiallyObscured;
- }
- } else if (w == aw) {
- above = true;
- }
- }
- }
-
- return result;
- }
-
- /**
- * Update the visibility of this window and its children.
- */
- private void updateVisibility() {
- Vector sc = getSelectingClients(EventCode.MaskVisibilityChange);
-
- if (sc != null) {
- int visibility = calculateVisibility();
-
- if (visibility != _visibility) {
- _visibility = visibility;
- if (visibility != NotViewable) {
- for (Client c : sc) {
- if (c == null) continue;
- try {
- EventCode.sendVisibilityNotify(c, this, visibility);
- } catch (IOException e) {
- removeSelectingClient(c);
- }
- }
- }
- }
- }
-
- for (Window w : _children)
- w.updateVisibility();
- }
-
- /**
- * Update the visibility of all the windows that might have been
- * affected by changes to this window.
- */
- private void updateAffectedVisibility() {
- if (_parent == null) {
- updateVisibility();
- return;
- }
-
- for (Window w : _parent._children) {
- w.updateVisibility();
- if (w == this) break;
- }
- }
-
- /**
- * Allows adding a new property to this window.
- * @param p property to add.
- */
- public void addProperty(Property p){
- _properties.put(p.getId(),p);
- }
-
- /**
- * Returns a property assigned to this window.
- * @param id Id of the property.
- * @return Property or null if not found.
- */
- public Property getProperty(int id) {
- return _properties.get(id);
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/XServer.java b/library/src/main/java/au/com/darkside/xserver/XServer.java
deleted file mode 100644
index 046c8f8..0000000
--- a/library/src/main/java/au/com/darkside/xserver/XServer.java
+++ /dev/null
@@ -1,963 +0,0 @@
-package au.com.darkside.xserver;
-
-import android.content.ComponentName;
-import android.content.Context;
-import android.content.Intent;
-import android.os.CountDownTimer;
-import android.util.DisplayMetrics;
-import android.util.Log;
-import android.view.WindowManager;
-
-import java.io.IOException;
-import java.net.InetAddress;
-import java.net.InetSocketAddress;
-import java.net.ServerSocket;
-import java.net.Socket;
-import java.util.Collection;
-import java.util.HashSet;
-import java.util.Hashtable;
-import java.util.Iterator;
-import java.util.Set;
-import java.util.Vector;
-
-import au.com.darkside.xserver.Xext.Extensions;
-import au.com.darkside.xserver.Xext.XShape;
-import au.com.darkside.xserver.Xext.XSync;
-
-/**
- * This class implements an X Windows server.
- *
- * @author Matthew Kwan
- */
-public class XServer {
-
- static public abstract class OnXSeverStartListener {
- public abstract void onStart();
- }
-
- public final short ProtocolMajorVersion = 11;
- public final short ProtocolMinorVersion = 0;
- public final String vendor = "Open source";
- public final int ReleaseNumber = 0;
-
- private final int _port;
- private final Context _context;
- private final String _windowManagerClass;
- private final Vector _formats;
- private final Hashtable _resources;
-
- private final Vector _clients;
- private final int _clientIdBits = 20;
- private final int _clientIdStep = (1 << _clientIdBits);
- private int _clientIdBase = _clientIdStep;
-
- private final Hashtable _atoms;
- private final Hashtable _atomNames;
- private int _maxAtomId = 0;
- private final Hashtable _selections;
-
- private final Keyboard _keyboard;
- private final Pointer _pointer;
- private final Font _defaultFont;
- private final Visual _rootVisual;
- private ScreenView _screen = null;
- private String[] _fontPath = null;
- private AcceptThread _acceptThread = null;
- private long _timestamp;
- private Client _grabClient;
-
- private int _screenSaverTimeout = 0;
- private int _screenSaverInterval = 0;
- private int _preferBlanking = 1;
- private int _allowExposures = 0;
- private long _screenSaverTime = 0;
- private CountDownTimer _screenSaverCountDownTimer = null;
-
- private boolean _accessControlEnabled = false;
- private final HashSet _accessControlHosts;
-
- private final Hashtable _extensions;
- private OnXSeverStartListener _onStartListener = null;
-
- /**
- * Constructor.
- *
- * @param c The application context.
- * @param port The port to listen on. Usually 6000.
- * @param windowManagerClass Window manager class name. Can be null.
- */
- public XServer(Context c, int port, String windowManagerClass) {
- _context = c;
- _port = port;
- _windowManagerClass = windowManagerClass;
- _formats = new Vector();
- _resources = new Hashtable();
- _clients = new Vector();
- _atoms = new Hashtable();
- _atomNames = new Hashtable();
- _selections = new Hashtable();
- _accessControlHosts = new HashSet();
-
- Extensions.Initialize();
- _extensions = new Hashtable();
- _extensions.put("Generic Event Extension", new Extension(Extensions.XGE, (byte) 0, (byte) 0));
- _extensions.put("BIG-REQUESTS", new Extension(Extensions.BigRequests, (byte) 0, (byte) 0));
- _extensions.put("SHAPE", new Extension(Extensions.Shape, XShape.EventBase, (byte) 0));
- //_extensions.put("SYNC", new Extension(Extensions.Sync, XSync.EventBase, XSync.ErrorBase));
- _extensions.put("XTEST", new Extension(Extensions.XTEST, (byte) 0, (byte) 0));
-
- _formats.add(new Format((byte) 32, (byte) 24, (byte) 8));
-
- _keyboard = new Keyboard();
- _pointer = new Pointer();
-
- _defaultFont = new Font(1, this, null, null);
- addResource(_defaultFont);
- addResource(new Cursor(2, this, null, (Font) null, (Font) null, 0, 1, 0xff000000, 0xffffffff));
-
- _screen = new ScreenView(_context, this, 3, pixelsPerMillimeter());
-
- Colormap cmap = new Colormap(4, this, null, _screen);
-
- cmap.setInstalled(true);
- addResource(cmap);
-
- _rootVisual = new Visual(1);
- Atom.registerPredefinedAtoms(this);
-
- _timestamp = System.currentTimeMillis();
- }
-
- public void setOnStartListener(OnXSeverStartListener l){
- _onStartListener = l;
- }
-
- /**
- * Start the thread that listens on the socket.
- * Also start the window manager if one is specified.
- *
- * @return True if the thread is started successfully.
- */
- public synchronized boolean start() {
- if (_acceptThread != null) return true; // Already running.
-
- try {
- _acceptThread = new AcceptThread(_port);
- _acceptThread.start();
- } catch (IOException e) {
- return false;
- }
-
- if (_windowManagerClass != null) {
- int idx = _windowManagerClass.lastIndexOf('.');
-
- if (idx > 0) {
- String pkg = _windowManagerClass.substring(0, idx);
- Intent intent = new Intent(Intent.ACTION_MAIN);
-
- intent.setComponent(new ComponentName(pkg, _windowManagerClass));
-
- try {
- if (_context.startService(intent) == null)
- Log.e("XServer", "Could not start " + _windowManagerClass);
- } catch (SecurityException e) {
- Log.e("XServer", "Could not start " + _windowManagerClass + ": " + e.getMessage());
- }
- }
- }
-
- resetScreenSaver();
-
- if(_onStartListener != null) _onStartListener.onStart();
-
- return true;
- }
-
- /**
- * Stop listening on the socket and terminate all clients.
- */
- public synchronized void stop() {
- if (_acceptThread != null) {
- _acceptThread.cancel();
- _acceptThread = null;
- }
-
- _grabClient = null;
- while (!_clients.isEmpty()) _clients.get(0).cancel();
- }
-
- /**
- * Reset the server.
- * This should be called when the last client disconnects with a
- * close-down mode of Destroy.
- */
- private void reset() {
- Iterator it = _resources.keySet().iterator();
- while (it.hasNext()) {
- Integer entry = it.next();
- if (entry > _clientIdStep) _resources.remove(entry);
- }
-
- _screen.removeNonDefaultColormaps();
-
- if (_atoms.size() != Atom.numPredefinedAtoms()) {
- _atoms.clear();
- _atomNames.clear();
- Atom.registerPredefinedAtoms(this);
- }
-
- _selections.clear();
- _timestamp = System.currentTimeMillis();
- }
-
- /**
- * Return the server's application context.
- *
- * @return The server's application context.
- */
- public Context getContext() {
- return _context;
- }
-
- /**
- * Return the internet address the server is listening on.
- *
- * @return The internet address the server is listening on.
- */
- public InetAddress getInetAddress() {
- if (_acceptThread == null) return null;
-
- return _acceptThread.getInetAddress();
- }
-
- /**
- * Return the number of milliseconds since the last reset.
- *
- * @return The number of milliseconds since the last reset.
- */
- public int getTimestamp() {
- long diff = System.currentTimeMillis() - _timestamp;
-
- if (diff <= 0) return 1;
-
- return (int) diff;
- }
-
- /**
- * Remove a client from the list of active clients.
- *
- * @param client The client to remove.
- */
- public void removeClient(Client client) {
- for (Selection sel : _selections.values())
- sel.clearClient(client);
-
- _clients.remove(client);
- if (_grabClient == client) _grabClient = null;
-
- if (client.getCloseDownMode() == Client.Destroy && _clients.size() == 0) reset();
- }
-
- /**
- * Disable all clients except this one.
- *
- * @param client The client issuing the grab.
- */
- public void grabServer(Client client) {
- _grabClient = client;
- }
-
- /**
- * End the server grab.
- *
- * @param client The client issuing the grab.
- */
- public void ungrabServer(Client client) {
- if (_grabClient == client) _grabClient = null;
- }
-
- /**
- * Return true if processing is allowed. This is only false if the
- * server has been grabbed by another client and the checking client
- * is not impervious to server grabs.
- *
- * @param client The client checking if processing is allowed.
- * @return True if processing is allowed for the client.
- */
- public boolean processingAllowed(Client client) {
- if (_grabClient == null || client.getImperviousToServerGrabs()) return true;
-
- return _grabClient == client;
- }
-
- /**
- * Get the X server's keyboard.
- *
- * @return The keyboard used by the X server.
- */
- public Keyboard getKeyboard() {
- return _keyboard;
- }
-
- /**
- * Get the X server's pointer.
- *
- * @return The pointer used by the X server.
- */
- public Pointer getPointer() {
- return _pointer;
- }
-
- /**
- * Get the server's font path.
- *
- * @return The server's font path.
- */
- public String[] getFontPath() {
- return _fontPath;
- }
-
- /**
- * Set the server's font path.
- *
- * @param path The new font path.
- */
- public void setFontPath(String[] path) {
- _fontPath = path;
- }
-
- /**
- * Return the screen attached to the display.
- *
- * @return The screen attached to the display.
- */
- public ScreenView getScreen() {
- return _screen;
- }
-
- /**
- * Return the number of pixels per millimeter on the display.
- *
- * @return The number of pixels per millimeter on the display.
- */
- private float pixelsPerMillimeter() {
- DisplayMetrics metrics = new DisplayMetrics();
- WindowManager wm = (WindowManager) _context.getSystemService(Context.WINDOW_SERVICE);
-
- wm.getDefaultDisplay().getMetrics(metrics);
- Font.setDpi((int) metrics.ydpi); // Use the value since we have it.
-
- return metrics.xdpi / 25.4f;
- }
-
- /**
- * Get the number of pixmap formats.
- *
- * @return The number of pixmap formats.
- */
- public int getNumFormats() {
- return _formats.size();
- }
-
- /**
- * Write details of all the pixmap formats.
- *
- * @param io The input/output stream.
- * @throws IOException
- */
- public void writeFormats(InputOutput io) throws IOException {
- for (Format f : _formats)
- f.write(io);
- }
-
- /**
- * Return the default font.
- *
- * @return The default font.
- */
- public Font getDefaultFont() {
- return _defaultFont;
- }
-
- /**
- * Return the root visual.
- *
- * @return The root visual.
- */
- public Visual getRootVisual() {
- return _rootVisual;
- }
-
- /**
- * Add an atom.
- *
- * @param a The atom to add.
- */
- public void addAtom(Atom a) {
- _atoms.put(a.getId(), a);
- _atomNames.put(a.getName(), a);
-
- if (a.getId() > _maxAtomId) _maxAtomId = a.getId();
- }
-
- /**
- * Return the atom with the specified ID.
- *
- * @param id The atom ID.
- * @return The specified atom, or null if it doesn't exist.
- */
- public Atom getAtom(int id) {
- if (!_atoms.containsKey(id)) // No such atom.
- return null;
-
- return _atoms.get(id);
- }
-
- /**
- * Return the atom with the specified name.
- *
- * @param name The atom's name.
- * @return The specified atom, or null if it doesn't exist.
- */
- public Atom findAtom(final String name) {
- if (!_atomNames.containsKey(name)) return null;
-
- return _atomNames.get(name);
- }
-
- /**
- * Does the atom with specified ID exist?
- *
- * @param id The atom ID.
- * @return True if an atom with the ID exists.
- */
- public boolean atomExists(int id) {
- return _atoms.containsKey(id);
- }
-
- /**
- * Get the ID of the next free atom.
- *
- * @return The ID of the next free atom.
- */
- public int nextFreeAtomId() {
- return ++_maxAtomId;
- }
-
- /**
- * Return the selection with the specified ID.
- *
- * @param id The selection ID.
- * @return The specified selection, or null if it doesn't exist.
- */
- public Selection getSelection(int id) {
- if (!_selections.containsKey(id)) // No such selection.
- return null;
-
- return _selections.get(id);
- }
-
- /**
- * Add a selection.
- *
- * @param sel The selection to add.
- */
- public void addSelection(Selection sel) {
- _selections.put(sel.getId(), sel);
- }
-
- /**
- * Add a resource.
- *
- * @param r The resource to add.
- */
- public void addResource(Resource r) {
- _resources.put(r.getId(), r);
- }
-
- /**
- * Return the resource with the specified ID.
- *
- * @param id The resource ID.
- * @return The specified resource, or null if it doesn't exist.
- */
- public Resource getResource(int id) {
- if (!resourceExists(id)) return null;
-
- return _resources.get(id);
- }
-
- /**
- * Does the resource with specified ID exist?
- *
- * @param id The resource ID.
- * @return True if a resource with the ID exists.
- */
- public boolean resourceExists(int id) {
- return _resources.containsKey(id);
- }
-
- /**
- * Free the resource with the specified ID.
- *
- * @param id The resource ID.
- */
- public void freeResource(int id) {
- _resources.remove(id);
- }
-
- /**
- * Get next free resource id.
- *
- * @param id The resource ID.
- */
- public int nextFreeResourceId() {
- int maxKey = 0;
- for (int cur : _resources.keySet())
- if (cur > maxKey)
- maxKey = cur;
- return maxKey++;
- }
-
- /**
- * If client is null, destroy the resources of all clients that have
- * terminated in RetainTemporary mode. Otherwise destroy all resources
- * associated with the client, which has terminated with mode
- * RetainPermanant or RetainTemporary.
- *
- * @param client The terminated client, or null.
- */
- public synchronized void destroyClientResources(Client client) {
- Collection rc = _resources.values();
- Vector dl = new Vector();
-
- if (client == null) {
- for (Resource r : rc) {
- Client c = r.getClient();
- boolean disconnected = (c == null || !c.isConnected());
-
- if (disconnected && r.getCloseDownMode() == Client.RetainTemporary) dl.add(r);
- }
- } else {
- for (Resource r : rc)
- if (r.getClient() == client) dl.add(r);
- }
-
- for (Resource r : dl)
- r.delete();
- }
-
- /**
- * Send a MappingNotify to all clients.
- *
- * @param request 0=Modifier, 1=Keyboard, 2=Pointer
- * @param firstKeycode First keycode in new keyboard map.
- * @param keycodeCount Number of keycodes in new keyboard map.
- */
- public void sendMappingNotify(int request, int firstKeycode, int keycodeCount) {
- for (Client c : _clients) {
- if (c == null) continue;
- try {
- EventCode.sendMappingNotify(c, request, firstKeycode, keycodeCount);
- } catch (IOException e) {
- }
- }
- }
-
- /**
- * Process a QueryExtension request.
- *
- * @param client The remote client.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public void processQueryExtensionRequest(Client client, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- if (bytesRemaining < 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.QueryExtension, 0);
- return;
- }
-
- int length = io.readShort(); // Length of name.
- int pad = -length & 3;
-
- io.readSkip(2); // Unused.
- bytesRemaining -= 4;
-
- if (bytesRemaining != length + pad) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.QueryExtension, 0);
- return;
- }
-
- byte[] bytes = new byte[length];
-
- io.readBytes(bytes, 0, length);
- io.readSkip(pad); // Unused.
-
- String s = new String(bytes);
- Extension e;
-
- if (_extensions.containsKey(s)) e = _extensions.get(s);
- else e = null;
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 0);
- io.writeInt(0); // Reply length.
-
- if (e == null) {
- io.writeByte((byte) 0); // Present. 0 = false.
- io.writeByte((byte) 0); // Major opcode.
- io.writeByte((byte) 0); // First event.
- io.writeByte((byte) 0); // First error.
- } else {
- io.writeByte((byte) 1); // Present. 1 = true.
- io.writeByte(e.majorOpcode); // Major opcode.
- io.writeByte(e.firstEvent); // First event.
- io.writeByte(e.firstError); // First error.
- }
-
- io.writePadBytes(20); // Unused.
- }
- io.flush();
- }
-
- /**
- * Write the list of extensions supported by the server.
- *
- * @param client The remote client.
- * @throws IOException
- */
- public void writeListExtensions(Client client) throws IOException {
- Set ss = _extensions.keySet();
- int length = 0;
-
- for (String s : ss)
- length += s.length() + 1;
-
- int pad = -length & 3;
- InputOutput io = client.getInputOutput();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) ss.size());
- io.writeInt((length + pad) / 4); // Reply length.
- io.writePadBytes(24); // Unused.
-
- for (String s : ss) {
- byte[] ba = s.getBytes();
-
- io.writeByte((byte) ba.length);
- io.writeBytes(ba, 0, ba.length);
- }
-
- io.writePadBytes(pad); // Unused.
- }
- io.flush();
- }
-
- /**
- * Process a ChangeHosts request.
- *
- * @param client The remote client.
- * @param mode Change mode. 0=Insert, 1=Delete.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public void processChangeHostsRequest(Client client, int mode, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- if (bytesRemaining < 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.ChangeHosts, 0);
- return;
- }
-
- int family = io.readByte(); // 0=Inet, 1=DECnet, 2=Chaos.
-
- io.readSkip(1); // Unused.
-
- int length = io.readShort(); // Length of address.
- int pad = -length & 3;
-
- bytesRemaining -= 4;
- if (bytesRemaining != length + pad) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, RequestCode.ChangeHosts, 0);
- return;
- }
-
- if (family != 0 || length != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Value, RequestCode.ChangeHosts, 0);
- return;
- }
-
- int address = 0;
-
- for (int i = 0; i < length; i++)
- address = (address << 8) | io.readByte();
-
- io.readSkip(pad); // Unused.
-
- if (mode == 0) _accessControlHosts.add(address);
- else _accessControlHosts.remove(address);
- }
-
- /**
- * Reply to a ListHosts request.
- *
- * @param client The remote client.
- * @throws IOException
- */
- public void writeListHosts(Client client) throws IOException {
- InputOutput io = client.getInputOutput();
- int n = _accessControlHosts.size();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) (_accessControlEnabled ? 1 : 0));
- io.writeInt(n * 2); // Reply length.
- io.writeShort((short) n); // Number of hosts.
- io.writePadBytes(22); // Unused.
-
- for (int addr : _accessControlHosts) {
- io.writeByte((byte) 0); // Family = Internet.
- io.writePadBytes(1); // Unused.
- io.writeShort((short) 4); // Length of address.
- io.writeByte((byte) ((addr >> 24) & 0xff));
- io.writeByte((byte) ((addr >> 16) & 0xff));
- io.writeByte((byte) ((addr >> 8) & 0xff));
- io.writeByte((byte) (addr & 0xff));
- }
- }
- io.flush();
- }
-
- /**
- * Enable/disable access control.
- *
- * @param enabled If true, enable access control.
- */
- public void setAccessControl(boolean enabled) {
- _accessControlEnabled = enabled;
- }
-
- /**
- * Get the list of hosts that are allowed to connect.
- * This can be modified.
- *
- * @return The set of addresses that are allowed to connect.
- */
- public HashSet getAccessControlHosts() {
- return _accessControlHosts;
- }
-
- /**
- * Is a client from the specified address allowed to connect?
- *
- * @param address The client's IP address, MSB format.
- * @return True if the client is allowed to exist.
- */
- private boolean isAccessAllowed(int address) {
- if (!_accessControlEnabled) return true;
-
- return _accessControlHosts.contains(address);
- }
-
- /**
- * Set the screen saver parameters.
- *
- * @param timeout Timeout period, in seconds. 0=disabled, -1=default.
- * @param interval Interval in seconds. 0=disabled, -1=default.
- * @param preferBlanking 0=No, 1=Yes, 2=Default.
- * @param allowExposures 0=No, 1=Yes, 2=Default.
- */
- public void setScreenSaver(int timeout, int interval, int preferBlanking, int allowExposures) {
- if (timeout == -1) _screenSaverTimeout = 0; // Default timeout.
- else _screenSaverTimeout = timeout;
-
- if (interval == -1) _screenSaverInterval = 0; // Default interval.
- else _screenSaverInterval = interval;
-
- _preferBlanking = preferBlanking;
- _allowExposures = allowExposures;
-
- resetScreenSaver();
- }
-
- /**
- * Called when we'd potentially want to blank the screen.
- */
- private void checkScreenBlank() {
- if (_screenSaverTimeout == 0) // Disabled.
- return;
-
- long offset = (_screenSaverTime + _screenSaverTimeout) * 1000 - System.currentTimeMillis() / 1000;
-
- if (offset < 1000) {
- _screen.blank(true);
- return;
- }
-
- _screenSaverCountDownTimer = new CountDownTimer(offset, offset + 1) {
- public void onTick(long millis) {
- }
-
- public void onFinish() {
- _screenSaverCountDownTimer = null;
- checkScreenBlank();
- }
- };
- _screenSaverCountDownTimer.start();
- }
-
- /**
- * Reset the screen saver timer.
- */
- public void resetScreenSaver() {
- long now = System.currentTimeMillis() / 1000;
-
- if (now == _screenSaverTime) return;
-
- _screenSaverTime = now;
- if (_screenSaverCountDownTimer == null) checkScreenBlank();
- }
-
- /**
- * Reply to GetScreenSaver request.
- *
- * @param client The remote client.
- * @throws IOException
- */
- public void writeScreenSaver(Client client) throws IOException {
- InputOutput io = client.getInputOutput();
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) 0);
- io.writeInt(0); // Reply length.
- io.writeShort((short) _screenSaverTimeout); // Timeout.
- io.writeShort((short) _screenSaverInterval); // Interval.
- io.writeByte((byte) _preferBlanking); // Prefer blanking.
- io.writeByte((byte) _allowExposures); // Allow exposures.
- io.writePadBytes(18); // Unused.
- }
- io.flush();
- }
-
- /**
- * This class holds details of an extension.
- *
- * @author Matthew Kwan
- */
- private class Extension {
- private final byte majorOpcode;
- private final byte firstEvent;
- private final byte firstError;
-
- /**
- * Constructor.
- *
- * @param pmajorOpcode Major opcode of the extension, or zero.
- * @param pfirstEvent Base event type code, or zero.
- * @param pfirstError Base error code, or zero.
- */
- public Extension(byte pmajorOpcode, byte pfirstEvent, byte pfirstError) {
- majorOpcode = pmajorOpcode;
- firstEvent = pfirstEvent;
- firstError = pfirstError;
- }
- }
-
- /**
- * This thread runs while listening for incoming connections.
- * It runs until it is cancelled.
- *
- * @author Matthew Kwan
- */
- private class AcceptThread extends Thread {
- private final ServerSocket _serverSocket;
-
- /**
- * Constructor.
- *
- * @param port The port to listen on.
- * @throws IOException
- */
- AcceptThread(int port) throws IOException {
- _serverSocket = new ServerSocket(port);
- }
-
- /**
- * Return the internet address that is accepting connections.
- * May be null.
- *
- * @return The internet address that is accepting connections.
- */
- public InetAddress getInetAddress() {
- return _serverSocket.getInetAddress();
- }
-
- /**
- * Run the thread.
- */
- public void run() {
- while (true) {
- Socket socket;
-
- try {
- // This is a blocking call and will only return on a
- // successful connection or an exception.
- socket = _serverSocket.accept();
- } catch (IOException e) {
- break;
- }
-
- int addr = 0;
- InetSocketAddress isa;
-
- isa = (InetSocketAddress) socket.getRemoteSocketAddress();
- if (isa != null) {
- InetAddress ia = isa.getAddress();
- byte[] ba = ia.getAddress();
-
- addr = ((ba[0] & 0xff) << 24) | ((ba[1] & 0xff) << 16) | ((ba[2] & 0xff) << 8) | (ba[3] & 0xff);
- }
-
- if (addr != 0 && !isAccessAllowed(addr)) {
- try {
- socket.close();
- } catch (IOException e) {
- }
- continue;
- }
-
- synchronized (this) {
- Client c;
-
- try {
- c = new Client(XServer.this, socket, _clientIdBase, _clientIdStep - 1);
- _clients.add(c);
- c.start();
- _clientIdBase += _clientIdStep;
- } catch (IOException e) {
- try {
- socket.close();
- } catch (IOException e2) {
- }
- }
- }
- }
- }
-
- /**
- * Cancel the thread.
- */
- public void cancel() {
- try {
- _serverSocket.close();
- } catch (IOException e) {
- }
- }
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/Xext/Counter.java b/library/src/main/java/au/com/darkside/xserver/Xext/Counter.java
deleted file mode 100644
index a0ab82a..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Xext/Counter.java
+++ /dev/null
@@ -1,26 +0,0 @@
-package au.com.darkside.xserver.Xext;
-
-public class Counter {
- public int COUNTER;
- public long value;
- public long firstTimestamp;
- public long firstTimestampNano;
-
- /**
- * Constructor.
- *
- * @param pmajorOpcode Major opcode of the extension, or zero.
- * @param pfirstEvent Base event type code, or zero.
- * @param pfirstError Base error code, or zero.
- */
- public Counter (int ID, long initVal) {
- COUNTER=ID;
- value=initVal;
- firstTimestamp=System.currentTimeMillis();
- firstTimestampNano=System.nanoTime();
- }
-
- public long getValue() {
- return System.currentTimeMillis()-firstTimestamp;
- }
-}
diff --git a/library/src/main/java/au/com/darkside/xserver/Xext/Extensions.java b/library/src/main/java/au/com/darkside/xserver/Xext/Extensions.java
deleted file mode 100644
index 97c7dbc..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Xext/Extensions.java
+++ /dev/null
@@ -1,88 +0,0 @@
-package au.com.darkside.xserver.Xext;
-
-import java.io.IOException;
-
-import au.com.darkside.xserver.Client;
-import au.com.darkside.xserver.ErrorCode;
-import au.com.darkside.xserver.InputOutput;
-import au.com.darkside.xserver.Util;
-import au.com.darkside.xserver.XServer;
-
-/**
- * This class handles requests relating to extensions.
- *
- * @author mkwan
- */
-public class Extensions {
- public static final byte XGE = -128;
- public static final byte XTEST = -124;
- public static final byte Sync = -127;
- public static final byte BigRequests = -126;
- public static final byte Shape = -125;
-
- static public void Initialize(){
- XSync.Initialize();
- }
-
- /**
- * Process a request relating to an X extension.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param opcode The request's opcode.
- * @param arg Optional first argument.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public static void processRequest(XServer xServer, Client client, byte opcode, byte arg, int bytesRemaining) throws IOException {
- InputOutput io = client.getInputOutput();
-
- switch (opcode) {
- case XGE:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else { // Assume arg == 0 (GEQueryVersion).
- short xgeMajor = (short) io.readShort();
- short xgeMinor = (short) io.readShort();
-
- synchronized (io) {
- Util.writeReplyHeader(client, arg);
- io.writeInt(0); // Reply length.
- io.writeShort(xgeMajor);
- io.writeShort(xgeMinor);
- io.writePadBytes(20);
- }
- io.flush();
- }
- break;
- case BigRequests:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else { // Assume arg == 0 (BigReqEnable).
- synchronized (io) {
- Util.writeReplyHeader(client, arg);
- io.writeInt(0);
- io.writeInt(Integer.MAX_VALUE);
- io.writePadBytes(20);
- }
- io.flush();
- }
- break;
- case Shape:
- XShape.processRequest(xServer, client, opcode, arg, bytesRemaining);
- break;
- case XTEST:
- XTest.processRequest(xServer, client, opcode, arg, bytesRemaining);
- break;
- case Sync:
- // XSync.processRequest(xServer, client, opcode, arg, bytesRemaining);
- // break;
- default:
- io.readSkip(bytesRemaining); // Not implemented.
- ErrorCode.write(client, ErrorCode.Implementation, opcode, 0);
- break;
- }
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/Xext/SystemCounter.java b/library/src/main/java/au/com/darkside/xserver/Xext/SystemCounter.java
deleted file mode 100644
index 7607e4b..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Xext/SystemCounter.java
+++ /dev/null
@@ -1,28 +0,0 @@
-package au.com.darkside.xserver.Xext;
-
-public class SystemCounter {
- public final byte resHi;
- public final byte resLo;
- public int COUNTER;
- public short nameLength;
- public byte[] name;
- public int nameLengthInt;
- public int padLen;
-
- /**
- * Constructor.
- *
- * @param pmajorOpcode Major opcode of the extension, or zero.
- * @param pfirstEvent Base event type code, or zero.
- * @param pfirstError Base error code, or zero.
- */
- public SystemCounter (int ID, int presHi, int presLo, String pname) {
- COUNTER=ID;
- resHi = (byte) presHi;
- resLo = (byte) presLo;
- name=pname.getBytes();
- nameLengthInt=name.length;
- nameLength=(short)nameLengthInt;
- padLen=2;
- }
-}
diff --git a/library/src/main/java/au/com/darkside/xserver/Xext/XShape.java b/library/src/main/java/au/com/darkside/xserver/Xext/XShape.java
deleted file mode 100644
index 28a4bcd..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Xext/XShape.java
+++ /dev/null
@@ -1,506 +0,0 @@
-package au.com.darkside.xserver.Xext;
-
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import android.graphics.Region;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import au.com.darkside.xserver.Client;
-import au.com.darkside.xserver.Drawable;
-import au.com.darkside.xserver.ErrorCode;
-import au.com.darkside.xserver.InputOutput;
-import au.com.darkside.xserver.Pixmap;
-import au.com.darkside.xserver.Util;
-import au.com.darkside.xserver.Window;
-import au.com.darkside.xserver.XServer;
-
-/**
- * Handles requests related to the X SHAPE extension.
- *
- * @author mkwan
- */
-public class XShape {
- public static final byte EventBase = 76;
- public static final byte KindBounding = 0;
- public static final byte KindClip = 1;
- public static final byte KindInput = 2;
-
- private static final byte ShapeQueryVersion = 0;
- private static final byte ShapeRectangles = 1;
- private static final byte ShapeMask = 2;
- private static final byte ShapeCombine = 3;
- private static final byte ShapeOffset = 4;
- private static final byte ShapeQueryExtents = 5;
- private static final byte ShapeSelectInput = 6;
- private static final byte ShapeInputSelected = 7;
- private static final byte ShapeGetRectangles = 8;
-
- private static final byte OpSet = 0;
- private static final byte OpUnion = 1;
- private static final byte OpIntersect = 2;
- private static final byte OpSubtract = 3;
- private static final byte OpInvert = 4;
-
- /**
- * Process a request relating to the X SHAPE extension.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param opcode The request's opcode.
- * @param arg Optional first argument.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public static void processRequest(XServer xServer, Client client, byte opcode, byte arg, int bytesRemaining) throws java.io.IOException {
- InputOutput io = client.getInputOutput();
-
- switch (arg) {
- case ShapeQueryVersion:
- if (bytesRemaining != 0) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- synchronized (io) {
- Util.writeReplyHeader(client, arg);
- io.writeInt(0); // Reply length.
- io.writeShort((short) 1); // Shape major.
- io.writeShort((short) 1); // Shape minor.
- io.writePadBytes(20);
- }
- io.flush();
- }
- break;
- case ShapeRectangles:
- if (bytesRemaining < 12) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- byte shapeOp = (byte) io.readByte();
- byte shapeKind = (byte) io.readByte();
-
- io.readByte(); // Ordering.
- io.readSkip(1);
-
- int wid = io.readInt();
- int x = io.readShort();
- int y = io.readShort();
- Window w = (Window) xServer.getResource(wid);
-
- bytesRemaining -= 12;
-
- int nr = bytesRemaining / 8;
- Region r = (nr == 0) ? null : new Region();
-
- for (int i = 0; i < nr; i++) {
- int rx = io.readShort();
- int ry = io.readShort();
- int rw = io.readShort();
- int rh = io.readShort();
-
- r.op(new Rect(rx, ry, rx + rw, ry + rh), Region.Op.UNION);
- bytesRemaining -= 8;
- }
-
- if (bytesRemaining != 0) // Oops!
- io.readSkip(bytesRemaining);
-
- regionOperate(w, shapeKind, r, shapeOp, x, y);
- if (shapeKind != KindInput && w.isViewable()) w.invalidate();
- }
- break;
- case ShapeMask:
- if (bytesRemaining != 16) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- byte shapeOp = (byte) io.readByte();
- byte shapeKind = (byte) io.readByte();
-
- io.readSkip(2);
-
- int wid = io.readInt();
- int x = io.readShort();
- int y = io.readShort();
- int pid = io.readInt(); // Pixmap ID.
- Window w = (Window) xServer.getResource(wid);
- Pixmap p = (pid == 0) ? null : (Pixmap) xServer.getResource(pid);
- Region r = (p == null) ? null : createRegion(p);
-
- regionOperate(w, shapeKind, r, shapeOp, x, y);
- if (shapeKind != KindInput && w.isViewable()) w.invalidate();
- }
- break;
- case ShapeCombine:
- if (bytesRemaining != 16) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- byte shapeOp = (byte) io.readByte();
- byte dstKind = (byte) io.readByte();
- byte srcKind = (byte) io.readByte();
-
- io.readSkip(1);
-
- int dwid = io.readInt();
- int x = io.readShort();
- int y = io.readShort();
- int swid = io.readInt();
- Window sw = (Window) xServer.getResource(swid);
- Window dw = (Window) xServer.getResource(dwid);
- Region sr = sw.getShapeRegion(srcKind);
- Rect irect = sw.getIRect();
-
- x -= irect.left; // Make region coordinates relative.
- y -= irect.top;
-
- regionOperate(dw, dstKind, sr, shapeOp, x, y);
- if (dstKind != KindInput && dw.isViewable()) dw.invalidate();
- }
- break;
- case ShapeOffset:
- if (bytesRemaining != 12) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- byte shapeKind = (byte) io.readByte();
-
- io.readSkip(3);
-
- int wid = io.readInt();
- int x = io.readShort();
- int y = io.readShort();
- Window w = (Window) xServer.getResource(wid);
- Region r = w.getShapeRegion(shapeKind);
-
- if (r != null && (x != 0 || y != 0)) {
- r.translate(x, y);
- w.sendShapeNotify(shapeKind);
- if (shapeKind != KindInput && w.isViewable()) w.invalidate();
- }
- }
- break;
- case ShapeQueryExtents:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- int wid = io.readInt();
- Window w = (Window) xServer.getResource(wid);
- boolean bs = w.isBoundingShaped();
- boolean cs = w.isClipShaped();
- Rect orect;
- Rect irect;
-
- if (bs) orect = w.getShapeRegion(KindBounding).getBounds();
- else orect = w.getORect();
-
- if (cs) irect = w.getShapeRegion(KindClip).getBounds();
- else irect = w.getIRect();
-
- synchronized (io) {
- Util.writeReplyHeader(client, arg);
- io.writeInt(0);
- io.writeByte((byte) (bs ? 1 : 0)); // Bounding shaped?
- io.writeByte((byte) (cs ? 1 : 0)); // Clip shaped?
- io.writePadBytes(2);
- io.writeShort((short) orect.left);
- io.writeShort((short) orect.top);
- io.writeShort((short) orect.width());
- io.writeShort((short) orect.height());
- io.writeShort((short) irect.left);
- io.writeShort((short) irect.top);
- io.writeShort((short) irect.width());
- io.writeShort((short) irect.height());
- io.writePadBytes(4);
- }
- io.flush();
- }
- break;
- case ShapeSelectInput:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- int wid = io.readInt();
- boolean enable = (io.readByte() == 1);
-
- io.readSkip(3);
-
- Window w = (Window) xServer.getResource(wid);
-
- if (enable) w.addShapeSelectInput(client);
- else w.removeShapeSelectInput(client);
- }
- break;
- case ShapeInputSelected:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- int wid = io.readInt();
- Window w = (Window) xServer.getResource(wid);
- boolean enabled = w.shapeSelectInputEnabled(client);
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) (enabled ? 1 : 0));
- io.writeInt(0); // Reply length.
- io.writePadBytes(24);
- }
- io.flush();
- }
- break;
- case ShapeGetRectangles:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- int wid = io.readInt();
- byte shapeKind = (byte) io.readByte();
-
- io.readSkip(3);
-
- Window w = (Window) xServer.getResource(wid);
- Region r = w.getShapeRegion(shapeKind);
- Rect irect = w.getIRect();
- byte ordering = 0; // Unsorted.
- List rectangles = rectanglesFromRegion(r);
- int nr = rectangles.size();
-
- synchronized (io) {
- Util.writeReplyHeader(client, ordering);
- io.writeInt(2 * nr); // Reply length.
- io.writeInt(nr);
- io.writePadBytes(20);
-
- for (Rect rect : rectangles) {
- io.writeShort((short) (rect.left - irect.left));
- io.writeShort((short) (rect.top - irect.top));
- io.writeShort((short) rect.width());
- io.writeShort((short) rect.height());
- }
- }
-
- io.flush();
- }
- break;
- default:
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Implementation, opcode, 0);
- break;
- }
- }
-
- /**
- * Carry out a shape operation on a region.
- *
- * @param w The destination window to operate on.
- * @param shapeKind The type of shape in the destination window.
- * @param sr Source region.
- * @param shapeOp Operation to carry out on the regions.
- * @param x X offset to apply to the source region.
- * @param y Y offset to apply to the source region.
- */
- private static void regionOperate(Window w, byte shapeKind, Region sr, byte shapeOp, int x, int y) {
- if (sr != null) { // Apply (x, y) offset.
- Region r = new Region();
- Rect irect = w.getIRect();
-
- sr.translate(x + irect.left, y + irect.top, r);
- sr = r;
- }
-
- Region dr = w.getShapeRegion(shapeKind);
-
- switch (shapeOp) {
- case OpSet:
- break;
- case OpUnion:
- if (sr == null || dr == null) sr = null;
- else sr.op(dr, Region.Op.UNION);
- break;
- case OpIntersect:
- if (sr == null) sr = dr;
- else if (dr != null) sr.op(dr, Region.Op.INTERSECT);
- break;
- case OpSubtract: // Subtract source region from dest region.
- if (sr == null) sr = new Region(); // Empty region.
- else if (dr == null) sr.op(w.getORect(), Region.Op.DIFFERENCE);
- else sr.op(dr, Region.Op.DIFFERENCE);
- break;
- case OpInvert: // Subtract dest region from source region.
- if (dr == null) {
- sr = new Region(); // Empty region.
- } else if (sr == null) {
- sr = new Region(w.getORect());
- sr.op(dr, Region.Op.REVERSE_DIFFERENCE);
- } else {
- sr.op(dr, Region.Op.REVERSE_DIFFERENCE);
- }
- break;
- default:
- return;
- }
-
- w.setShapeRegion(shapeKind, sr);
- w.sendShapeNotify(shapeKind);
- }
-
- /**
- * Return a list of rectangles that when combined make up the region.
- *
- * @param r The region.
- * @return
- */
- private static List rectanglesFromRegion(Region r) {
- ArrayList rl = new ArrayList();
-
- if (r != null && !r.isEmpty()) {
- if (r.isRect()) rl.add(r.getBounds());
- else extractRectangles(r, r.getBounds(), rl);
- }
-
- return rl;
- }
-
- /**
- * Recursively break the region contained in the rectangle into
- * rectangles entirely contained in the rectangle.
- *
- * @param r Region being broken into rectangles.
- * @param rect Part of the region being analyzed..
- * @param rl Return list of rectangles.
- */
- private static void extractRectangles(Region r, Rect rect, ArrayList rl) {
- int rs = regionRectIntersection(r, rect);
-
- if (rs == 0) // No intersection with rect.
- return;
-
- if (rs == 1) { // Full intersection with rect.
- rl.add(rect);
- return;
- }
-
- int rw = rect.width();
- int rh = rect.height();
-
- if (rw > rh) { // Split the rectangle horizontally.
- int cx = rect.left + rw / 2;
-
- extractRectangles(r, new Rect(rect.left, rect.top, cx, rect.bottom), rl);
- extractRectangles(r, new Rect(cx, rect.top, rect.right, rect.bottom), rl);
- } else { // Split it vertically.
- int cy = rect.top + rh / 2;
-
- extractRectangles(r, new Rect(rect.left, rect.top, rect.right, cy), rl);
- extractRectangles(r, new Rect(rect.left, cy, rect.right, rect.bottom), rl);
- }
- }
-
- /**
- * Check how a region intersects with a rectangle.
- *
- * @param r The region.
- * @param rect The rectangle.
- * @return 0 = no overlap; 1 = full overlap; -1 = partial overlap.
- */
- private static int regionRectIntersection(final Region r, final Rect rect) {
- if (r.quickReject(rect)) return 0;
-
- int icount = 0;
- int ocount = 0;
-
- for (int y = rect.top; y < rect.bottom; y++) {
- for (int x = rect.left; x < rect.right; x++)
- if (r.contains(x, y)) icount++;
- else ocount++;
-
- if (icount > 0 && ocount > 0) return -1;
- }
-
- if (icount == 0) return 0;
- else if (ocount == 0) return 1;
-
- return -1;
- }
-
- /**
- * Create a region using the non-zero pixels in the pixmap.
- *
- * @param p The pixmap.
- * @return A region equivalent to the non-zero pixels.
- */
- private static Region createRegion(Pixmap p) {
- Drawable d = p.getDrawable();
- Region r = new Region();
-
- extractRegion(r, d.getBitmap(), new Rect(0, 0, d.getWidth(), d.getHeight()));
-
- return r;
- }
-
- /**
- * Recursively break the image contained in the rectangle into
- * rectangles containing non-zero pixels.
- *
- * @param region Returned region.
- * @param bitmap Bitmap where the pixels appear.
- * @param rect Rectangle containing the pixels.
- */
- private static void extractRegion(Region region, Bitmap bitmap, Rect rect) {
- int nzp = checkNonZeroPixels(bitmap, rect);
-
- if (nzp == 1) // Empty.
- return;
-
- int rw = rect.width();
- int rh = rect.height();
-
- if (nzp == 2) { // All non-zero. We have a rectangle.
- region.op(rect, Region.Op.UNION);
- return;
- }
-
- if (rw > rh) { // Split the rectangle horizontally.
- int cx = rect.left + rw / 2;
-
- extractRegion(region, bitmap, new Rect(rect.left, rect.top, cx, rect.bottom));
- extractRegion(region, bitmap, new Rect(cx, rect.top, rect.right, rect.bottom));
- } else { // Split it vertically.
- int cy = rect.top + rh / 2;
-
- extractRegion(region, bitmap, new Rect(rect.left, rect.top, rect.right, cy));
- extractRegion(region, bitmap, new Rect(rect.left, cy, rect.right, rect.bottom));
- }
- }
-
- /**
- * Check the number of non-zero pixels contained in the rectangle.
- * Return a bit mask indicating whether all the pixels are non-zero,
- * none of them, or a mix.
- *
- * @param bitmap The bitmap containing the pixels.
- * @param rect The rectangle.
- * @return 1 = no pixels set; 2 = all pixels set; 0 = some pixels set
- */
- private static int checkNonZeroPixels(Bitmap bitmap, Rect rect) {
- final int width = rect.width();
- final int height = rect.height();
- int[] pixels = new int[width];
- int mask = 3;
-
- for (int i = 0; i < height; i++) {
- bitmap.getPixels(pixels, 0, width, rect.left, rect.top + i, width, 1);
-
- for (int p : pixels) {
- mask &= (p != 0xff000000) ? 2 : 1;
- if (mask == 0) return 0;
- }
- }
-
- return mask;
- }
-}
\ No newline at end of file
diff --git a/library/src/main/java/au/com/darkside/xserver/Xext/XSync.java b/library/src/main/java/au/com/darkside/xserver/Xext/XSync.java
deleted file mode 100644
index 20d027d..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Xext/XSync.java
+++ /dev/null
@@ -1,143 +0,0 @@
-package au.com.darkside.xserver.Xext;
-
-import java.util.Hashtable;
-
-import au.com.darkside.xserver.XServer;
-import au.com.darkside.xserver.Client;
-import au.com.darkside.xserver.InputOutput;
-import au.com.darkside.xserver.Util;
-import au.com.darkside.xserver.ErrorCode;
-
-/**
- * Handles requests related to the X SYNC extension.
- */
-public class XSync {
- private static int syncMajor = -1;
- private static int syncMinor;
- private static final Hashtable _systemCounters = new Hashtable();
- private static final Hashtable _counters = new Hashtable();
-
- public static final byte SYNC_INIT = 0;
- public static final byte SYNC_LIST = 1;
- public static final byte SYNC_CREATE = 2;
- public static final byte SYNC_DESTROY = 3;
- public static final byte EventBase = 95;
- public static final byte ErrorBase = (byte)154;
-
- static public void Initialize() {
- _systemCounters.put("dummy", new SystemCounter (1,4, 0,"dummy"));
- _systemCounters.put("SERVERTIME", new SystemCounter (3,6,7,"SERVERTIME"));
- }
-
- /**
- * Process a request relating to the X SYNC extension.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param opcode The request's opcode.
- * @param arg Optional first argument.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- static public void processRequest(XServer xServer, Client client, byte opcode, byte arg, int bytesRemaining) throws java.io.IOException {
- InputOutput io=client.getInputOutput();
- switch(arg) {
- case SYNC_INIT:
- if (bytesRemaining < 2) {
- io.readSkip (bytesRemaining);
- ErrorCode.write (client, ErrorCode.Length, opcode, 0);
- } else {
- syncMajor=io.readByte();
- syncMinor=io.readByte();
- bytesRemaining-=2;
- io.readSkip (bytesRemaining);
- synchronized(io) {
- Util.writeReplyHeader(client, arg);
- io.writeInt (0); // Reply length.
- io.writeByte((byte)syncMajor);
- io.writeByte((byte)syncMinor);
- io.writePadBytes(22);
- }
- io.flush ();
- }
- break;
- case SYNC_LIST:
- int n = _systemCounters.size();//number of counters
- int length = 0;
- for(String key : _systemCounters.keySet()) {
- int temp=(key.length()+2)%4;
- if(temp==0)
- temp=4;
- length+=14+key.length()+(4-temp);
- }
- int len=length%32;
- length/=32;
- if(len>0)
- length++;
- else
- len=32;
- length*=8;
- synchronized(io) {
- Util.writeReplyHeader(client, arg);
- io.writeInt (length); // Reply length.
- io.writeInt (n); // List length.
- io.writePadBytes(20); //unused
- for(SystemCounter count : _systemCounters.values()) {
- /* 4 COUNTER counter
- 8 INT64 resolution
- 2 n length of name in bytes
- n STRING8 name
- p pad,p=pad(n+2) */
- io.writeInt(count.COUNTER);
- io.writeInt(count.resLo);
- io.writeInt(count.resHi);
- io.writeShort(count.nameLength);
- io.writeBytes(count.name,0,count.name.length);
- int pad=(count.name.length+2)%4;
- if(pad==0)
- pad=4;
- io.writePadBytes(4-pad);
- }
- io.writePadBytes(32-(len));
- }
- io.flush();
- break;
- case SYNC_CREATE:
- if (bytesRemaining != 12) {
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Length, opcode, 0);
- } else {
- int ID=io.readInt();
- long initVal=io.readLong();
- bytesRemaining-=12;
- _counters.put(ID, new Counter(ID,initVal));
- }
- break;
- case SYNC_DESTROY:
- if (bytesRemaining != 4) {
- io.readSkip (bytesRemaining);
- ErrorCode.write (client, ErrorCode.Length, opcode, 0);
- } else {
- int ID=io.readInt();
- bytesRemaining-=4;
- Counter count=_counters.remove(ID);
- if(count!=null) {
- synchronized(io) {
- Util.writeReplyHeader(client, arg);
- io.writeInt(0);
- io.writeLong(count.getValue());
- io.writePadBytes(16);
- }
- io.flush();
- }
- else {
- ErrorCode.writeWithMinorOpcode(client, ErrorBase, arg, opcode, ID);
- }
- }
- break;
- default:
- io.readSkip(bytesRemaining); // Not implemented.
- ErrorCode.write(client, ErrorCode.Implementation, opcode, 0);
- break;
- }
- }}
diff --git a/library/src/main/java/au/com/darkside/xserver/Xext/XTest.java b/library/src/main/java/au/com/darkside/xserver/Xext/XTest.java
deleted file mode 100644
index bcc78cc..0000000
--- a/library/src/main/java/au/com/darkside/xserver/Xext/XTest.java
+++ /dev/null
@@ -1,211 +0,0 @@
-package au.com.darkside.xserver.Xext;
-
-import java.io.IOException;
-
-import au.com.darkside.xserver.Client;
-import au.com.darkside.xserver.Cursor;
-import au.com.darkside.xserver.ErrorCode;
-import au.com.darkside.xserver.InputOutput;
-import au.com.darkside.xserver.Resource;
-import au.com.darkside.xserver.ScreenView;
-import au.com.darkside.xserver.Util;
-import au.com.darkside.xserver.Window;
-import au.com.darkside.xserver.XServer;
-
-/**
- * Handles requests related to the XTEST extension.
- *
- * @author mkwan
- */
-public class XTest {
- private static final byte XTestGetVersion = 0;
- private static final byte XTestCompareCursor = 1;
- private static final byte XTestFakeInput = 2;
- private static final byte XTestGrabControl = 3;
-
- private static final byte KeyPress = 2;
- private static final byte KeyRelease = 3;
- private static final byte ButtonPress = 4;
- private static final byte ButtonRelease = 5;
- private static final byte MotionNotify = 6;
-
- /**
- * Process a request relating to the X XTEST extension.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param opcode The request's opcode.
- * @param arg Optional first argument.
- * @param bytesRemaining Bytes yet to be read in the request.
- * @throws IOException
- */
- public static void processRequest(XServer xServer, Client client, byte opcode, byte arg, int bytesRemaining) throws java.io.IOException {
- InputOutput io = client.getInputOutput();
-
- switch (arg) {
- case XTestGetVersion:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- io.readSkip(4); // Skip client major/minor version.
-
- final byte serverMajorVersion = 2;
- final int serverMinorVersion = 1;
-
- synchronized (io) {
- Util.writeReplyHeader(client, serverMajorVersion);
- io.writeInt(0); // Reply length.
- io.writeShort((short) serverMinorVersion);
- io.writePadBytes(22);
- }
- io.flush();
- }
- break;
- case XTestCompareCursor:
- if (bytesRemaining != 8) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- int wid = io.readInt();
- int cid = io.readInt();
- Resource r = xServer.getResource(wid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Window, arg, opcode, wid);
- return;
- }
-
- Window w = (Window) r;
- Cursor c = w.getCursor();
- boolean same;
-
- if (cid == 0) // No cursor.
- same = (c == null);
- else if (cid == 1) // CurrentCursor.
- same = (c == xServer.getScreen().getCurrentCursor());
- else same = (cid == c.getId());
-
- synchronized (io) {
- Util.writeReplyHeader(client, (byte) (same ? 1 : 0));
- io.writeInt(0); // Reply length.
- io.writePadBytes(24);
- }
- io.flush();
- }
- break;
- case XTestFakeInput:
- if (bytesRemaining != 32) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- byte type = (byte) io.readByte();
- int detail = io.readByte();
-
- io.readSkip(2);
-
- int delay = io.readInt();
- int wid = io.readInt();
-
- io.readSkip(8);
-
- int x = io.readShort();
- int y = io.readShort();
-
- io.readSkip(8);
-
- Window root;
-
- if (wid == 0) {
- root = xServer.getScreen().getRootWindow();
- } else {
- Resource r = (Window) xServer.getResource(wid);
-
- if (r == null || r.getType() != Resource.WINDOW) {
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Window, arg, opcode, wid);
- return;
- } else {
- root = (Window) r;
- }
- }
- testFakeInput(xServer, client, opcode, arg, type, detail, delay, root, x, y);
- }
- break;
- case XTestGrabControl:
- if (bytesRemaining != 4) {
- io.readSkip(bytesRemaining);
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Length, arg, opcode, 0);
- } else {
- boolean impervious = (io.readByte() != 0);
-
- io.readSkip(3);
- client.setImperviousToServerGrabs(impervious);
- }
- break;
- default:
- io.readSkip(bytesRemaining);
- ErrorCode.write(client, ErrorCode.Implementation, opcode, 0);
- break;
- }
- }
-
- /**
- * Inject a fake event.
- *
- * @param xServer The X server.
- * @param client The remote client.
- * @param opcode The request opcode, used for error reporting.
- * @param minorOpcode The minor opcode, used for error reporting.
- * @param type The event type.
- * @param detail Meaning depends on event type.
- * @param delay Millisecond delay.
- * @param root The root window in which motion takes place.
- * @param x The X coordinate of a motion event.
- * @param y The Y coordinate of a motion event.
- * @throws java.io.IOException
- */
- private static void testFakeInput(XServer xServer, Client client, byte opcode, byte minorOpcode, byte type, int detail, int delay, Window root, int x, int y) throws java.io.IOException {
- if (delay != 0) {
- try {
- Thread.sleep(delay);
- } catch (InterruptedException e) {
- }
- }
-
- ScreenView sv = xServer.getScreen();
-
- switch (type) {
- case KeyPress:
- sv.notifyKeyPressedReleased(detail, true);
- break;
- case KeyRelease:
- sv.notifyKeyPressedReleased(detail, false);
- break;
- case ButtonPress:
- sv.updatePointerButtons(detail, true);
- break;
- case ButtonRelease:
- sv.updatePointerButtons(detail, false);
- break;
- case MotionNotify:
- if (root != null) sv = root.getScreen();
-
- if (detail != 0) { // Relative position.
- x += sv.getPointerX();
- y += sv.getPointerY();
- }
-
- if (x < 0) x = 0;
- else if (x >= sv.getWidth()) x = sv.getWidth() - 1;
-
- if (y < 0) y = 0;
- else if (y >= sv.getHeight()) y = sv.getHeight() - 1;
-
- sv.updatePointerPosition(x, y, 0);
- break;
- default:
- ErrorCode.writeWithMinorOpcode(client, ErrorCode.Value, minorOpcode, opcode, type);
- break;
- }
- }
-}
\ No newline at end of file
diff --git a/library/src/main/res/drawable/xc_arrow.png b/library/src/main/res/drawable/xc_arrow.png
deleted file mode 100644
index ad371d8..0000000
Binary files a/library/src/main/res/drawable/xc_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_based_arrow_down.png b/library/src/main/res/drawable/xc_based_arrow_down.png
deleted file mode 100644
index eaf8292..0000000
Binary files a/library/src/main/res/drawable/xc_based_arrow_down.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_based_arrow_up.png b/library/src/main/res/drawable/xc_based_arrow_up.png
deleted file mode 100644
index b61921b..0000000
Binary files a/library/src/main/res/drawable/xc_based_arrow_up.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_boat.png b/library/src/main/res/drawable/xc_boat.png
deleted file mode 100644
index ec1293a..0000000
Binary files a/library/src/main/res/drawable/xc_boat.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_bogosity.png b/library/src/main/res/drawable/xc_bogosity.png
deleted file mode 100644
index a772183..0000000
Binary files a/library/src/main/res/drawable/xc_bogosity.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_bottom_left_corner.png b/library/src/main/res/drawable/xc_bottom_left_corner.png
deleted file mode 100644
index 9d0cc2d..0000000
Binary files a/library/src/main/res/drawable/xc_bottom_left_corner.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_bottom_right_corner.png b/library/src/main/res/drawable/xc_bottom_right_corner.png
deleted file mode 100644
index 63e8418..0000000
Binary files a/library/src/main/res/drawable/xc_bottom_right_corner.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_bottom_side.png b/library/src/main/res/drawable/xc_bottom_side.png
deleted file mode 100644
index 1d8df41..0000000
Binary files a/library/src/main/res/drawable/xc_bottom_side.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_bottom_tee.png b/library/src/main/res/drawable/xc_bottom_tee.png
deleted file mode 100644
index 10fa1e1..0000000
Binary files a/library/src/main/res/drawable/xc_bottom_tee.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_box_spiral.png b/library/src/main/res/drawable/xc_box_spiral.png
deleted file mode 100644
index 82ec74f..0000000
Binary files a/library/src/main/res/drawable/xc_box_spiral.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_center_ptr.png b/library/src/main/res/drawable/xc_center_ptr.png
deleted file mode 100644
index b4ffb68..0000000
Binary files a/library/src/main/res/drawable/xc_center_ptr.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_circle.png b/library/src/main/res/drawable/xc_circle.png
deleted file mode 100644
index f98ca29..0000000
Binary files a/library/src/main/res/drawable/xc_circle.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_clock.png b/library/src/main/res/drawable/xc_clock.png
deleted file mode 100644
index e0e0479..0000000
Binary files a/library/src/main/res/drawable/xc_clock.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_coffee_mug.png b/library/src/main/res/drawable/xc_coffee_mug.png
deleted file mode 100644
index 93343ce..0000000
Binary files a/library/src/main/res/drawable/xc_coffee_mug.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_cross.png b/library/src/main/res/drawable/xc_cross.png
deleted file mode 100644
index bb968a2..0000000
Binary files a/library/src/main/res/drawable/xc_cross.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_cross_reverse.png b/library/src/main/res/drawable/xc_cross_reverse.png
deleted file mode 100644
index 34a2527..0000000
Binary files a/library/src/main/res/drawable/xc_cross_reverse.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_crosshair.png b/library/src/main/res/drawable/xc_crosshair.png
deleted file mode 100644
index 11bf39b..0000000
Binary files a/library/src/main/res/drawable/xc_crosshair.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_diamond_cross.png b/library/src/main/res/drawable/xc_diamond_cross.png
deleted file mode 100644
index 5c718e2..0000000
Binary files a/library/src/main/res/drawable/xc_diamond_cross.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_dot.png b/library/src/main/res/drawable/xc_dot.png
deleted file mode 100644
index b66f38e..0000000
Binary files a/library/src/main/res/drawable/xc_dot.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_dotbox.png b/library/src/main/res/drawable/xc_dotbox.png
deleted file mode 100644
index 0bde743..0000000
Binary files a/library/src/main/res/drawable/xc_dotbox.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_double_arrow.png b/library/src/main/res/drawable/xc_double_arrow.png
deleted file mode 100644
index c431a3c..0000000
Binary files a/library/src/main/res/drawable/xc_double_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_draft_large.png b/library/src/main/res/drawable/xc_draft_large.png
deleted file mode 100644
index 70fb5cd..0000000
Binary files a/library/src/main/res/drawable/xc_draft_large.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_draft_small.png b/library/src/main/res/drawable/xc_draft_small.png
deleted file mode 100644
index 73e60ee..0000000
Binary files a/library/src/main/res/drawable/xc_draft_small.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_draped_box.png b/library/src/main/res/drawable/xc_draped_box.png
deleted file mode 100644
index 17a49b8..0000000
Binary files a/library/src/main/res/drawable/xc_draped_box.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_exchange.png b/library/src/main/res/drawable/xc_exchange.png
deleted file mode 100644
index d981b87..0000000
Binary files a/library/src/main/res/drawable/xc_exchange.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_fleur.png b/library/src/main/res/drawable/xc_fleur.png
deleted file mode 100644
index c3c6ebe..0000000
Binary files a/library/src/main/res/drawable/xc_fleur.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_gobbler.png b/library/src/main/res/drawable/xc_gobbler.png
deleted file mode 100644
index 2958d1d..0000000
Binary files a/library/src/main/res/drawable/xc_gobbler.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_gumby.png b/library/src/main/res/drawable/xc_gumby.png
deleted file mode 100644
index 2e9e839..0000000
Binary files a/library/src/main/res/drawable/xc_gumby.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_hand1.png b/library/src/main/res/drawable/xc_hand1.png
deleted file mode 100644
index 384a8a9..0000000
Binary files a/library/src/main/res/drawable/xc_hand1.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_hand2.png b/library/src/main/res/drawable/xc_hand2.png
deleted file mode 100644
index 0607d42..0000000
Binary files a/library/src/main/res/drawable/xc_hand2.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_heart.png b/library/src/main/res/drawable/xc_heart.png
deleted file mode 100644
index af5166e..0000000
Binary files a/library/src/main/res/drawable/xc_heart.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_icon.png b/library/src/main/res/drawable/xc_icon.png
deleted file mode 100644
index e2cb540..0000000
Binary files a/library/src/main/res/drawable/xc_icon.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_iron_cross.png b/library/src/main/res/drawable/xc_iron_cross.png
deleted file mode 100644
index 435f5df..0000000
Binary files a/library/src/main/res/drawable/xc_iron_cross.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_left_ptr.png b/library/src/main/res/drawable/xc_left_ptr.png
deleted file mode 100644
index db2aada..0000000
Binary files a/library/src/main/res/drawable/xc_left_ptr.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_left_side.png b/library/src/main/res/drawable/xc_left_side.png
deleted file mode 100644
index ab3eb9e..0000000
Binary files a/library/src/main/res/drawable/xc_left_side.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_left_tee.png b/library/src/main/res/drawable/xc_left_tee.png
deleted file mode 100644
index 8396d4d..0000000
Binary files a/library/src/main/res/drawable/xc_left_tee.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_leftbutton.png b/library/src/main/res/drawable/xc_leftbutton.png
deleted file mode 100644
index 2bdc699..0000000
Binary files a/library/src/main/res/drawable/xc_leftbutton.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_ll_angle.png b/library/src/main/res/drawable/xc_ll_angle.png
deleted file mode 100644
index 182e7c9..0000000
Binary files a/library/src/main/res/drawable/xc_ll_angle.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_lr_angle.png b/library/src/main/res/drawable/xc_lr_angle.png
deleted file mode 100644
index 586c2d3..0000000
Binary files a/library/src/main/res/drawable/xc_lr_angle.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_man.png b/library/src/main/res/drawable/xc_man.png
deleted file mode 100644
index eff9bf8..0000000
Binary files a/library/src/main/res/drawable/xc_man.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_middlebutton.png b/library/src/main/res/drawable/xc_middlebutton.png
deleted file mode 100644
index d0ecb86..0000000
Binary files a/library/src/main/res/drawable/xc_middlebutton.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_mouse.png b/library/src/main/res/drawable/xc_mouse.png
deleted file mode 100644
index 3b6436d..0000000
Binary files a/library/src/main/res/drawable/xc_mouse.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_pencil.png b/library/src/main/res/drawable/xc_pencil.png
deleted file mode 100644
index 916d99e..0000000
Binary files a/library/src/main/res/drawable/xc_pencil.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_pirate.png b/library/src/main/res/drawable/xc_pirate.png
deleted file mode 100644
index 4d00c37..0000000
Binary files a/library/src/main/res/drawable/xc_pirate.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_plus.png b/library/src/main/res/drawable/xc_plus.png
deleted file mode 100644
index f43ab1b..0000000
Binary files a/library/src/main/res/drawable/xc_plus.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_question_arrow.png b/library/src/main/res/drawable/xc_question_arrow.png
deleted file mode 100644
index d680a26..0000000
Binary files a/library/src/main/res/drawable/xc_question_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_right_ptr.png b/library/src/main/res/drawable/xc_right_ptr.png
deleted file mode 100644
index cbce09b..0000000
Binary files a/library/src/main/res/drawable/xc_right_ptr.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_right_side.png b/library/src/main/res/drawable/xc_right_side.png
deleted file mode 100644
index 513f3d5..0000000
Binary files a/library/src/main/res/drawable/xc_right_side.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_right_tee.png b/library/src/main/res/drawable/xc_right_tee.png
deleted file mode 100644
index ee147f8..0000000
Binary files a/library/src/main/res/drawable/xc_right_tee.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_rightbutton.png b/library/src/main/res/drawable/xc_rightbutton.png
deleted file mode 100644
index a3b6b53..0000000
Binary files a/library/src/main/res/drawable/xc_rightbutton.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_rtl_logo.png b/library/src/main/res/drawable/xc_rtl_logo.png
deleted file mode 100644
index 6ba8d20..0000000
Binary files a/library/src/main/res/drawable/xc_rtl_logo.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sailboat.png b/library/src/main/res/drawable/xc_sailboat.png
deleted file mode 100644
index c24605d..0000000
Binary files a/library/src/main/res/drawable/xc_sailboat.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sb_down_arrow.png b/library/src/main/res/drawable/xc_sb_down_arrow.png
deleted file mode 100644
index 3f83356..0000000
Binary files a/library/src/main/res/drawable/xc_sb_down_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sb_h_double_arrow.png b/library/src/main/res/drawable/xc_sb_h_double_arrow.png
deleted file mode 100644
index 165784c..0000000
Binary files a/library/src/main/res/drawable/xc_sb_h_double_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sb_left_arrow.png b/library/src/main/res/drawable/xc_sb_left_arrow.png
deleted file mode 100644
index 2fab177..0000000
Binary files a/library/src/main/res/drawable/xc_sb_left_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sb_right_arrow.png b/library/src/main/res/drawable/xc_sb_right_arrow.png
deleted file mode 100644
index c01255d..0000000
Binary files a/library/src/main/res/drawable/xc_sb_right_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sb_up_arrow.png b/library/src/main/res/drawable/xc_sb_up_arrow.png
deleted file mode 100644
index a8779ba..0000000
Binary files a/library/src/main/res/drawable/xc_sb_up_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sb_v_double_arrow.png b/library/src/main/res/drawable/xc_sb_v_double_arrow.png
deleted file mode 100644
index bf51035..0000000
Binary files a/library/src/main/res/drawable/xc_sb_v_double_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_shuttle.png b/library/src/main/res/drawable/xc_shuttle.png
deleted file mode 100644
index 53545bb..0000000
Binary files a/library/src/main/res/drawable/xc_shuttle.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_sizing.png b/library/src/main/res/drawable/xc_sizing.png
deleted file mode 100644
index ee15f39..0000000
Binary files a/library/src/main/res/drawable/xc_sizing.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_spider.png b/library/src/main/res/drawable/xc_spider.png
deleted file mode 100644
index 21fc089..0000000
Binary files a/library/src/main/res/drawable/xc_spider.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_spraycan.png b/library/src/main/res/drawable/xc_spraycan.png
deleted file mode 100644
index 13d31a1..0000000
Binary files a/library/src/main/res/drawable/xc_spraycan.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_star.png b/library/src/main/res/drawable/xc_star.png
deleted file mode 100644
index f2acd87..0000000
Binary files a/library/src/main/res/drawable/xc_star.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_target.png b/library/src/main/res/drawable/xc_target.png
deleted file mode 100644
index a93f723..0000000
Binary files a/library/src/main/res/drawable/xc_target.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_tcross.png b/library/src/main/res/drawable/xc_tcross.png
deleted file mode 100644
index c5cc5c2..0000000
Binary files a/library/src/main/res/drawable/xc_tcross.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_top_left_arrow.png b/library/src/main/res/drawable/xc_top_left_arrow.png
deleted file mode 100644
index 683ba96..0000000
Binary files a/library/src/main/res/drawable/xc_top_left_arrow.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_top_left_corner.png b/library/src/main/res/drawable/xc_top_left_corner.png
deleted file mode 100644
index 4bc8306..0000000
Binary files a/library/src/main/res/drawable/xc_top_left_corner.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_top_right_corner.png b/library/src/main/res/drawable/xc_top_right_corner.png
deleted file mode 100644
index 181ec37..0000000
Binary files a/library/src/main/res/drawable/xc_top_right_corner.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_top_side.png b/library/src/main/res/drawable/xc_top_side.png
deleted file mode 100644
index 356d080..0000000
Binary files a/library/src/main/res/drawable/xc_top_side.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_top_tee.png b/library/src/main/res/drawable/xc_top_tee.png
deleted file mode 100644
index 819f80b..0000000
Binary files a/library/src/main/res/drawable/xc_top_tee.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_trek.png b/library/src/main/res/drawable/xc_trek.png
deleted file mode 100644
index 4ef9978..0000000
Binary files a/library/src/main/res/drawable/xc_trek.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_ul_angle.png b/library/src/main/res/drawable/xc_ul_angle.png
deleted file mode 100644
index 32bdaec..0000000
Binary files a/library/src/main/res/drawable/xc_ul_angle.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_umbrella.png b/library/src/main/res/drawable/xc_umbrella.png
deleted file mode 100644
index 04bdd59..0000000
Binary files a/library/src/main/res/drawable/xc_umbrella.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_ur_angle.png b/library/src/main/res/drawable/xc_ur_angle.png
deleted file mode 100644
index 9a43ae2..0000000
Binary files a/library/src/main/res/drawable/xc_ur_angle.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_watch.png b/library/src/main/res/drawable/xc_watch.png
deleted file mode 100644
index c878fa7..0000000
Binary files a/library/src/main/res/drawable/xc_watch.png and /dev/null differ
diff --git a/library/src/main/res/drawable/xc_xterm.png b/library/src/main/res/drawable/xc_xterm.png
deleted file mode 100644
index 29351c4..0000000
Binary files a/library/src/main/res/drawable/xc_xterm.png and /dev/null differ
diff --git a/settings.gradle b/settings.gradle
index 887c9fa..8d3a1c4 100644
--- a/settings.gradle
+++ b/settings.gradle
@@ -1,3 +1,3 @@
rootProject.name = "Vectras VM"
-include ':app', ':terminal-emulator', ':terminal-view', ':shell-loader:stub', ':shell-loader', ':library'
+include ':app', ':terminal-emulator', ':terminal-view', ':shell-loader:stub', ':shell-loader'
diff --git a/web/data/UpdateConfig.json b/web/data/UpdateConfig.json
index ed4b866..2b80861 100644
--- a/web/data/UpdateConfig.json
+++ b/web/data/UpdateConfig.json
@@ -5,11 +5,11 @@
"url": "https://github.com/xoureldeen/Vectras-VM-Android/releases",
"Message": "3.4.0
\n- Fixed the issue of exporting rom with virtual machine ID.\n- New dialog for copying files in creating new virtual machine.\n- New dialog showing information after successful rom import.\n- Fixed no sound playing with Termux.\n- Fixed invalid file path error when using Manual setup.\n- Fixed dialog showing content without line breaks.\n- Fixed rom export error.\n- Added Processes to System monitor.\n- Improved interface.\n- Thinner fonts.\n- Fixed an issue with interaction in Rom store.\n- Fixed the External VNC Server switch being incorrect in certain cases.\n- Removed unnecessary resources.\n- Updated Chinese (Simplified) language (contributed by @WeiguangTWK).\n- Fixed issue with installing system files after not completing the first time.\n- New setup wizard.\n- Added auto return to Home after importing rom and creating virtual machine in Rom store.\n- Improved image viewer.\n- Fixed Unknow display error in architecture in rom info if it is PowerPC architecture.\n- New setup wizard interface that automatically changes according to screen size.\n- New ID generator for virtual machine.\n- Added dialog when deleting virtual machine.",
"cancellable": true,
- "versionCodeBeta":"47",
- "versionNameBeta":"3.4.3",
- "versionNameBetas":"3.0.0,3.1.0,3.2.1,3.2.2,3.2.3,3.2.4,3.2.5,3.2.6,3.2.7,3.2.8,3.2.9,3.2.10,3.3.1,3.3.2,3.3.3,3.3.4,3.3.5,3.3.6,3.3.7,3.3.8,3.3.9,3.4.1,3.4.2,3.4.3",
- "sizeBeta": "55 MB",
+ "versionCodeBeta":"48",
+ "versionNameBeta":"3.4.4",
+ "versionNameBetas":"3.0.0,3.1.0,3.2.1,3.2.2,3.2.3,3.2.4,3.2.5,3.2.6,3.2.7,3.2.8,3.2.9,3.2.10,3.3.1,3.3.2,3.3.3,3.3.4,3.3.5,3.3.6,3.3.7,3.3.8,3.3.9,3.4.1,3.4.2,3.4.3,3.4.4",
+ "sizeBeta": "45 MB",
"urlBeta": "https://github.com/AnBui2004/Vectras-VM-Emu-Android/releases",
- "MessageBeta": "3.4.3
Bugs fixed.",
+ "MessageBeta": "3.4.4
Bugs fixed.",
"cancellableBeta": true
}