├── .gitignore
├── CMakeLists.txt
├── LICENSE
├── Manual.md
├── README.md
├── TUTORIAL.md
├── doc_html
├── manual-dark.html.gz
├── manual-light.html.gz
├── tutorial-dark.html.gz
└── tutorial-light.html.gz
├── doc_templates
├── doctemplate.html
├── github-markdown-dark.css
└── github-markdown-light.css
├── examples
└── yt-dl-gui
├── gendocHTML.sh
├── src
├── docviewer.sh
├── helper.c
├── tgui-bash.sh
└── unzip.sh
└── tutorial
├── dialog.sh
├── events.sh
├── hello_world.sh
├── image.sh
├── linearlayout.sh
├── scroll.sh
└── widget.sh
/.gitignore:
--------------------------------------------------------------------------------
1 | CMakeLists.txt.user
2 | CMakeCache.txt
3 | CMakeFiles
4 | CMakeScripts
5 | Testing
6 | Makefile
7 | cmake_install.cmake
8 | install_manifest.txt
9 | compile_commands.json
10 | CTestTestfile.cmake
11 | _deps
12 |
13 |
14 | /build
15 | /.idea
16 | /.vscode
17 | /termux-gui-bash.tar.gz
18 | /push.sh
19 |
--------------------------------------------------------------------------------
/CMakeLists.txt:
--------------------------------------------------------------------------------
1 | cmake_minimum_required(VERSION 3.18)
2 | project(termux-gui-bash)
3 |
4 | set(CMAKE_C_STANDARD 99)
5 | set(CMAKE_C_STANDARD_REQUIRED ON)
6 | set(CMAKE_C_FLAGS "-Os")
7 | set(THREADS_PREFER_PTHREAD_FLAG ON)
8 |
9 | set(TERMUX_PREFIX "${CMAKE_INSTALL_PREFIX}")
10 |
11 | find_package(Threads REQUIRED)
12 |
13 | set(version 1.0)
14 |
15 |
16 |
17 | add_executable(termux-gui-bash-helper src/helper.c)
18 |
19 | target_link_libraries(termux-gui-bash-helper Threads::Threads)
20 |
21 |
22 | configure_file(src/tgui-bash.sh tgui-bash.sh @ONLY)
23 | configure_file(src/unzip.sh tgui-bash @ONLY)
24 | configure_file(src/docviewer.sh docviewer.sh @ONLY)
25 |
26 | execute_process(
27 | COMMAND bash -c "gzip -c -k \"${CMAKE_CURRENT_BINARY_DIR}/tgui-bash.sh\" >> \"${CMAKE_CURRENT_BINARY_DIR}/tgui-bash\""
28 | WORKING_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}")
29 |
30 | install(PROGRAMS "${CMAKE_CURRENT_BINARY_DIR}/tgui-bash" TYPE BIN)
31 | install(PROGRAMS "${CMAKE_CURRENT_BINARY_DIR}/docviewer.sh" DESTINATION "${CMAKE_INSTALL_PREFIX}/share/tgui-bash")
32 | install(FILES
33 | doc_html/tutorial-light.html.gz
34 | doc_html/tutorial-dark.html.gz
35 | doc_html/manual-light.html.gz
36 | doc_html/manual-dark.html.gz
37 | DESTINATION "${CMAKE_INSTALL_PREFIX}/share/tgui-bash")
38 | install(TARGETS termux-gui-bash-helper RUNTIME DESTINATION "${CMAKE_INSTALL_PREFIX}/libexec")
39 |
40 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | Mozilla Public License Version 2.0
2 | ==================================
3 |
4 | 1. Definitions
5 | --------------
6 |
7 | 1.1. "Contributor"
8 | means each individual or legal entity that creates, contributes to
9 | the creation of, or owns Covered Software.
10 |
11 | 1.2. "Contributor Version"
12 | means the combination of the Contributions of others (if any) used
13 | by a Contributor and that particular Contributor's Contribution.
14 |
15 | 1.3. "Contribution"
16 | means Covered Software of a particular Contributor.
17 |
18 | 1.4. "Covered Software"
19 | means Source Code Form to which the initial Contributor has attached
20 | the notice in Exhibit A, the Executable Form of such Source Code
21 | Form, and Modifications of such Source Code Form, in each case
22 | including portions thereof.
23 |
24 | 1.5. "Incompatible With Secondary Licenses"
25 | means
26 |
27 | (a) that the initial Contributor has attached the notice described
28 | in Exhibit B to the Covered Software; or
29 |
30 | (b) that the Covered Software was made available under the terms of
31 | version 1.1 or earlier of the License, but not also under the
32 | terms of a Secondary License.
33 |
34 | 1.6. "Executable Form"
35 | means any form of the work other than Source Code Form.
36 |
37 | 1.7. "Larger Work"
38 | means a work that combines Covered Software with other material, in
39 | a separate file or files, that is not Covered Software.
40 |
41 | 1.8. "License"
42 | means this document.
43 |
44 | 1.9. "Licensable"
45 | means having the right to grant, to the maximum extent possible,
46 | whether at the time of the initial grant or subsequently, any and
47 | all of the rights conveyed by this License.
48 |
49 | 1.10. "Modifications"
50 | means any of the following:
51 |
52 | (a) any file in Source Code Form that results from an addition to,
53 | deletion from, or modification of the contents of Covered
54 | Software; or
55 |
56 | (b) any new file in Source Code Form that contains any Covered
57 | Software.
58 |
59 | 1.11. "Patent Claims" of a Contributor
60 | means any patent claim(s), including without limitation, method,
61 | process, and apparatus claims, in any patent Licensable by such
62 | Contributor that would be infringed, but for the grant of the
63 | License, by the making, using, selling, offering for sale, having
64 | made, import, or transfer of either its Contributions or its
65 | Contributor Version.
66 |
67 | 1.12. "Secondary License"
68 | means either the GNU General Public License, Version 2.0, the GNU
69 | Lesser General Public License, Version 2.1, the GNU Affero General
70 | Public License, Version 3.0, or any later versions of those
71 | licenses.
72 |
73 | 1.13. "Source Code Form"
74 | means the form of the work preferred for making modifications.
75 |
76 | 1.14. "You" (or "Your")
77 | means an individual or a legal entity exercising rights under this
78 | License. For legal entities, "You" includes any entity that
79 | controls, is controlled by, or is under common control with You. For
80 | purposes of this definition, "control" means (a) the power, direct
81 | or indirect, to cause the direction or management of such entity,
82 | whether by contract or otherwise, or (b) ownership of more than
83 | fifty percent (50%) of the outstanding shares or beneficial
84 | ownership of such entity.
85 |
86 | 2. License Grants and Conditions
87 | --------------------------------
88 |
89 | 2.1. Grants
90 |
91 | Each Contributor hereby grants You a world-wide, royalty-free,
92 | non-exclusive license:
93 |
94 | (a) under intellectual property rights (other than patent or trademark)
95 | Licensable by such Contributor to use, reproduce, make available,
96 | modify, display, perform, distribute, and otherwise exploit its
97 | Contributions, either on an unmodified basis, with Modifications, or
98 | as part of a Larger Work; and
99 |
100 | (b) under Patent Claims of such Contributor to make, use, sell, offer
101 | for sale, have made, import, and otherwise transfer either its
102 | Contributions or its Contributor Version.
103 |
104 | 2.2. Effective Date
105 |
106 | The licenses granted in Section 2.1 with respect to any Contribution
107 | become effective for each Contribution on the date the Contributor first
108 | distributes such Contribution.
109 |
110 | 2.3. Limitations on Grant Scope
111 |
112 | The licenses granted in this Section 2 are the only rights granted under
113 | this License. No additional rights or licenses will be implied from the
114 | distribution or licensing of Covered Software under this License.
115 | Notwithstanding Section 2.1(b) above, no patent license is granted by a
116 | Contributor:
117 |
118 | (a) for any code that a Contributor has removed from Covered Software;
119 | or
120 |
121 | (b) for infringements caused by: (i) Your and any other third party's
122 | modifications of Covered Software, or (ii) the combination of its
123 | Contributions with other software (except as part of its Contributor
124 | Version); or
125 |
126 | (c) under Patent Claims infringed by Covered Software in the absence of
127 | its Contributions.
128 |
129 | This License does not grant any rights in the trademarks, service marks,
130 | or logos of any Contributor (except as may be necessary to comply with
131 | the notice requirements in Section 3.4).
132 |
133 | 2.4. Subsequent Licenses
134 |
135 | No Contributor makes additional grants as a result of Your choice to
136 | distribute the Covered Software under a subsequent version of this
137 | License (see Section 10.2) or under the terms of a Secondary License (if
138 | permitted under the terms of Section 3.3).
139 |
140 | 2.5. Representation
141 |
142 | Each Contributor represents that the Contributor believes its
143 | Contributions are its original creation(s) or it has sufficient rights
144 | to grant the rights to its Contributions conveyed by this License.
145 |
146 | 2.6. Fair Use
147 |
148 | This License is not intended to limit any rights You have under
149 | applicable copyright doctrines of fair use, fair dealing, or other
150 | equivalents.
151 |
152 | 2.7. Conditions
153 |
154 | Sections 3.1, 3.2, 3.3, and 3.4 are conditions of the licenses granted
155 | in Section 2.1.
156 |
157 | 3. Responsibilities
158 | -------------------
159 |
160 | 3.1. Distribution of Source Form
161 |
162 | All distribution of Covered Software in Source Code Form, including any
163 | Modifications that You create or to which You contribute, must be under
164 | the terms of this License. You must inform recipients that the Source
165 | Code Form of the Covered Software is governed by the terms of this
166 | License, and how they can obtain a copy of this License. You may not
167 | attempt to alter or restrict the recipients' rights in the Source Code
168 | Form.
169 |
170 | 3.2. Distribution of Executable Form
171 |
172 | If You distribute Covered Software in Executable Form then:
173 |
174 | (a) such Covered Software must also be made available in Source Code
175 | Form, as described in Section 3.1, and You must inform recipients of
176 | the Executable Form how they can obtain a copy of such Source Code
177 | Form by reasonable means in a timely manner, at a charge no more
178 | than the cost of distribution to the recipient; and
179 |
180 | (b) You may distribute such Executable Form under the terms of this
181 | License, or sublicense it under different terms, provided that the
182 | license for the Executable Form does not attempt to limit or alter
183 | the recipients' rights in the Source Code Form under this License.
184 |
185 | 3.3. Distribution of a Larger Work
186 |
187 | You may create and distribute a Larger Work under terms of Your choice,
188 | provided that You also comply with the requirements of this License for
189 | the Covered Software. If the Larger Work is a combination of Covered
190 | Software with a work governed by one or more Secondary Licenses, and the
191 | Covered Software is not Incompatible With Secondary Licenses, this
192 | License permits You to additionally distribute such Covered Software
193 | under the terms of such Secondary License(s), so that the recipient of
194 | the Larger Work may, at their option, further distribute the Covered
195 | Software under the terms of either this License or such Secondary
196 | License(s).
197 |
198 | 3.4. Notices
199 |
200 | You may not remove or alter the substance of any license notices
201 | (including copyright notices, patent notices, disclaimers of warranty,
202 | or limitations of liability) contained within the Source Code Form of
203 | the Covered Software, except that You may alter any license notices to
204 | the extent required to remedy known factual inaccuracies.
205 |
206 | 3.5. Application of Additional Terms
207 |
208 | You may choose to offer, and to charge a fee for, warranty, support,
209 | indemnity or liability obligations to one or more recipients of Covered
210 | Software. However, You may do so only on Your own behalf, and not on
211 | behalf of any Contributor. You must make it absolutely clear that any
212 | such warranty, support, indemnity, or liability obligation is offered by
213 | You alone, and You hereby agree to indemnify every Contributor for any
214 | liability incurred by such Contributor as a result of warranty, support,
215 | indemnity or liability terms You offer. You may include additional
216 | disclaimers of warranty and limitations of liability specific to any
217 | jurisdiction.
218 |
219 | 4. Inability to Comply Due to Statute or Regulation
220 | ---------------------------------------------------
221 |
222 | If it is impossible for You to comply with any of the terms of this
223 | License with respect to some or all of the Covered Software due to
224 | statute, judicial order, or regulation then You must: (a) comply with
225 | the terms of this License to the maximum extent possible; and (b)
226 | describe the limitations and the code they affect. Such description must
227 | be placed in a text file included with all distributions of the Covered
228 | Software under this License. Except to the extent prohibited by statute
229 | or regulation, such description must be sufficiently detailed for a
230 | recipient of ordinary skill to be able to understand it.
231 |
232 | 5. Termination
233 | --------------
234 |
235 | 5.1. The rights granted under this License will terminate automatically
236 | if You fail to comply with any of its terms. However, if You become
237 | compliant, then the rights granted under this License from a particular
238 | Contributor are reinstated (a) provisionally, unless and until such
239 | Contributor explicitly and finally terminates Your grants, and (b) on an
240 | ongoing basis, if such Contributor fails to notify You of the
241 | non-compliance by some reasonable means prior to 60 days after You have
242 | come back into compliance. Moreover, Your grants from a particular
243 | Contributor are reinstated on an ongoing basis if such Contributor
244 | notifies You of the non-compliance by some reasonable means, this is the
245 | first time You have received notice of non-compliance with this License
246 | from such Contributor, and You become compliant prior to 30 days after
247 | Your receipt of the notice.
248 |
249 | 5.2. If You initiate litigation against any entity by asserting a patent
250 | infringement claim (excluding declaratory judgment actions,
251 | counter-claims, and cross-claims) alleging that a Contributor Version
252 | directly or indirectly infringes any patent, then the rights granted to
253 | You by any and all Contributors for the Covered Software under Section
254 | 2.1 of this License shall terminate.
255 |
256 | 5.3. In the event of termination under Sections 5.1 or 5.2 above, all
257 | end user license agreements (excluding distributors and resellers) which
258 | have been validly granted by You or Your distributors under this License
259 | prior to termination shall survive termination.
260 |
261 | ************************************************************************
262 | * *
263 | * 6. Disclaimer of Warranty *
264 | * ------------------------- *
265 | * *
266 | * Covered Software is provided under this License on an "as is" *
267 | * basis, without warranty of any kind, either expressed, implied, or *
268 | * statutory, including, without limitation, warranties that the *
269 | * Covered Software is free of defects, merchantable, fit for a *
270 | * particular purpose or non-infringing. The entire risk as to the *
271 | * quality and performance of the Covered Software is with You. *
272 | * Should any Covered Software prove defective in any respect, You *
273 | * (not any Contributor) assume the cost of any necessary servicing, *
274 | * repair, or correction. This disclaimer of warranty constitutes an *
275 | * essential part of this License. No use of any Covered Software is *
276 | * authorized under this License except under this disclaimer. *
277 | * *
278 | ************************************************************************
279 |
280 | ************************************************************************
281 | * *
282 | * 7. Limitation of Liability *
283 | * -------------------------- *
284 | * *
285 | * Under no circumstances and under no legal theory, whether tort *
286 | * (including negligence), contract, or otherwise, shall any *
287 | * Contributor, or anyone who distributes Covered Software as *
288 | * permitted above, be liable to You for any direct, indirect, *
289 | * special, incidental, or consequential damages of any character *
290 | * including, without limitation, damages for lost profits, loss of *
291 | * goodwill, work stoppage, computer failure or malfunction, or any *
292 | * and all other commercial damages or losses, even if such party *
293 | * shall have been informed of the possibility of such damages. This *
294 | * limitation of liability shall not apply to liability for death or *
295 | * personal injury resulting from such party's negligence to the *
296 | * extent applicable law prohibits such limitation. Some *
297 | * jurisdictions do not allow the exclusion or limitation of *
298 | * incidental or consequential damages, so this exclusion and *
299 | * limitation may not apply to You. *
300 | * *
301 | ************************************************************************
302 |
303 | 8. Litigation
304 | -------------
305 |
306 | Any litigation relating to this License may be brought only in the
307 | courts of a jurisdiction where the defendant maintains its principal
308 | place of business and such litigation shall be governed by laws of that
309 | jurisdiction, without reference to its conflict-of-law provisions.
310 | Nothing in this Section shall prevent a party's ability to bring
311 | cross-claims or counter-claims.
312 |
313 | 9. Miscellaneous
314 | ----------------
315 |
316 | This License represents the complete agreement concerning the subject
317 | matter hereof. If any provision of this License is held to be
318 | unenforceable, such provision shall be reformed only to the extent
319 | necessary to make it enforceable. Any law or regulation which provides
320 | that the language of a contract shall be construed against the drafter
321 | shall not be used to construe this License against a Contributor.
322 |
323 | 10. Versions of the License
324 | ---------------------------
325 |
326 | 10.1. New Versions
327 |
328 | Mozilla Foundation is the license steward. Except as provided in Section
329 | 10.3, no one other than the license steward has the right to modify or
330 | publish new versions of this License. Each version will be given a
331 | distinguishing version number.
332 |
333 | 10.2. Effect of New Versions
334 |
335 | You may distribute the Covered Software under the terms of the version
336 | of the License under which You originally received the Covered Software,
337 | or under the terms of any subsequent version published by the license
338 | steward.
339 |
340 | 10.3. Modified Versions
341 |
342 | If you create software not governed by this License, and you want to
343 | create a new license for such software, you may create and use a
344 | modified version of this License if you rename the license and remove
345 | any references to the name of the license steward (except to note that
346 | such modified license differs from this License).
347 |
348 | 10.4. Distributing Source Code Form that is Incompatible With Secondary
349 | Licenses
350 |
351 | If You choose to distribute Source Code Form that is Incompatible With
352 | Secondary Licenses under the terms of this version of the License, the
353 | notice described in Exhibit B of this License must be attached.
354 |
355 | Exhibit A - Source Code Form License Notice
356 | -------------------------------------------
357 |
358 | This Source Code Form is subject to the terms of the Mozilla Public
359 | License, v. 2.0. If a copy of the MPL was not distributed with this
360 | file, You can obtain one at http://mozilla.org/MPL/2.0/.
361 |
362 | If it is not possible or desirable to put the notice in a particular
363 | file, then You may include the notice in a location (such as a LICENSE
364 | file in a relevant directory) where a recipient would be likely to look
365 | for such a notice.
366 |
367 | You may add additional accurate notices of copyright ownership.
368 |
369 | Exhibit B - "Incompatible With Secondary Licenses" Notice
370 | ---------------------------------------------------------
371 |
372 | This Source Code Form is "Incompatible With Secondary Licenses", as
373 | defined by the Mozilla Public License, v. 2.0.
374 |
--------------------------------------------------------------------------------
/Manual.md:
--------------------------------------------------------------------------------
1 | ## Name
2 | **tgui-bash** - Termux:GUI in bash
3 |
4 | ## Synopsis
5 | **tgui-bash** *filepath* ...
6 | **tgui-bash** -h ...
7 | source **tgui-bash**
8 |
9 | ## Description
10 | Sets up a connection to the Termux:GUI plugin through a small C helper, defines functions to interact with the plugin and finally sources the parameter into the script, so the functions are available.
11 |
12 | Can be used in a shebang (`#!/bin/tgui-bash`) or a script can self-exec (`! [ -v tgc_activity_tid ] && exec tgui-bash "${BASH_SOURCE[0]}" "$@"`).
13 |
14 | Using `set -eo pipefail` is advised to make your script exit when the connection to the plugin gets broken.
15 | For development, you should use `set -u` to make sure you spelled the constant names correctly.
16 |
17 | This library also uses the EXIT trap handler, so make sure to just add to it, but not overwrite it.
18 |
19 | ## Options
20 | `-h` Shows this manual or the tutorial in a browser of your choice. The following positional arguments are taken as answers to the questions.
21 |
22 |
23 | ## Environment
24 | All environment variables that affect bash will affect this program.
25 |
26 |
27 | ## Functions
28 |
29 | For passing arrays to functions and returning arrays, [bash namerefs](https://www.gnu.org/software/bash/manual/html_node/Shell-Parameters.html) are used.
30 | Reference parameters are marked with & and accept a variable name.
31 | Colors are specified in RGBA in hex with `aabbggrr`.
32 | Boolean values use the literal text `true` and `false`, as they are directly used for the JSON messages to the plugin.
33 | Images should be in PNG or JPEG format and base64 encoded (`base64 -w 0 file` or `image_generating_command | base64 -w 0`).
34 | Public functions and variables start with `tg_`, private functions and variables with `tg__`.
35 | Private functions and variables can change between versions, public ones should be stable.
36 |
37 |
38 | More documentation for the functions as defined in the protocol is available [here](https://github.com/termux/termux-gui/blob/main/Protocol.md#protocol-methods).
39 |
40 |
41 |
42 |
43 | ### Global Functions
44 |
45 |
46 |
47 | | Name | Description | Parameters | Return code |
48 | |----------------------------|-------------------------------------------------------------|------------|---------------------------|
49 | | tg_global_turn_screen_on | Turns the screen on. | | |
50 | | tg_global_is_locked | Returns whether the screen is locked. | | 0: locked 1: unlocked |
51 | | tg_global_version | Returns the version code of the plugin to stdout. | | |
52 | | tg_msg_recv_event | Returns an event if one is available, else an empty string. | | |
53 | | tg_msg_recv_event_blocking | Waits for an event and returns it. | | |
54 |
55 |
56 |
57 |
58 |
59 | ### Activity Functions
60 |
61 |
62 | | Name | Description | Parameters |
63 | |-----------------------------------|------------------------------------------------------------------------------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
64 | | tg_activity_new | Creates a new Activity. See the `tgc_activity_*` constants for keys and their effect. |
& Options associative array. See the constants for keys.
& Return array. \[0] will contain the Activity id, \[1] will contain the Task id (if the Task id wasn't given as an option).
|
65 | | tg_activity_finish | Finishes an Activity. | The Activity id of the Activity. |
66 | | tg_activity_to_back | Moves the Task of an Activity to the back. | The Activity id of the Activity. |
67 | | tg_activity_theme | Sets the theme of the Activity. |
The Activity id of the Activity.
The status bar color.
The primary color.
The window background color.
The text color.
The accent color
|
68 | | tg_activity_description | Sets the Task description and icon. |
The Activity id of the Activity.
The description (appears unused).
The icon.
|
69 | | tg_activity_pip_params | Sets the aspect ratio for picture-in-picture mode. |
The Activity id of the Activity.
The numerator of the aspect ratio.
The denominator of the aspect ratio.
|
70 | | tg_activity_input | Sets how the Activity responds to the soft keyboard. "resize" resizes the Activity to fit the keyboard, "pan", pans the Activity upward. |
The Activity id of the Activity.
The response option.
|
71 | | tg_activity_pip | Makes an Activity enter or leave picture-in-picture-mode. |
The Activity id of the Activity.
Boolean: Whether the Activity should be in pip or not.
|
72 | | tg_activity_pip_auto | Set if an Activity should go into pip automatically if the user leaves. |
The Activity id of the Activity.
Boolean: Whether the Activity should go into pip automatically or not.
|
73 | | tg_activity_keep_screen_on | Sets if showing the Activity should keep the screen from turning off. |
The Activity id of the Activity.
Boolean: Whether screen should be kept on.
|
74 | | tg_activity_orientation | Sets the Orientation of the Activity. |
The Activity id of the Activity.
Orientation. Please see table ["Android Activity Orientation Table"](#android-activity-orientation-table) below for values.
|
75 | | tg_activity_position | Sets the screen position for an overlay Activity. |
The Activity id of the Activity.
The x position.
The y position.
|
76 | | tg_activity_configuration | Gets the configuration for the Activity as a string. Get the values with the `tg_configuration_*` functions. |
The Activity id of the Activity.
|
77 | | tg_activity_request_unlock | Requests the user to unlock the screen or unlocks it if the screen isn't protected. |
|
79 | | tg_activity_intercept_back_button | Sets whether the back button should be intercepted. See the constant `tg_actvivity_intercept` fro more information. |
The Activity id of the Activity.
Boolean: Whether to intercept the back button.
|
80 |
81 |
82 |
83 |
84 | ### Task Functions
85 |
86 |
87 |
88 | | Name | Description | Parameters |
89 | |------------------|-----------------------------------------|--------------|
90 | | tg_task_finish | Finishes all activites in a Task. | The Task id. |
91 | | tg_task_to_front | Makes a Task visible to the user again. | The Task id. |
92 |
93 |
94 |
95 | ### Configuration Functions
96 |
97 | These functions all get the configuration string as the first parameter.
98 |
99 | | Name | Description |
100 | |---------------------------------|------------------------------------------------------------------------------------------|
101 | | tg_configuration_dark_mode | Whether dark mode is enabled, "true" or "false". "null" on Android versions prior to 10. |
102 | | tg_configuration_country | The country as a 2-letter string. |
103 | | tg_configuration_language | The language as a 2-letter string. |
104 | | tg_configuration_orientation | The screen orientation, either "landscape" or "portrait". |
105 | | tg_configuration_keyboardHidden | Whether a keyboard is currently available, as the string "true" or "false". |
106 | | tg_configuration_screenwidth | The current window width in dp. |
107 | | tg_configuration_screenheight | The current window height in dp. |
108 | | tg_configuration_fontscale | The current font scale value as a floating point number. |
109 | | tg_configuration_density | The display density as a float, such that screenwidth * density = screenwidth_in_px. |
110 |
111 |
112 |
113 | ### View Creation Functions
114 |
115 | All functions take the Activity id as the first parameter and
116 | a parameter associative array reference as the second parameter.
117 | The third parameter is an optional parent view id.
118 | For root Views, specify `""` as the third parameter or leave it out.
119 | The fourth parameter is the optional initial visibility of the View.
120 | The id of the created View is returned on stdout.
121 | The key for the parameter array are listed under the constants under `tgc_create_*`.
122 |
123 |
124 | | Name | Description |
125 | |-----------------------------|---------------------------------|
126 | | tg_create_linear | Creates a LinearLayout. |
127 | | tg_create_frame | Creates a FrameLayout. |
128 | | tg_create_swipe_refresh | Creates a SwipeRefreshLayout. |
129 | | tg_create_text | Creates a TextView. |
130 | | tg_create_edit | Creates an EditText. |
131 | | tg_create_button | Creates a Button. |
132 | | tg_create_image | Creates an ImageView. |
133 | | tg_create_space | Creates a Space. |
134 | | tg_create_nested_scroll | Creates a NestedScrollView. |
135 | | tg_create_horizontal_scroll | Creates a HorizontalScrollView. |
136 | | tg_create_radio | Creates a RadioButton. |
137 | | tg_create_radio_group | Creates a RadioGroup. |
138 | | tg_create_checkbox | Creates a Checkbox. |
139 | | tg_create_toggle | Creates a ToggleButton. |
140 | | tg_create_switch | Creates a Switch. |
141 | | tg_create_spinner | Creates a Spinner. |
142 | | tg_create_progress | Creates a ProgressBar. |
143 | | tg_create_tab | Creates a TabLayout. |
144 | | tg_create_grid | Creates a GridLayout. |
145 | | tg_create_web | Creates a WebView. |
146 |
147 |
148 |
149 | ### View Functions
150 |
151 | All these functions get the Activity id and the View id as the first and second parameters respectively.
152 |
153 |
154 | | Name | Description | Parameters |
155 | |-------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
156 | | tg_view_show_cursor | Sets whether or not a cursor is shown in an EditText. |
Boolean. Whether to show the cursor or not.
|
157 | | tg_view_linear | Sets the LinearLayout parameters for a View in a LinearLayout. |
The weight of the View.
The position of the View.
|
158 | | tg_view_grid | Sets the GridLayout parameters for a View in a GridLayout. |
The starting row of the View.
The starting column of the View.
The amount of rows this View uses.
The amount of columns this View uses
The alignment of the View in the row.
The alignment of the View in the column.
|
159 | | tg_view_location | Sets position of a View. |
The x position.
The y position
Whether to position is in dp or not.
Whether the View should be on top of al others.
|
160 | | tg_view_vis | Sets the visibility of a Vew. |
The visibility of the View.
|
161 | | tg_view_width | Sets the width of the view. |
The width of the View.
Whether the width is in px or not.
|
162 | | tg_view_height | Sets the height of the view. |
The height of the View.
Whether the height is in px or not.
|
163 | | tg_view_dimensions | Gets the current with and height of a View in pixels. | |
164 | | tg_view_delete | Deletes a View and its children from the Layout hierarchy. | |
165 | | tg_view_delete_children | Deletes the children of a View from the Layout hierarchy. | |
166 | | tg_view_margin | Sets the margin of a View. |
The margin in dp.
The direction of the margin. Leave empty for all directions.
|
167 | | tg_view_padding | Sets the padding of a View. |
The padding in dp.
The direction of the padding. Leave empty for all directions.
|
168 | | tg_view_bg_color | Sets the background color of a View. |
The color.
|
169 | | tg_view_text_color | Sets the text color of a View. |
The color
|
170 | | tg_view_progress | Sets the progress of a ProgressBar. |
The progress in range from 0 to 100.
|
171 | | tg_view_refreshing | Sets whether a SwipeRefreshLayout is refreshing. |
Whether the SwipeRefreshLayout is refreshing.
|
172 | | tg_view_text | Sets the text of the View. |
The text.
|
173 | | tg_view_gravity | Sets the gravity of the text of the View. |
The horizontal gravity.
The vertical gravity
|
174 | | tg_view_text_size | Sets the text size. |
The text size in sp.
|
175 | | tg_view_get_text | gets the text of the View. | |
176 | | tg_view_checked | Sets a RadioButton, CheckBox, Switch or ToggleButton to checked or unchecked explicitly. |
Whether the View is checked.
|
177 | | tg_view_request_focus | Focuses a View and opens the soft keyboard if the View has Keyboard input. |
Whether the soft keyboard should be forced to open.
|
178 | | tg_view_get_scroll | Gets the x and y scroll position of an NestedScrollView or HorizontalScrollView. | |
179 | | tg_view_set_scroll | Sets the x and y scroll position of an NestedScrollView or HorizontalScrollView. |
The x scroll position.
The y scroll position.
Whether the srcoll should be smooth.
|
180 | | tg_view_list | Set the list of a Spinner or TabLayout. |
& The array of tab/item names.
|
181 | | tg_view_image | Sets the image for an ImageView. |
The image as a base64 encoded string.
|
182 | | tg_view_select_tab | Selects a Tab in a TabLayout. The corresponding itemselected event is also send. |
The tab index, starting from 0.
|
183 | | tg_view_select_item | Selects a item in a Spinner. The corresponding itemselected event is also send. |
The item index, starting from 0.
|
184 | | tg_view_clickable | Sets whether a View can be clicked by the user (if yes, emits a sound and animation when clicked and sends a click event (if click events are enabled))). |
Whether the View should be clickable.
|
185 |
186 |
187 | ### Remote Layout, Widget & Notification Functions
188 |
189 |
190 |
191 | | Name | Description | Parameters |
192 | |---------------------------|-------------------------------------------------------------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------|
193 | | tg_remote_create_layout | Creates a new remote Layout. Returns the id for the remote Layout | |
194 | | tg_remote_delete_layout | Deletes a remote Layout. |
The id of the Layout to delete.
|
195 | | tg_remote_create_frame | Creates a FrameLayout in a remote Layout. Returns the View id in the Layout. |
The id of the Layout.
Optional. The parent if for the View.
|
196 | | tg_remote_create_text | Creates a TextView in a remote Layout. Returns the View id in the Layout. |
The id of the Layout.
Optional. The parent if for the View.
|
197 | | tg_remote_create_button | Creates a Button in a remote Layout. Returns the View id in the Layout. |
The id of the Layout.
Optional. The parent if for the View.
|
198 | | tg_remote_create_image | Creates an ImageView in a remote Layout. Returns the View id in the Layout. |
The id of the Layout.
Optional. The parent if for the View.
|
199 | | tg_remote_create_progress | Creates a ProgressBar in a remote Layout. Returns the View id in the Layout. |
The id of the Layout.
Optional. The parent if for the View.
|
200 | | tg_remote_bg_color | Sets the background color for a View in a remote Layout. |
The id of the Layout.
The id of the View.
The background color.
|
201 | | tg_remote_progress | Sets values for a ProgressBar in a remote Layout. |
The id of the Layout.
The id of the View.
The progress between 0 and 100.
|
202 | | tg_remote_text | Sets the text of a remote View. |
The id of the Layout.
The id of the View.
The text.
|
203 | | tg_remote_text_size | Sets the text size of a remote View. |
The id of the Layout.
The id of the View.
The text size.
|
204 | | tg_remote_text_color | Sets the Text color for a View in a remote Layout. |
The id of the Layout.
The id of the View.
The text color.
|
205 | | tg_remote_vis | Sets the visibility for a View in a remote Layout. |
The id of the Layout.
The id of the View.
The View visibility.
|
206 | | tg_remote_padding | Sets the padding in pixels for a View in a remote Layout. |
The id of the Layout.
The id of the View.
The padding.
|
207 | | tg_remote_image | Sets the image of a remote ImageView. |
The id of the Layout.
The id of the View.
The image.
|
208 | | tg_widget_layout | Sets the layout of a Widget to a remote Layout. |
The id of the Layout.
The id of the Widget.
|
209 | | tg_not_create_channel | On Android 8.0 and higher this creates a NotificationChannel, if one with the given id doesn't exist. |
The id string of the channel.
The importance of the channel.
The user-visible name.
|
210 | | tg_not_create | Creates a notification. Returns the notification id used for further calls. |
The channel id.
The notification importance
& The parameter array. See the `tgc_not_*` constants.
|
211 | | tg_not_cancel | Cancels a notification. |
The id of the Notification to cancel.
|
212 |
213 |
214 |
215 | ### Event Functions
216 |
217 | These functions change whether specific events are send for Views.
218 | The first parameter is the Activity id of the View, the second the id of the View
219 | and the third is the boolean for whether to send the event or not.
220 |
221 | | Name |
222 | |--------------------------|
223 | | tg_event_send_click |
224 | | tg_event_send_long_click |
225 | | tg_event_send_focus |
226 | | tg_event_send_touch |
227 | | tg_event_send_text |
228 |
229 |
230 | ### Event Parsing Functions
231 |
232 | Events are send as JSON, and are thus not usable directly in Bash.
233 | That's where the dependency on `jq` comes in: it is used to parse the events.
234 | You can use `jq` on the event data directly, but for some common tasks there are utility functions.
235 | They all get the event data as their only parameter.
236 | For more information about events, see [the protocol specification](https://github.com/termux/termux-gui/blob/main/Protocol.md#events).
237 |
238 | | Name | Description |
239 | |----------------|------------------------------------------------------------------------------------------------|
240 | | tg_event_type | Returns the event type, which can then be compared to one of the `tgc_ev_*` constants. |
241 | | tg_event_value | Returns the event value, which is a JSON object for some events and a direct value for others. |
242 | | tg_event_aid | Returns the Activity id of the event, or "null" if not present. |
243 | | tg_event_id | Returns the View id of the event, or "null" if not present. |
244 |
245 | ### WebView Functions
246 |
247 | All these functions get the Activity id and the View id as the first and second parameters respectively.
248 |
249 | | Name | Description | Parameters |
250 | |-------------------------|--------------------------------------------------------------------|--------------------------------------------------------------|
251 | | tg_web_allow_js | Sets whether Javascript is allowed to run in the WebView. |
Boolean.Whether to allow or not.
|
252 | | tg_web_allow_content | Sets whether content URIs are allowed in the WebView. |
Boolean.Whether to allow or not.
|
253 | | tg_web_set_data | Sets the document. |
The data.
|
254 | | tg_web_load_uri | Loads a specific URI. |
The URI.
|
255 | | tg_web_allow_navigation | Sets whether user/Javascript navigation is allowed in the WebView. |
Boolean.Whether to allow or not.
|
256 | | tg_web_back | Goes back in the history. | |
257 | | tg_web_forward | Goes forward in the history. | |
258 | | tg_web_eval_js | Runs Javascript. |
The Javascript.
|
259 |
260 | ## Constants
261 |
262 |
263 |
264 | #### tgc_activity_tid="tid"
265 | Key for the `tg_activity_new` options array. The value is a number.
266 | Specify a Task id here if you want Activities to launch over each other in the same Task.
267 |
268 | #### tgc_activity_dialog="dialog"
269 | Key for the `tg_activity_new` options array. The value is a boolean.
270 | Set this to make the Activity a dialog.
271 |
272 | #### tgc_activity_canceloutside="canceloutside"
273 | Key for the `tg_activity_new` options array. The value is a boolean.
274 | Set this to false if you want your dialog to not be dismissed when the user taps on something else.
275 |
276 | #### tgc_activity_pip="pip"
277 | Key for the `tg_activity_new` options array. The value is a boolean.
278 | Set this to let the Activity start in picture-in-picture mode.
279 |
280 | #### tgc_activity_lockscreen="lockscreen"
281 | Key for the `tg_activity_new` options array. The value is a boolean.
282 | Set this to make the Activity stay visible and interactable on the lockscreen.
283 | Make sure your interface is secure in this case, to not allow arbitrary command execution or file I/O.
284 |
285 | #### tgc_activity_overlay="overlay"
286 | Key for the `tg_activity_new` options array. The value is a boolean.
287 | This launches the Activity as an overlay over everything else, similar to picture-in-picture mode, but you can interact with all Views.
288 |
289 | #### tgc_activity_intercept="intercept"
290 | Key for the `tg_activity_new` options array. The value is a boolean.
291 | This option makes the back button send an event instead of finishing the Activity.
292 |
293 |
294 | #### tgc_create_text="text"
295 | Key for the `tg_create_*` parameter array.
296 | For Button, TextView and EditText, this is the initial Text.
297 |
298 | #### tgc_create_selectable_text="selectableText"
299 |
300 | Key for the `tg_create_*` parameter array.
301 | For TextViews, this specifies whether the text can be selected. Default is false.
302 |
303 | #### tgc_create_clickable_links="clickableLinks"
304 |
305 | Key for the `tg_create_*` parameter array.
306 | For TextViews, this specifies whether links can be clicked or not. Default is false.
307 |
308 | #### tgc_create_vertical="vertical"
309 |
310 | Key for the `tg_create_*` parameter array.
311 | For LinearLayout, this specifies if the Layout is vertical or horizontal.
312 | If not specified, vertical is assumed.
313 |
314 | #### tgc_create_snapping="snapping"
315 |
316 | Key for the `tg_create_*` parameter array.
317 | NestedScrollView and HorizontalScrollView snap to the nearest item if this is set to true.
318 | Default is false.
319 |
320 | #### tgc_create_fill_viewport="fillviewport"
321 |
322 | Key for the `tg_create_*` parameter array.
323 | Makes the child of a HorizontalScrollView or a NestedScrollView automatically expand to the ScrollView size.
324 | Default is false.
325 |
326 | #### tgc_create_no_bar="nobar"
327 |
328 | Key for the `tg_create_*` parameter array.
329 | Hides the scroll bar for HorizontalScrollView and NestedScrollView.
330 | Default is false.
331 |
332 | #### tgc_create_checked="checked"
333 |
334 | Key for the `tg_create_*` parameter array.
335 | Whether a RadioButton, CheckBox, Switch or ToggleButton should be checked.
336 | Defaults to false.
337 |
338 | #### tgc_create_single_line="singleline"
339 |
340 | Key for the `tg_create_*` parameter array.
341 | Whether an EditText should enable multiple lines to be entered.
342 |
343 | #### tgc_create_line="line"
344 |
345 | Key for the `tg_create_*` parameter array.
346 | Whether the line below an EditText should be shown.
347 |
348 | #### tgc_create_type="type"
349 |
350 | Key for the `tg_create_*` parameter array.
351 | For EditText this specifies the [input type](https://developer.android.com/reference/android/widget/TextView#attr_android:inputType): can be one of "text", "textMultiLine", "phone", "date", "time", "datetime", "number", "numberDecimal", "numberPassword", "numberSigned", "numberDecimalSigned", "textEmailAddress", "textPassword". "text" is the default. Specifying singleline as true sets this to "text".
352 |
353 | #### tgc_create_rows="rows"
354 |
355 | Key for the `tg_create_*` parameter array.
356 | Row count for GridLayout.
357 |
358 | #### tgc_create_cols="cols"
359 |
360 | Key for the `tg_create_*` parameter array.
361 | Column count for GridLayout.
362 |
363 | #### tgc_create_all_caps="allcaps"
364 |
365 | Key for the `tg_create_*` parameter array.
366 | Use this when creating a button to make all text automatically all caps (using small caps if possible).
367 |
368 | #### tgc_vis_gone="0"
369 |
370 | Visibility constant for Views. This makes Views invisible and take up no space in the Layout.
371 |
372 | #### tgc_vis_visible="2"
373 |
374 | Visibility constant for Views. This makes Views visible.
375 | #### tgc_vis_hidden="1"
376 |
377 | Visibility constant for Views. This makes Views invisible, but still take up space in the Layout.
378 |
379 | #### tgc_view_wrap_content='"WRAP_CONTENT"'
380 |
381 | Size constant for Views. This makes Views take as much space as needed for their content.
382 |
383 | #### tgc_view_match_parent='"MATCH_PARENT"'
384 |
385 | Size constant for Views. This makes Views take as much space as their parent.
386 |
387 | #### tgc_grid_top="top"
388 |
389 | Alignment for Views in GridLayout.
390 |
391 | #### tgc_grid_bottom="bottom"
392 |
393 | Alignment for Views in GridLayout.
394 |
395 | #### tgc_grid_left="left"
396 |
397 | Alignment for Views in GridLayout.
398 |
399 | #### tgc_grid_right="right"
400 |
401 | Alignment for Views in GridLayout.
402 |
403 | #### tgc_grid_center="center"
404 |
405 | Alignment for Views in GridLayout.
406 |
407 | #### tgc_grid_baseline="baseline"
408 |
409 | Alignment for Views in GridLayout.
410 |
411 | #### tgc_grid_fill="fill"
412 |
413 | Alignment for Views in GridLayout.
414 |
415 | #### tgc_dir_top="top"
416 |
417 | Direction constant.
418 |
419 | #### tgc_dir_bottom="bottom"
420 |
421 | Direction constant.
422 |
423 | #### tgc_dir_left="left"
424 |
425 | Direction constant.
426 |
427 | #### tgc_dir_right="right"
428 |
429 | Direction constant.
430 |
431 | #### tgc_grav_top_left="0"
432 |
433 | Text gravity constant. This makes text gravitate to the top/left.
434 |
435 | #### tgc_grav_center="1"
436 |
437 | Text gravity constant. This makes text gravitate to the center.
438 |
439 | #### tgc_grav_bottom_right="2"
440 |
441 | Text gravity constant. This makes text gravitate to the bottom/right.
442 |
443 | #### tgc_not_id="id"
444 |
445 | Key for the `tg_not_create` parameter array.
446 | The id of the notification to update. If not specified, generates a new id.
447 |
448 | #### tgc_not_ongoing="ongoing"
449 |
450 | Key for the `tg_not_create` parameter array.
451 | If true, the notification cannot be dismissed by the user,
452 | but the notification is automatically dismissed when you close the connection to the plugin.
453 |
454 | #### tgc_not_layout="layout"
455 |
456 | Key for the `tg_not_create` parameter array.
457 | The id of the remote Layout to use.
458 |
459 | #### tgc_not_expanded_layout="expandedLayout"
460 |
461 | Key for the `tg_not_create` parameter array.
462 | The id of the remote Layout to use when the notification has been expanded.
463 |
464 | #### tgc_not_hud_layout="hudLayout"
465 |
466 | Key for the `tg_not_create` parameter array.
467 | The id of the remote Layout to use when the notification is shown as a head-up notification.
468 |
469 | #### tgc_not_title="title"
470 |
471 | Key for the `tg_not_create` parameter array.
472 | The notification title.
473 |
474 | #### tgc_not_content="content"
475 |
476 | Key for the `tg_not_create` parameter array.
477 | The notification content text.
478 |
479 | #### tgc_not_large_image="largeImage"
480 |
481 | Key for the `tg_not_create` parameter array.
482 | A large image to display in the expanded view. You can only set either largeImage or largeText.
483 |
484 | #### tgc_not_large_text="largeText"
485 |
486 | Key for the `tg_not_create` parameter array.
487 | A large block of text to display in the expanded view. HTML formatting is supported.
488 | You can only set either largeImage or largeText.
489 |
490 | #### tgc_not_large_image_thumbnail="largeImageAsThumbnail"
491 |
492 | Key for the `tg_not_create` parameter array.
493 | If true, the largeImage is shown as a thumbnail in the collapsed view.
494 |
495 | #### tgc_not_icon="icon"
496 |
497 | Key for the `tg_not_create` parameter array.
498 | An image for the Notification in PNG or JPEG.
499 | Defaults to the Termux:GUI app icon if left empty.
500 |
501 | #### tgc_not_alert_once="alertOnce"
502 |
503 | Key for the `tg_not_create` parameter array.
504 | If this call is used to update a notification, don't alert the user again.
505 |
506 | #### tgc_not_show_timestamp="showTimestamp"
507 |
508 | Key for the `tg_not_create` parameter array.
509 | Shows the timestamp of the notification.
510 |
511 | #### tgc_not_timestamp="timestamp"
512 |
513 | Key for the `tg_not_create` parameter array.
514 | The timestamp to use in form of milliseconds since start of the epoch.
515 |
516 | #### tgc_not_actions="actions"
517 |
518 | Key for the `tg_not_create` parameter array.
519 | An array of strings with the names of actions.
520 | Pressing actions will generate a notificationaction event.
521 |
522 | ### Event Constants
523 |
524 | For more information about events, see [the protocol specification](https://github.com/termux/termux-gui/blob/main/Protocol.md#events).
525 |
526 | #### tgc_ev_click="click"
527 |
528 |
529 | #### tgc_ev_long_click="longClick"
530 |
531 |
532 | #### tgc_ev_focus_change="focusChange"
533 |
534 |
535 | #### tgc_ev_refresh="refresh"
536 |
537 |
538 | #### tgc_ev_selected="selected"
539 |
540 |
541 | #### tgc_ev_item_selected="itemselected"
542 |
543 |
544 | #### tgc_ev_text="text"
545 |
546 |
547 | #### tgc_ev_back="back"
548 |
549 |
550 | #### tgc_ev_webview_navigation="webviewNavigation"
551 |
552 |
553 | #### tgc_ev_webview_http_error="webviewHTTPError"
554 |
555 |
556 | #### tgc_ev_webview_error="webviewError"
557 |
558 |
559 | #### tgc_ev_webview_destroyed="webviewDestroyed"
560 |
561 |
562 | #### tgc_ev_webview_progress="webviewProgress"
563 |
564 |
565 | #### tgc_ev_webview_console_message="webviewConsoleMessage"
566 |
567 |
568 | #### tgc_ev_create="create"
569 |
570 |
571 | #### tgc_ev_start="start"
572 |
573 |
574 | #### tgc_ev_resume="resume"
575 |
576 |
577 | #### tgc_ev_pause="pause"
578 |
579 |
580 | #### tgc_ev_stop="stop"
581 |
582 |
583 | #### tgc_ev_destroy="destroy"
584 |
585 |
586 | #### tgc_ev_config="config"
587 |
588 |
589 | #### tgc_ev_user_leave_hint="UserLeaveHint"
590 |
591 |
592 | #### tgc_ev_pip_changed="pipchanged"
593 |
594 |
595 | #### tgc_ev_airplane="airplane"
596 |
597 |
598 | #### tgc_ev_locale="locale"
599 |
600 |
601 | #### tgc_ev_screen_on="screen_on"
602 |
603 |
604 | #### tgc_ev_screen_off="screen_off"
605 |
606 |
607 | #### tgc_ev_timezone="timezone"
608 |
609 |
610 | #### tgc_ev_notification="notification"
611 |
612 |
613 | #### tgc_ev_notification_dismissed="notificationDismissed"
614 |
615 |
616 | #### tgc_ev_notification_action="notificationaction"
617 |
618 |
619 | #### tgc_ev_remote_click="remoteclick"
620 |
621 |
622 |
623 |
624 |
625 | ## External Resources
626 |
627 |
628 |
629 | ### [Android Activity Orientation Table](https://developer.android.com/reference/android/R.attr#screenOrientation)
630 |
631 | | Constant | Description |
632 | |:-----------------|:------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
633 | | behind | Keep the screen in the same orientation as whatever is behind this activity. Corresponds to ActivityInfo.SCREEN_ORIENTATION_BEHIND. |
634 | | fullSensor | Orientation is determined by a physical orientation sensor: the display will rotate based on how the user moves the device. This allows any of the 4 possible rotations, regardless of what the device will normally do (for example some devices won't normally use 180 degree rotation). Corresponds to ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR. |
635 | | fullUser | Respect the user's sensor-based rotation preference, but if sensor-based rotation is enabled then allow the screen to rotate in all 4 possible directions regardless of what the device will normally do (for example some devices won't normally use 180 degree rotation). Corresponds to ActivityInfo.SCREEN_ORIENTATION_FULL_USER. |
636 | | landscape | Would like to have the screen in a landscape orientation: that is, with the display wider than it is tall, ignoring sensor data. Corresponds to ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE. |
637 | | locked | Screen is locked to its current rotation, whatever that is. Corresponds to ActivityInfo.SCREEN_ORIENTATION_LOCKED. |
638 | | nosensor | Always ignore orientation determined by orientation sensor: the display will not rotate when the user moves the device. Corresponds to ActivityInfo.SCREEN_ORIENTATION_NOSENSOR. |
639 | | portrait | Would like to have the screen in a portrait orientation: that is, with the display taller than it is wide, ignoring sensor data. Corresponds to ActivityInfo.SCREEN_ORIENTATION_PORTRAIT. |
640 | | reverseLandscape | Would like to have the screen in landscape orientation, turned in the opposite direction from normal landscape. Corresponds to ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE. |
641 | | reversePortrait | Would like to have the screen in portrait orientation, turned in the opposite direction from normal portrait. Corresponds to ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT. |
642 | | sensor | Orientation is determined by a physical orientation sensor: the display will rotate based on how the user moves the device. Ignores user's setting to turn off sensor-based rotation. Corresponds to ActivityInfo.SCREEN_ORIENTATION_SENSOR. |
643 | | sensorLandscape | Would like to have the screen in landscape orientation, but can use the sensor to change which direction the screen is facing. Corresponds to ActivityInfo.SCREEN_ORIENTATION_SENSOR_LANDSCAPE. |
644 | | sensorPortrait | Would like to have the screen in portrait orientation, but can use the sensor to change which direction the screen is facing. Corresponds to ActivityInfo.SCREEN_ORIENTATION_SENSOR_PORTRAIT. |
645 | | unspecified | No preference specified: let the system decide the best orientation. This will either be the orientation selected by the activity below, or the user's preferred orientation if this activity is the bottom of a task. If the user explicitly turned off sensor based orientation through settings sensor based device rotation will be ignored. If not by default sensor based orientation will be taken into account and the orientation will changed based on how the user rotates the device. Corresponds to ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED. |
646 | | user | Use the user's current preferred orientation of the handset. Corresponds to ActivityInfo.SCREEN_ORIENTATION_USER. |
647 | | userLandscape | Would like to have the screen in landscape orientation, but if the user has enabled sensor-based rotation then we can use the sensor to change which direction the screen is facing. Corresponds to ActivityInfo.SCREEN_ORIENTATION_USER_LANDSCAPE. |
648 | | userPortrait | Would like to have the screen in portrait orientation, but if the user has enabled sensor-based rotation then we can use the sensor to change which direction the screen is facing. Corresponds to ActivityInfo.SCREEN_ORIENTATION_USER_PORTRAIT. |
649 |
650 |
651 |
652 | ## Bugs
653 | Report bugs as GitHub issues:
654 |
655 |
656 | ## Author
657 | Tarek Sander
658 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Termux:GUI Bash
2 | Bash library for Termux:GUI.
3 |
4 | [Documentation](Manual.md)
5 |
6 | [Tutorial](TUTORIAL.md)
7 |
8 | ### Installing
9 |
10 | #### With `pkg`
11 |
12 | Use `pkg install termux-gui-bash` to install.
13 |
14 | #### From Source
15 |
16 | Additional dependency: CMake
17 |
18 | ````bash
19 | git clone https://github.com/tareksander/termux-gui-bash.git
20 | cd termux-gui-bash
21 | cmake . -DCMAKE_INSTALL_PREFIX=$PREFIX
22 | make install
23 | ````
24 |
25 | ### Dependencies
26 |
27 | Only need to be installed manually when building from source.
28 |
29 | - [jq](https://github.com/stedolan/jq)
30 | - Bash (should be installed by default in Termux)
31 |
32 | ### License
33 |
34 | The license is the [Mozilla Public License 2.0](https://www.mozilla.org/en-US/MPL/2.0/).
35 | TL;DR: You can use this library in your own projects, regardless of the license you choose for it. Modifications to this
36 | library have to be published under the MPL 2.0 (or a GNU license in some cases) though.
37 |
38 |
--------------------------------------------------------------------------------
/TUTORIAL.md:
--------------------------------------------------------------------------------
1 | # Bash Library Tutorial
2 |
3 | Make sure you installed the library like explained in the README.
4 | This tutorial assumes you have the basic understanding of the Android GUI from
5 | the [crash course](https://github.com/termux/termux-gui).
6 | The full source code can also be found in the tutorial folder.
7 |
8 | ## Loading the library
9 |
10 | To use the library, you have 2 options:
11 | - Use the shebang `#!/bin/tgui-bash` instead of `#!/bin/bash`. The library will initialize itself and then load your script.
12 | - Exec tgui-bash with your script path as argument when tgui-bash is not loaded: `! [ -v tgc_activity_tid ] && exec tgui-bash "${BASH_SOURCE[0]}" "$@"`.
13 |
14 | The library exits when your script exits, and all remaining Activities are cleaned up by the Plugin after that.
15 |
16 |
17 | ## Hello World
18 |
19 | ````bash
20 | #!/bin/tgui-bash
21 |
22 | set -u
23 |
24 | # Parameters for the Activity, can be empty
25 | declare -A aparams=()
26 | # Array to store the Activity id and Task id in
27 | declare -a activity=()
28 |
29 | # Start the Activity
30 | tg_activity_new aparams activity
31 |
32 | # Get the Activity id from the array as a shortcut
33 | aid="${activity[0]}"
34 |
35 | # Parameters for creating a TextView, in this case the initial text.
36 | # For the keys there are constants, to help with IDE autocompletion and
37 | # to make it obvious when you mistyped.
38 | declare -A tparams=([${tgc_create_text}]="Hello World!")
39 |
40 | # Create the TextView
41 | tg_create_text "$aid" tparams
42 |
43 | # Wait 2 seconds before exiting
44 | sleep 2
45 | ````
46 |
47 | [hello_world.sh](tutorial/hello_world.sh)
48 |
49 |
50 | ## Events
51 |
52 |
53 | In a GUI, you want to react to events caused by the user.
54 | In this library you have the option to poll for events (not recommended) with `tg_msg_recv_event`
55 | and to wait for events with `tg_msg_recv_event_blocking`.
56 | To process events, you have some functions and `jq` available to get the information you need.
57 | Though for most of the events you only need to know that the `.` operator in jq accesses a value of an object.
58 | With that, you can parse the events you need according to the [protocol definition](https://github.com/termux/termux-gui/blob/main/Protocol.md#events).
59 |
60 |
61 |
62 | ````bash
63 | #!/bin/tgui-bash
64 |
65 | set -u
66 |
67 | declare -A aparams=()
68 | declare -a activity=()
69 |
70 | tg_activity_new aparams activity
71 |
72 | aid="${activity[0]}"
73 |
74 | # Parameters for creating a Button, in this case the text.
75 | declare -A bparams=([${tgc_create_text}]="Hello World!")
76 |
77 | # Create the Button and save the id
78 | b="$(tg_create_button "$aid" bparams)"
79 |
80 | while true; do
81 | ev="$(tg_msg_recv_event_blocking)"
82 |
83 | # Print when the button is pressed
84 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_click" ] && [ "$(tg_event_id "$ev")" = "$b" ]; then
85 | echo "Button pressed!"
86 | fi
87 |
88 | # Exit when the Activity is closed
89 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_destroy" ]; then
90 | exit 0
91 | fi
92 | done
93 | ````
94 |
95 | [events.sh](tutorial/events.sh)
96 |
97 | ## Layout hierarchy
98 |
99 | To arrange Views you need to use Layouts. The simplest one is LinearLayout.
100 |
101 | ````bash
102 | #!/bin/tgui-bash
103 |
104 | set -u
105 |
106 | declare -A aparams=()
107 | declare -a activity=()
108 |
109 | tg_activity_new aparams activity
110 |
111 | aid="${activity[0]}"
112 |
113 |
114 | declare -A lparams=()
115 |
116 | # Create the LinearLayout and save the id
117 | layout="$(tg_create_linear "$aid" lparams)"
118 |
119 | # Create Buttons in the Layout
120 | declare -A bparams=()
121 | for i in {1..5}; do
122 | bparams[$tgc_create_text]=$i
123 | tg_create_button "$aid" bparams "$layout" >/dev/null
124 | done
125 |
126 | while true; do
127 | ev="$(tg_msg_recv_event_blocking)"
128 | # Exit when the Activity is closed
129 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_destroy" ]; then
130 | exit 0
131 | fi
132 | done
133 | ````
134 |
135 | [linearlayout.sh](tutorial/linearlayout.sh)
136 |
137 | ## Images and picture-in-picture
138 |
139 | You can display images in PNG or JPEG format by base43-encoding them.
140 | The `base64` command is preinstalled in Termux.
141 | To generate the image string you should use `img="$(base64 -w 0 )"`.
142 |
143 | Picture-in-picture mode allows you to show the Activity in a small overlay window.
144 |
145 |
146 | ````bash
147 | #!/bin/tgui-bash
148 |
149 | set -u
150 |
151 | # Base64-encoded image of the Termux banner
152 | banner="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"
153 |
154 | # Let the Activity start in picture-in-picture mode
155 | declare -A aparams=([$tgc_activity_pip]="true")
156 | declare -a activity=()
157 |
158 | tg_activity_new aparams activity
159 |
160 | aid="${activity[0]}"
161 |
162 | # set the aspect ratio to that of the image
163 | tg_activity_pip_params "$aid" "320" "180"
164 |
165 | declare -A imgparams=()
166 |
167 | # Create an ImageView and save the id
168 | img="$(tg_create_image "$aid" imgparams)"
169 |
170 | # Set the image
171 | tg_view_image "$aid" "$img" "$banner"
172 |
173 | while true; do
174 | ev="$(tg_msg_recv_event_blocking)"
175 | # Exit when the user leaves
176 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_stop" ]; then
177 | exit 0
178 | fi
179 | done
180 | ````
181 |
182 | [image.sh](tutorial/image.sh)
183 |
184 | ## Dialogs & Inputs
185 |
186 | An Activity can also be shown as a dialog.
187 | This make for a great user experience with Termux, as exiting the dialog drops you right back into the terminal without animation.
188 |
189 |
190 | ````bash
191 | #!/bin/tgui-bash
192 |
193 | set -u
194 |
195 |
196 | # Let the Activity start as a dialog
197 | declare -A aparams=([$tgc_activity_dialog]="true")
198 | declare -a activity=()
199 |
200 | tg_activity_new aparams activity
201 |
202 | aid="${activity[0]}"
203 |
204 | declare -A params=()
205 |
206 | layout="$(tg_create_linear "$aid" params)"
207 |
208 | # EditText
209 | et="$(tg_create_edit "$aid" params "$layout")"
210 |
211 | params[$tgc_create_text]="Click me!"
212 | echo "${params[@]}"
213 | # Button
214 | bt="$(tg_create_button "$aid" params "$layout")"
215 |
216 | #unset "params[$tgc_create_text]"
217 | declare -a list=("Option 1" "Option 2" "Option 3" "Option 4")
218 |
219 | # Spinner
220 | sp="$(tg_create_spinner "$aid" params "$layout")"
221 | # Set the options
222 | tg_view_list "$aid" "$sp" list
223 |
224 | # Toggle
225 | tg="$(tg_create_toggle "$aid" params "$layout")"
226 |
227 | params[$tgc_create_text]="Switch"
228 |
229 | # Switch
230 | sw="$(tg_create_switch "$aid" params "$layout")"
231 |
232 |
233 | params[$tgc_create_text]="Checkbox"
234 | # CheckBox
235 | cb="$(tg_create_checkbox "$aid" params "$layout")"
236 |
237 | # Group for RadioButtons
238 | rg="$(tg_create_radio_group "$aid" params "$layout")"
239 |
240 | # Create some RadioButtons
241 | # RadioButtons have to be in a RadioGroup to work
242 | params[$tgc_create_text]="RadioButton 1"
243 | rb1="$(tg_create_radio "$aid" params "$rg")"
244 |
245 | params[$tgc_create_text]="RadioButton 2"
246 | rb2="$(tg_create_radio "$aid" params "$rg")"
247 |
248 | params[$tgc_create_text]="RadioButton 3"
249 | rb3="$(tg_create_radio "$aid" params "$rg")"
250 |
251 |
252 | while true; do
253 | ev="$(tg_msg_recv_event_blocking)"
254 | # Exit when the user leaves
255 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_stop" ]; then
256 | exit 0
257 | fi
258 | # Print out the EditText text when the Button gets clicked
259 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_click" ] && [ "$(tg_event_aid "$ev")" = "$aid" ] && [ "$(tg_event_id "$ev")" = "$bt" ]; then
260 | echo "EditText text: '$(tg_view_get_text "$aid" "$et")'"
261 | fi
262 | # Print the RadioButton id that is selected
263 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_selected" ] && [ "$(tg_event_aid "$ev")" = "$aid" ] && [ "$(tg_event_id "$ev")" = "$rg" ]; then
264 | echo "RadioButton pressed: $(echo "$ev" | jq -r '.value.selected')"
265 | fi
266 | # Print the checked state of other button on click
267 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_click" ] && [ "$(tg_event_aid "$ev")" = "$aid" ] && [ "$(tg_event_id "$ev")" = "$cb" ]; then
268 | echo "CheckBox pressed: $(echo "$ev" | jq -r '.value.set')"
269 | fi
270 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_click" ] && [ "$(tg_event_aid "$ev")" = "$aid" ] && [ "$(tg_event_id "$ev")" = "$sw" ]; then
271 | echo "Switch pressed: $(echo "$ev" | jq -r '.value.set')"
272 | fi
273 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_click" ] && [ "$(tg_event_aid "$ev")" = "$aid" ] && [ "$(tg_event_id "$ev")" = "$tg" ]; then
274 | echo "ToggleButton pressed: $(echo "$ev" | jq -r '.value.set')"
275 | fi
276 | # Print the selected Spinner option
277 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_item_selected" ] && [ "$(tg_event_aid "$ev")" = "$aid" ] && [ "$(tg_event_id "$ev")" = "$sp" ]; then
278 | echo "Spinner option: '$(echo "$ev" | jq -r '.value.selected')'"
279 | fi
280 | done
281 | ````
282 |
283 | [dialog.sh](tutorial/dialog.sh)
284 |
285 |
286 |
287 | ## Nested Layouts & Scrolling
288 |
289 | By default, LinearLayouts arrange their children vertically.
290 | To create e.g. a bar at the top, you can override this with `$tgc_create_vertical`.
291 | To create a bar however, you should also set the height of the nested layout to `$tgc_view_wrap_content`,
292 | and the layout weight to 0, so it only takes up the space of its children.
293 | Nested layouts can also be used for content in NestedScrollViews, when you can't be sure if the content will fit on the screen.
294 |
295 |
296 | ````bash
297 | #!/bin/tgui-bash
298 |
299 | set -u
300 |
301 |
302 | # Let the Activity start as a dialog
303 | declare -A aparams=()
304 | declare -a activity=()
305 |
306 | tg_activity_new aparams activity
307 |
308 | aid="${activity[0]}"
309 |
310 | declare -A params=()
311 |
312 | layout="$(tg_create_linear "$aid" params)"
313 |
314 |
315 | # Create a Horizontal LinearLayout
316 | params[$tgc_create_vertical]=false
317 |
318 | bar="$(tg_create_linear "$aid" params "$layout")"
319 |
320 | unset "params[$tgc_create_vertical]"
321 |
322 | # Set the height no the minimum needed
323 | tg_view_height "$aid" "$bar" "$tgc_view_wrap_content"
324 | # Don't let it expand to unused space
325 | tg_view_linear "$aid" "$bar" 0
326 |
327 | # Create 2 Buttons in the bar
328 | params[$tgc_create_text]="Bar button 1"
329 | bt1="$(tg_create_button "$aid" params "$bar")"
330 |
331 | params[$tgc_create_text]="Bar button 2"
332 | bt2="$(tg_create_button "$aid" params "$bar")"
333 |
334 | unset "params[$tgc_create_text]"
335 |
336 |
337 | # Create a NestedScrollView and a LinearLayout in it
338 | sc="$(tg_create_nested_scroll "$aid" params "$layout")"
339 | scl="$(tg_create_linear "$aid" params "$sc")"
340 |
341 | # Create Buttons in the NestedScrollView
342 | for i in {1..30}; do
343 | params[$tgc_create_text]="Button $i"
344 | tg_create_button "$aid" params "$scl" >/dev/null
345 | done
346 |
347 |
348 | while true; do
349 | ev="$(tg_msg_recv_event_blocking)"
350 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_destroy" ]; then
351 | exit 0
352 | fi
353 | done
354 | ````
355 |
356 | [scroll.sh](tutorial/scroll.sh)
357 |
358 |
359 | ## Widgets
360 |
361 | Termux:GUI allows you to create widgets which programs can fill.
362 | The methods for widgets are slightly different, because Android doesn't support as much functionality for widgets.
363 |
364 |
365 | ````bash
366 | #!/bin/tgui-bash
367 |
368 | set -u
369 |
370 |
371 | # Let the Activity start as a dialog
372 | declare -A aparams=()
373 | declare -a activity=()
374 |
375 | tg_activity_new aparams activity
376 |
377 | aid="${activity[0]}"
378 |
379 | declare -A params=()
380 |
381 | layout="$(tg_create_linear "$aid" params)"
382 |
383 |
384 | widfield="$(tg_create_edit "$aid" params "$layout")"
385 |
386 | textfield="$(tg_create_edit "$aid" params "$layout")"
387 |
388 |
389 | params[$tgc_create_text]="Set widget text"
390 |
391 | b="$(tg_create_button "$aid" params "$layout")"
392 |
393 |
394 | while true; do
395 | ev="$(tg_msg_recv_event_blocking)"
396 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_destroy" ]; then
397 | exit 0
398 | fi
399 | if [ "$(tg_event_type "$ev")" = "$tgc_ev_click" ] && [ "$(tg_event_id "$ev")" = "$b" ]; then
400 | # Get the widget id
401 | wid="$(tg_view_get_text "$aid" "$widfield")"
402 | text="$(tg_view_get_text "$aid" "$textfield")"
403 | # Create a remote layout and TextView
404 | rl="$(tg_remote_create_layout)"
405 | rt="$(tg_remote_create_text "$rl")"
406 | # Set the text
407 | tg_remote_text "$rl" "$rt" "$text"
408 | # Set the widget layout and destroy the remote layout again
409 | tg_widget_layout "$rl" "$wid"
410 | tc_remote_delete_layout "$rl"
411 | fi
412 | done
413 | ````
414 |
415 | If you want to see full programs using this, look at [the examples](https://github.com/tareksander/termux-gui-bash/tree/main/examples).
416 |
417 |
418 |
--------------------------------------------------------------------------------
/doc_html/manual-dark.html.gz:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tareksander/termux-gui-bash/4555edfc75a8432f6c564facd09e0f8ba0b7a82d/doc_html/manual-dark.html.gz
--------------------------------------------------------------------------------
/doc_html/manual-light.html.gz:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tareksander/termux-gui-bash/4555edfc75a8432f6c564facd09e0f8ba0b7a82d/doc_html/manual-light.html.gz
--------------------------------------------------------------------------------
/doc_html/tutorial-dark.html.gz:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tareksander/termux-gui-bash/4555edfc75a8432f6c564facd09e0f8ba0b7a82d/doc_html/tutorial-dark.html.gz
--------------------------------------------------------------------------------
/doc_html/tutorial-light.html.gz:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/tareksander/termux-gui-bash/4555edfc75a8432f6c564facd09e0f8ba0b7a82d/doc_html/tutorial-light.html.gz
--------------------------------------------------------------------------------
/doc_templates/doctemplate.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | $for(author-meta)$
8 |
9 | $endfor$
10 | $if(date-meta)$
11 |
12 | $endif$
13 | $if(keywords)$
14 |
15 | $endif$
16 | $if(title-prefix)$$title-prefix$ – $endif$$pagetitle$
17 |
20 | $for(css)$
21 |
22 | $endfor$
23 | $if(math)$
24 | $math$
25 | $endif$
26 | $for(header-includes)$
27 | $header-includes$
28 | $endfor$
29 |
30 |
31 | $for(include-before)$
32 | $include-before$
33 | $endfor$
34 | $if(title)$
35 |
36 |