File indexing completed on 2024-03-24 16:01:40

0001 #
0002 #  SPDX-License-Identifier: GPL-3.0-or-later
0003 #
0004 # Helper function for extracting translatable messages from Krita source code.
0005 # Usage: kundo2_aware_xgettext <pot-filename-without-path> <source-files-list>
0006 # If there are no messages or the <source-files-list> is empty, the pot file is deleted.
0007 #
0008 # Example usage that creates $podir/myapp.pot file:
0009 #     kundo2_aware_xgettext myapp.pot `find . -name \*.cpp -o -name \*.h`
0010 #
0011 function kundo2_aware_xgettext() {
0012     POTFILE="$podir/$1"
0013     shift
0014     if test -n "$*"; then
0015         # we rely on last line being a 'msgstr' signaling that strings has been extracted (a header is always present)
0016         # normally it ends with 'msgstr ""' but if plural it can end with eg 'msgstr[1] ""'
0017         kundo2_aware_xgettext_internal $* | tee "${POTFILE}" | tail -n1 | grep "^msgstr" > /dev/null \
0018             || rm -f "${POTFILE}" 2> /dev/null
0019     fi
0020 }
0021 
0022 # How to unit test:
0023 #   export podir=.
0024 #   cp init-sample.pot sample.pot
0025 #   source krita_xgettext.sh
0026 #   add_ctxt_qtundo sample.pot
0027 #
0028 #   Then check that all messages in sample.pot have "(qtundo-format)" in msgctxt.
0029 function add_ctxt_qtundo() {
0030     POT_PART_QUNDOFORMAT="$1"
0031     POT_PART_QUNDOFORMAT2="`mktemp $podir/_qundoformat2_XXXXXXXX.pot`"
0032 
0033     # Prepend "(qtundo-format)" to existing msgctxt properties of messages
0034     sed -i -e 's/^msgctxt "/msgctxt "(qtundo-format) /' "${POT_PART_QUNDOFORMAT}"
0035 
0036     # Add msgctxt "(qtundo-format)" to messages not having msgctxt yet
0037     #
0038     # lastLine != "#, fuzzy" is the check for the .pot header.
0039     # If lastLine starts with '"' the msgctxt has been split on several lines and is treated by sed above, so skip it
0040     mv "${POT_PART_QUNDOFORMAT}" "${POT_PART_QUNDOFORMAT2}"
0041     cat "${POT_PART_QUNDOFORMAT2}" | awk '
0042         /^msgid "/ {
0043             if (lastLine !~ /^"/ && lastLine !~ /^msgctxt/ && lastLine != "#, fuzzy") {
0044                 print "msgctxt \"(qtundo-format)\""
0045             }
0046         }
0047         { print ; lastLine = $0 }' > "${POT_PART_QUNDOFORMAT}"
0048 
0049     rm -f "${POT_PART_QUNDOFORMAT2}"
0050 }
0051 
0052 function kundo2_aware_xgettext_internal() {
0053     SRC_FILES="$*"
0054     POT_PART_NORMAL="`mktemp $podir/_normal_XXXXXXXX.pot`"
0055     POT_PART_QUNDOFORMAT="`mktemp $podir/_qundoformat_XXXXXXXX.pot`"
0056     POT_MERGED="`mktemp $podir/_merged_XXXXXXXX.pot`"
0057 
0058     $XGETTEXT ${CXG_EXTRA_ARGS} ${SRC_FILES} -o "${POT_PART_NORMAL}" --force-po
0059 
0060     XGETTEXT_FLAGS_KUNDO2="\
0061 --copyright-holder=This_file_is_part_of_KDE \
0062 --msgid-bugs-address=http://bugs.kde.org \
0063 --from-code=UTF-8
0064 -C -k --kde \
0065 -kkundo2_i18n:1 -kkundo2_i18np:1,2 -kkundo2_i18nc:1c,2 -kkundo2_i18ncp:1c,2,3 \
0066 "
0067 
0068     $XGETTEXT_PROGRAM ${XGETTEXT_FLAGS_KUNDO2} ${CXG_EXTRA_ARGS} ${SRC_FILES} -o "${POT_PART_QUNDOFORMAT}"
0069 
0070     if [ $(cat ${POT_PART_NORMAL} ${POT_PART_QUNDOFORMAT} | grep -c \(qtundo-format\)) != 0 ]; then
0071         echo "ERROR: Context '(qtundo-format)' should not be added manually. Use kundo2_i18n*() calls instead." 1>&2
0072         exit 17
0073     fi
0074 
0075     if [ -s "${POT_PART_QUNDOFORMAT}" ]; then
0076         add_ctxt_qtundo "${POT_PART_QUNDOFORMAT}"
0077     fi
0078 
0079     if [ -s "${POT_PART_NORMAL}" -a -s "${POT_PART_QUNDOFORMAT}" ]; then
0080         # ensure an empty line or else KDE_HEADER search will fail
0081         # in case POT_PART_NORMAL only contains header
0082         echo "" >>${POT_PART_NORMAL}
0083 
0084         ${MSGCAT} -F "${POT_PART_NORMAL}" "${POT_PART_QUNDOFORMAT}" > ${POT_MERGED}
0085         MERGED_HEADER_LINE_COUNT=$(cat ${POT_MERGED} | grep "^$" -B 100000 --max-count=1 | wc -l)
0086         KDE_HEADER="$(cat ${POT_PART_NORMAL} | grep "^$" -B 100000 --max-count=1)"
0087         MERGED_TAIL="$(cat ${POT_MERGED} | tail -n +$MERGED_HEADER_LINE_COUNT)"
0088 
0089         # Print out the resulting .pot
0090         echo "$KDE_HEADER"
0091         echo "$MERGED_TAIL"
0092     elif [ -s "${POT_PART_NORMAL}" ]; then
0093         echo "# POT_PART_NORMAL only"
0094         cat "${POT_PART_NORMAL}"
0095     elif [ -s "${POT_PART_QUNDOFORMAT}" ]; then
0096         echo "# POT_PART_QUNDOFORMAT only"
0097         cat "${POT_PART_QUNDOFORMAT}"
0098     fi
0099 
0100     rm -f "${POT_PART_NORMAL}" "${POT_PART_QUNDOFORMAT}" "${POT_MERGED}"
0101 }
0102 
0103 # Sets EXCLUDE variable to excludes compatible with the find(1) command, e.g. '-path a -o -path b'.
0104 # To unconditionally exclude dir (with subdirs) just put an empty file .i18n in it.
0105 # To disable excluding for given file, e.g. foo.pot, add "foo.pot" line to the .i18n file.
0106 function find_exclude() {
0107     EXCLUDE=""
0108     for f in `find . -name .i18n | sed 's/\/\.i18n$//g' | sort`; do
0109         if ! grep -q "^${1}$" "$f/.i18n" ; then
0110             if [ -n "$EXCLUDE" ] ; then EXCLUDE="$EXCLUDE -o " ; fi
0111             EXCLUDE="$EXCLUDE -path $f"
0112         fi
0113     done
0114     if [ -z "$EXCLUDE" ] ; then EXCLUDE="-path __dummy__" ; fi # needed because -prune in find needs args
0115 }