-
Notifications
You must be signed in to change notification settings - Fork 6
Expand file tree
/
Copy pathOCR4Linux.sh
More file actions
executable file
·346 lines (314 loc) · 11 KB
/
OCR4Linux.sh
File metadata and controls
executable file
·346 lines (314 loc) · 11 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
#!/bin/bash
# ========================================================================================================================
# Author: Mohamed Hussein Al-Adawy
# Version: 1.5.0
# Description:
# OCR4Linux is a versatile text extraction tool for Linux systems that:
# 1. Takes screenshots of selected areas using:
# - grimblast for Wayland sessions
# - scrot for X11 sessions
# 2. Performs Optical Character Recognition (OCR) using tesseract by passing the screenshot to a Python script
# 3. Copies extracted text to clipboard using:
# - wl-copy and cliphist for Wayland
# - xclip for X11
#
# Features:
# - Support for both Wayland and X11 sessions
# - Configurable screenshot directory
# - Optional logging functionality
# - Optional screenshot retention
# - Command-line interface with various options
#
# Dependencies:
# - tesseract-ocr: For text extraction
# - grimblast/scrot: For screenshot capture
# - wl-clipboard/xclip: For clipboard operations
# - rofi: For language selection menu
# - Python 3.x: For image processing
#
# Usage:
# ./OCR4Linux.sh [-r] [-d DIRECTORY] [-l] [-h]
# See './OCR4Linux.sh -h' for more details
# ========================================================================================================================
SCREENSHOT_NAME="screenshot_$(date +%d%m%Y_%H%M%S).jpg"
SCREENSHOT_DIRECTORY="$HOME/Pictures/screenshots"
# Get the absolute path of the script itself, handling symlinks
SCRIPT_PATH=$(realpath "$0")
# Extract the directory part
OCR4Linux_HOME="$(dirname "$SCRIPT_PATH")"
OCR4Linux_PYTHON_NAME="OCR4Linux.py"
OCR4Linux_CONFIG="$HOME/.config/OCR4Linux"
TEXT_OUTPUT_FILE_NAME="$OCR4Linux_CONFIG/output_text.txt"
LOGS_FILE_NAME="$OCR4Linux_CONFIG/OCR4Linux.log"
SLEEP_DURATION=0.5
REMOVE_SCREENSHOT=false
KEEP_LOGS=false
SHOW_NOTIFICATION=false
LANG_SPECIFIED=false
SPECIFIED_LANGS=""
VERSION="v1.5.0"
langs=()
# Add log function
log_message() {
local message
message="[$(date '+%Y-%m-%d %H:%M:%S')] $1"
echo "$message" >&2
if [ "$KEEP_LOGS" = true ]; then
{
echo "$message"
} >>"$LOGS_FILE_NAME"
fi
}
# Display help message
show_help() {
echo "Usage: $(basename "$0") [OPTIONS]"
echo "Options:"
echo " -r Remove screenshot in the screenshot directory"
echo " -d DIRECTORY Set screenshot directory (default: $SCREENSHOT_DIRECTORY)"
echo " -l Keep logs"
echo " -n | --notify Show notification after taking the screenshot"
echo " --lang LANGUAGES Specify OCR languages (e.g., 'all', 'eng', 'eng+ara')"
echo " -v | --version Print the package version, then exist"
echo " -h | --help Show this help message, then exit"
echo "Example:"
echo " OCR4Linux.sh -d $HOME/screenshots -l"
echo " OCR4Linux.sh --notify"
echo " OCR4Linux.sh --lang eng+ara"
echo " OCR4Linux.sh --lang all -l"
echo " OCR4Linux.sh -h"
echo " OCR4Linux.sh -v"
echo "Note:"
echo " - If --lang is not specified, an interactive language selection menu will appear"
echo " - Use 'all' to select all available languages"
echo " - Use '+' to separate multiple languages (e.g., 'eng+ara+fra')"
echo " - Without arguments, screenshots are saved to $SCREENSHOT_DIRECTORY"
}
# Parse command line arguments
while [[ $# -gt 0 ]]; do
case $1 in
-r)
REMOVE_SCREENSHOT=true
shift
;;
-d)
SCREENSHOT_DIRECTORY="$2"
shift 2
;;
-l)
KEEP_LOGS=true
shift
;;
-n|--notify)
SHOW_NOTIFICATION=true
shift
;;
--lang)
SPECIFIED_LANGS="$2"
LANG_SPECIFIED=true
shift 2
;;
-h|--help)
show_help
exit 0
;;
-v|--version)
echo "${VERSION}"
exit 0
;;
*)
echo "Unknown option: $1"
show_help
exit 1
;;
esac
done
# Check if the required files/binaries exist.
check_if_requirements_exists() {
log_message "Checking required files and directories..."
# Check if rofi is installed
if ! command -v rofi &>/dev/null; then
log_message "ERROR: rofi is not installed. Please install rofi to use language selection."
exit 1
fi
# Validate screenshot directory
if [ ! -d "$SCREENSHOT_DIRECTORY" ]; then
log_message "Creating screenshot directory: $SCREENSHOT_DIRECTORY since it does not exist."
if ! mkdir -p "$SCREENSHOT_DIRECTORY"; then
log_message "ERROR: Failed to create directory $SCREENSHOT_DIRECTORY"
exit 1
fi
log_message "Successfully created screenshot directory: $SCREENSHOT_DIRECTORY"
fi
# Check if the directory is writable
if [ ! -w "$SCREENSHOT_DIRECTORY" ]; then
log_message "ERROR: $SCREENSHOT_DIRECTORY is not writable"
exit 1
fi
# Check if the python script exists.
if [ ! -f "$OCR4Linux_HOME/$OCR4Linux_PYTHON_NAME" ]; then
log_message "ERROR: $OCR4Linux_PYTHON_NAME not found in $OCR4Linux_HOME"
exit 1
fi
# Validate config directory
if [ ! -d "$OCR4Linux_CONFIG" ]; then
log_message "Creating config directory: $OCR4Linux_CONFIG since it does not exist."
if ! mkdir -p "$OCR4Linux_CONFIG"; then
log_message "ERROR: Failed to create directory $OCR4Linux_CONFIG"
exit 1
fi
log_message "Successfully created config directory: $OCR4Linux_CONFIG"
fi
# Check if the directory is writable
if [ ! -w "$OCR4Linux_CONFIG" ]; then
log_message "ERROR: $OCR4Linux_CONFIG is not writable"
exit 1
fi
}
# Process specified languages from command line
process_specified_langs() {
log_message "Processing specified languages: $SPECIFIED_LANGS"
# Handle "all" case
if [[ "$SPECIFIED_LANGS" == "all" ]]; then
mapfile -t langs < <(tesseract --list-langs | awk 'FNR>1')
log_message "Using ALL available languages: $(
IFS=+
echo "${langs[*]}"
)"
else
# Split the language string by '+' and populate the langs array
IFS='+' read -ra langs <<<"$SPECIFIED_LANGS"
log_message "Using specified languages: $(
IFS=+
echo "${langs[*]}"
)"
# Validate that the specified languages are available
available_langs=$(tesseract --list-langs | awk 'FNR>1')
for lang in "${langs[@]}"; do
if ! echo "$available_langs" | grep -q "^$lang$"; then
log_message "WARNING: Language '$lang' is not available on this system"
fi
done
fi
}
# Choose languages for OCR using rofi
choose_lang() {
log_message "Fetching available languages for OCR selection..."
# Get available languages and add "ALL" option at the beginning
mapfile -t langs < <(tesseract --list-langs | awk 'BEGIN {print "ALL" } FNR>1' | rofi -dmenu -multi-select -p "Select OCR Languages:")
if [ ${#langs[@]} -eq 0 ]; then
log_message "CANCELLED: User aborted language selection"
exit 1
fi
# If "ALL" is selected, use all available languages
if [[ " ${langs[*]} " =~ " ALL " ]]; then
mapfile -t langs < <(tesseract --list-langs | awk 'FNR>1')
log_message "Selected ALL languages: $(
IFS=+
echo "${langs[*]}"
)"
else
log_message "Selected languages: $(
IFS=+
echo "${langs[*]}"
)"
fi
}
# take shots using grimblast for wayland
takescreenshot_wayland() {
log_message "Taking screenshot using grimblast for Wayland..."
sleep $SLEEP_DURATION
if [ "$SHOW_NOTIFICATION" = true ]; then
grimblast --notify copysave area "$SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME"
else
grimblast copysave area "$SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME"
fi
log_message "Screenshot saved to $SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME in wayland session"
}
# take shots using scrot for x11
takescreenshot_x11() {
log_message "Taking screenshot using scrot for X11..."
sleep $SLEEP_DURATION
scrot -s -Z 0 -o -F "$SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME"
if [ "$SHOW_NOTIFICATION" = true ]; then
notify-send "OCR4Linux" "Screenshot saved to $SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME" -i camera-photo
fi
log_message "Screenshot saved to $SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME in x11 session"
}
# Run the screenshot functions based on the session type.
takescreenshot() {
if [ "$XDG_SESSION_TYPE" = "wayland" ]; then
takescreenshot_wayland
else
takescreenshot_x11
fi
}
# Pass the screenshot to OCR tool to extract text from the image.
extract_text() {
# Create language string for passing to Python script
local lang_string=""
if [ ${#langs[@]} -gt 0 ]; then
lang_string=$(
IFS=+
echo "${langs[*]}"
)
fi
if [ -n "$lang_string" ]; then
python "$OCR4Linux_HOME/$OCR4Linux_PYTHON_NAME" \
"$SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME" \
"$TEXT_OUTPUT_FILE_NAME" \
--langs "$lang_string"
else
python "$OCR4Linux_HOME/$OCR4Linux_PYTHON_NAME" \
"$SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME" \
"$TEXT_OUTPUT_FILE_NAME"
fi
log_message "Text extraction completed successfully"
}
# Copy the extracted text to clipboard using wl-copy and cliphist.
copy_to_wayland_clipboard() {
log_message "Copying extracted text to Wayland clipboard using wl-copy and cliphist..."
cliphist store <"$TEXT_OUTPUT_FILE_NAME"
cliphist list | head -n 1 | cliphist decode | wl-copy
log_message "Extracted text copied to Wayland clipboard successfully."
}
# Copy the extracted text to clipboard using xclip.
copy_to_x11_clipboard() {
log_message "Copying extracted text to X11 clipboard using xclip..."
xclip -selection clipboard -i "$TEXT_OUTPUT_FILE_NAME"
xclip -selection primary -i "$TEXT_OUTPUT_FILE_NAME"
log_message "Extracted text copied to X11 clipboard successfully."
}
# Run the copy to clipboard functions based on the session type.
run_copy_to_clipboard() {
if [ "$XDG_SESSION_TYPE" = "wayland" ]; then
copy_to_wayland_clipboard
else
copy_to_x11_clipboard
fi
rm "$TEXT_OUTPUT_FILE_NAME"
log_message "The extracted text has been copied to the clipboard."
}
# Remove the screenshot if the -r option is passed.
remove_image() {
if [ "$REMOVE_SCREENSHOT" = true ]; then
rm "$SCREENSHOT_DIRECTORY/$SCREENSHOT_NAME"
log_message "Screenshot $SCREENSHOT_NAME has been deleted since you passed the -l option."
fi
}
# Run the functions
main() {
check_if_requirements_exists
# Handle language selection
if [ "$LANG_SPECIFIED" = true ]; then
process_specified_langs
else
choose_lang
fi
takescreenshot
extract_text
run_copy_to_clipboard
remove_image
log_message "The script has finished successfully."
log_message "====================================================================================================="
}
main