Changes related to text input on Android, general bug fixes, license change to GPLv3

This commit is contained in:
Yousef Khadadeh 2026-05-11 23:06:39 +03:00
parent 8b3e321ab5
commit fc8f414b67
308 changed files with 8707 additions and 440 deletions

View file

@ -1,3 +1,21 @@
/*
* InfiniPaint
* Copyright (C) 2025-2026 Yousef Khadadeh
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#include "ParagraphStyleData.hpp"
namespace RichText {

View file

@ -1,3 +1,21 @@
/*
* InfiniPaint
* Copyright (C) 2025-2026 Yousef Khadadeh
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#pragma once
#include <modules/skparagraph/include/ParagraphStyle.h>

View file

@ -1,3 +1,21 @@
/*
* InfiniPaint
* Copyright (C) 2025-2026 Yousef Khadadeh
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#include "TextBox.hpp"
#include "Helpers/Networking/ByteStream.hpp"
#include "TextStyleModifier.hpp"
@ -360,6 +378,68 @@ TextPosition TextBox::get_text_pos_closest_to_point(Vector2f point) {
return TextPosition{pIndex, 0};
}
int TextBox::get_codepoint_location_from_text_position(TextPosition pos) {
pos = move(Movement::NOWHERE, pos);
std::string str = get_string();
size_t bytePos = get_byte_pos_from_text_pos(pos);
const char* utf8StartPtr = str.c_str();
const char* utf8EndPtr = str.c_str() + bytePos;
const char* utf8StringEndPtr = str.c_str() + str.size();
int i = 0;
for(; utf8StartPtr < utf8EndPtr; i++) {
SkUnichar u = SkUTF::NextUTF8(&utf8StartPtr, utf8StringEndPtr);
if(u == -1)
return 0;
}
return i;
}
TextPosition TextBox::get_text_position_from_codepoint_location(int p) {
std::string str = get_string();
const char* utf8StartPtr = str.c_str();
const char* utf8StringEndPtr = str.c_str() + str.size();
for(int i = 0; i < p; i++) {
SkUnichar u = SkUTF::NextUTF8(&utf8StartPtr, utf8StringEndPtr);
if(u == -1)
return move(Movement::HOME, {0, 0});
else if(utf8StartPtr == utf8StringEndPtr)
return move(Movement::END, {0, 0});
}
size_t bytePos = utf8StartPtr - str.c_str();
return get_text_pos_from_byte_pos(str, bytePos);
}
int TextBox::get_utf16_location_from_codepoint_location(int p) {
std::string u8s = get_string();
std::u16string str = SkUnicodes::ICU::Make()->convertUtf8ToUtf16(u8s.c_str(), u8s.length());
const uint16_t* utf16StartPtr = reinterpret_cast<const uint16_t*>(str.data());
const uint16_t* utf16StringEndPtr = reinterpret_cast<const uint16_t*>(str.data()) + str.size();
for(int i = 0; i < p; i++) {
SkUnichar u = SkUTF::NextUTF16(&utf16StartPtr, utf16StringEndPtr);
if(u == -1)
return 0;
else if(utf16StartPtr == utf16StringEndPtr)
return str.length();
}
size_t u16Pos = utf16StartPtr - (const uint16_t*)str.c_str();
return u16Pos;
}
int TextBox::get_codepoint_location_from_utf16_location(int p) {
std::string u8s = get_string();
std::u16string str = SkUnicodes::ICU::Make()->convertUtf8ToUtf16(u8s.c_str(), u8s.length());
const uint16_t* utf16StartPtr = reinterpret_cast<const uint16_t*>(str.data());
const uint16_t* utf16EndPtr = reinterpret_cast<const uint16_t*>(str.data()) + p;
const uint16_t* utf16StringEndPtr = reinterpret_cast<const uint16_t*>(str.data()) + str.size();
int i = 0;
for(; utf16StartPtr < utf16EndPtr; i++) {
SkUnichar u = SkUTF::NextUTF16(&utf16StartPtr, utf16StringEndPtr);
if(u == -1)
return 0;
}
return i;
}
TextData TextBox::get_rich_text_data() {
TextData toRet;
for(auto& p : paragraphs) {
@ -643,8 +723,7 @@ TextPosition TextBox::move(Movement movement, TextPosition pos, std::optional<fl
if(pos.fTextByteIndex >= paragraphs[pos.fParagraphIndex].text.size())
pos.fTextByteIndex = paragraphs[pos.fParagraphIndex].text.size();
if(movement != Movement::NOWHERE && movement != Movement::HOME && movement != Movement::END) {
rebuild();
if(movement != Movement::NOWHERE && movement != Movement::HOME && movement != Movement::END) {
if(flipDependingOnTextDirection && paragraphs[pos.fParagraphIndex].pStyleData.textDirection == skia::textlayout::TextDirection::kRtl) {
if(movement == Movement::LEFT)
movement = Movement::RIGHT;

View file

@ -1,3 +1,21 @@
/*
* InfiniPaint
* Copyright (C) 2025-2026 Yousef Khadadeh
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#pragma once
#include <cstdint>
#include <cwchar>
@ -106,6 +124,11 @@ class TextBox {
bool skiaAA = false;
};
int get_codepoint_location_from_text_position(TextPosition pos);
TextPosition get_text_position_from_codepoint_location(int p);
int get_utf16_location_from_codepoint_location(int p);
int get_codepoint_location_from_utf16_location(int p);
TextPosition move(Movement movement, TextPosition pos, std::optional<float>* previousX = nullptr, bool flipDependingOnTextDirection = false);
void set_max_width(float newWidth);
void set_max_height(float newMaxHeight);
@ -166,6 +189,8 @@ class TextBox {
SkRect get_cursor_rect(TextPosition pos);
skia::textlayout::TextDirection get_suggested_direction(size_t pIndex);
TextPosition get_text_pos_closest_to_point(Vector2f point);
private:
std::pair<TextPosition, TextPosition> get_start_end_text_pos(TextPosition p1, TextPosition p2);
std::pair<size_t, size_t> get_start_end_paragraph_pos(size_t p1, size_t p2);
@ -180,7 +205,6 @@ class TextBox {
void rects_between_text_positions_func(TextPosition p1, TextPosition p2, std::function<void(const SkRect& r)> f);
TextPosition get_text_pos_closest_to_point(Vector2f point);
std::shared_ptr<TextStyleModifier> get_last_text_style_mod_before_pos(TextPosition pos, TextStyleModifier::ModifierType modType);
void erase_if_over_all_styles_until_pos(TextPosition pos, const std::function<bool(TextPosition, const std::shared_ptr<TextStyleModifier>&)>& func);
void insert_style_at_pos(TextPosition pos, const std::shared_ptr<TextStyleModifier>& modifier);

View file

@ -1,3 +1,21 @@
/*
* InfiniPaint
* Copyright (C) 2025-2026 Yousef Khadadeh
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#include "TextStyleModifier.hpp"
#include <Helpers/ConvertVec.hpp>
#include <Helpers/Serializers.hpp>

View file

@ -1,3 +1,21 @@
/*
* InfiniPaint
* Copyright (C) 2025-2026 Yousef Khadadeh
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
#pragma once
#include <cstdint>
#include <modules/skparagraph/include/Paragraph.h>