Skip to content

Commit bb7fa88

Browse files
Kruna1Pate1agnostic-apollo
authored andcommitted
Added|Changed: Fill .ws_xpixel and .ws_ypixel in winsize
This allows to get terminal size in pixel using `TIOCGWINSZ` ioctl. Set `.ws_xpixel` using `columns * cell_width` and set `.ws_ypixel` using `rows * cell_height`. Cell width and height is font width and line spacing, respectively.
1 parent f35063d commit bb7fa88

File tree

4 files changed

+20
-16
lines changed

4 files changed

+20
-16
lines changed

terminal-emulator/src/main/java/com/termux/terminal/JNI.java

+2-2
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,10 @@ final class JNI {
2323
* @return the file descriptor resulting from opening /dev/ptmx master device. The sub process will have opened the
2424
* slave device counterpart (/dev/pts/$N) and have it as stdint, stdout and stderr.
2525
*/
26-
public static native int createSubprocess(String cmd, String cwd, String[] args, String[] envVars, int[] processId, int rows, int columns);
26+
public static native int createSubprocess(String cmd, String cwd, String[] args, String[] envVars, int[] processId, int rows, int columns, int cellWidth, int cellHeight);
2727

2828
/** Set the window size for a given pty, which allows connected programs to learn how large their screen is. */
29-
public static native void setPtyWindowSize(int fd, int rows, int cols);
29+
public static native void setPtyWindowSize(int fd, int rows, int cols, int cellWidth, int cellHeight);
3030

3131
/**
3232
* Causes the calling thread to wait for the process associated with the receiver to finish executing.

terminal-emulator/src/main/java/com/termux/terminal/TerminalSession.java

+7-7
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
* A terminal session, consisting of a process coupled to a terminal interface.
2222
* <p>
2323
* The subprocess will be executed by the constructor, and when the size is made known by a call to
24-
* {@link #updateSize(int, int)} terminal emulation will begin and threads will be spawned to handle the subprocess I/O.
24+
* {@link #updateSize(int, int, int, int)} terminal emulation will begin and threads will be spawned to handle the subprocess I/O.
2525
* All terminal emulation and callback methods will be performed on the main thread.
2626
* <p>
2727
* The child process may be exited forcefully by using the {@link #finishIfRunning()} method.
@@ -61,7 +61,7 @@ public final class TerminalSession extends TerminalOutput {
6161

6262
/**
6363
* The file descriptor referencing the master half of a pseudo-terminal pair, resulting from calling
64-
* {@link JNI#createSubprocess(String, String, String[], String[], int[], int, int)}.
64+
* {@link JNI#createSubprocess(String, String, String[], String[], int[], int, int, int, int)}.
6565
*/
6666
private int mTerminalFileDescriptor;
6767

@@ -100,11 +100,11 @@ public void updateTerminalSessionClient(TerminalSessionClient client) {
100100
}
101101

102102
/** Inform the attached pty of the new size and reflow or initialize the emulator. */
103-
public void updateSize(int columns, int rows) {
103+
public void updateSize(int columns, int rows, int fontWidth, int fontHeight) {
104104
if (mEmulator == null) {
105-
initializeEmulator(columns, rows);
105+
initializeEmulator(columns, rows, fontWidth, fontHeight);
106106
} else {
107-
JNI.setPtyWindowSize(mTerminalFileDescriptor, rows, columns);
107+
JNI.setPtyWindowSize(mTerminalFileDescriptor, rows, columns, fontWidth, fontHeight);
108108
mEmulator.resize(columns, rows);
109109
}
110110
}
@@ -120,11 +120,11 @@ public String getTitle() {
120120
* @param columns The number of columns in the terminal window.
121121
* @param rows The number of rows in the terminal window.
122122
*/
123-
public void initializeEmulator(int columns, int rows) {
123+
public void initializeEmulator(int columns, int rows, int cellWidth, int cellHeight) {
124124
mEmulator = new TerminalEmulator(this, columns, rows, mTranscriptRows, mClient);
125125

126126
int[] processId = new int[1];
127-
mTerminalFileDescriptor = JNI.createSubprocess(mShellPath, mCwd, mArgs, mEnv, processId, rows, columns);
127+
mTerminalFileDescriptor = JNI.createSubprocess(mShellPath, mCwd, mArgs, mEnv, processId, rows, columns, cellWidth, cellHeight);
128128
mShellPid = processId[0];
129129

130130
final FileDescriptor terminalFileDescriptorWrapped = wrapFileDescriptor(mTerminalFileDescriptor, mClient);

terminal-emulator/src/main/jni/termux.c

+10-6
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,9 @@ static int create_subprocess(JNIEnv* env,
2929
char** envp,
3030
int* pProcessId,
3131
jint rows,
32-
jint columns)
32+
jint columns,
33+
jint cell_width,
34+
jint cell_height)
3335
{
3436
int ptm = open("/dev/ptmx", O_RDWR | O_CLOEXEC);
3537
if (ptm < 0) return throw_runtime_exception(env, "Cannot open /dev/ptmx");
@@ -57,7 +59,7 @@ static int create_subprocess(JNIEnv* env,
5759
tcsetattr(ptm, TCSANOW, &tios);
5860

5961
/** Set initial winsize. */
60-
struct winsize sz = { .ws_row = (unsigned short) rows, .ws_col = (unsigned short) columns };
62+
struct winsize sz = { .ws_row = (unsigned short) rows, .ws_col = (unsigned short) columns, .ws_xpixel = (unsigned short) (columns * cell_width), .ws_ypixel = (unsigned short) (rows * cell_height)};
6163
ioctl(ptm, TIOCSWINSZ, &sz);
6264

6365
pid_t pid = fork();
@@ -121,7 +123,9 @@ JNIEXPORT jint JNICALL Java_com_termux_terminal_JNI_createSubprocess(
121123
jobjectArray envVars,
122124
jintArray processIdArray,
123125
jint rows,
124-
jint columns)
126+
jint columns,
127+
jint cell_width,
128+
jint cell_height)
125129
{
126130
jsize size = args ? (*env)->GetArrayLength(env, args) : 0;
127131
char** argv = NULL;
@@ -156,7 +160,7 @@ JNIEXPORT jint JNICALL Java_com_termux_terminal_JNI_createSubprocess(
156160
int procId = 0;
157161
char const* cmd_cwd = (*env)->GetStringUTFChars(env, cwd, NULL);
158162
char const* cmd_utf8 = (*env)->GetStringUTFChars(env, cmd, NULL);
159-
int ptm = create_subprocess(env, cmd_utf8, cmd_cwd, argv, envp, &procId, rows, columns);
163+
int ptm = create_subprocess(env, cmd_utf8, cmd_cwd, argv, envp, &procId, rows, columns, cell_width, cell_height);
160164
(*env)->ReleaseStringUTFChars(env, cmd, cmd_utf8);
161165
(*env)->ReleaseStringUTFChars(env, cmd, cmd_cwd);
162166

@@ -178,9 +182,9 @@ JNIEXPORT jint JNICALL Java_com_termux_terminal_JNI_createSubprocess(
178182
return ptm;
179183
}
180184

181-
JNIEXPORT void JNICALL Java_com_termux_terminal_JNI_setPtyWindowSize(JNIEnv* TERMUX_UNUSED(env), jclass TERMUX_UNUSED(clazz), jint fd, jint rows, jint cols)
185+
JNIEXPORT void JNICALL Java_com_termux_terminal_JNI_setPtyWindowSize(JNIEnv* TERMUX_UNUSED(env), jclass TERMUX_UNUSED(clazz), jint fd, jint rows, jint cols, jint cell_width, jint cell_height)
182186
{
183-
struct winsize sz = { .ws_row = (unsigned short) rows, .ws_col = (unsigned short) cols };
187+
struct winsize sz = { .ws_row = (unsigned short) rows, .ws_col = (unsigned short) cols, .ws_xpixel = (unsigned short) (cols * cell_width), .ws_ypixel = (unsigned short) (rows * cell_height) };
184188
ioctl(fd, TIOCSWINSZ, &sz);
185189
}
186190

terminal-view/src/main/java/com/termux/view/TerminalView.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -956,7 +956,7 @@ public void updateSize() {
956956
int newRows = Math.max(4, (viewHeight - mRenderer.mFontLineSpacingAndAscent) / mRenderer.mFontLineSpacing);
957957

958958
if (mEmulator == null || (newColumns != mEmulator.mColumns || newRows != mEmulator.mRows)) {
959-
mTermSession.updateSize(newColumns, newRows);
959+
mTermSession.updateSize(newColumns, newRows, (int) mRenderer.getFontWidth(), mRenderer.getFontLineSpacing());
960960
mEmulator = mTermSession.getEmulator();
961961
mClient.onEmulatorSet();
962962

0 commit comments

Comments
 (0)