Skip to content

Commit

Permalink
v0.0.77
Browse files Browse the repository at this point in the history
  • Loading branch information
yousefvand committed Dec 22, 2024
1 parent e7263f0 commit fb0dc84
Show file tree
Hide file tree
Showing 27 changed files with 467 additions and 351 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,11 @@

============

## 0.0.77

- Implemented:
- Encoding Menu -> Interpret as ... KOI8-R

## 0.0.76

- Implemented:
Expand Down
7 changes: 6 additions & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,10 @@ if(CMAKE_CXX_COMPILER_ID MATCHES "GNU|Clang")
endif()

# Find Qt6 packages in a single call
find_package(Qt6 REQUIRED COMPONENTS
find_package(
Qt6
REQUIRED
COMPONENTS
Core
Gui
Widgets
Expand Down Expand Up @@ -154,6 +157,8 @@ set(PROJECT_SOURCES
src/encoding/interpret_as_scsu.h
src/encoding/interpret_as_koi8_u.cpp
src/encoding/interpret_as_koi8_u.h
src/encoding/interpret_as_koi8_r.cpp
src/encoding/interpret_as_koi8_r.h
${PROJECT_UI}
)

Expand Down
12 changes: 6 additions & 6 deletions CMakeLists.txt.user
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE QtCreatorProject>
<!-- Written by QtCreator 15.0.0, 2024-12-21T21:20:46. -->
<!-- Written by QtCreator 15.0.0, 2024-12-22T13:28:41. -->
<qtcreator>
<data>
<variable>EnvironmentId</variable>
Expand Down Expand Up @@ -103,14 +103,14 @@
<value type="int" key="CMake.Configure.BaseEnvironment">2</value>
<value type="bool" key="CMake.Configure.ClearSystemEnvironment">false</value>
<valuelist type="QVariantList" key="CMake.Configure.UserEnvironmentChanges"/>
<value type="QString" key="CMake.Initial.Parameters">-DCMAKE_GENERATOR:STRING=Ninja
<value type="QString" key="CMake.Initial.Parameters">-DQT_QMAKE_EXECUTABLE:FILEPATH=%{Qt:qmakeExecutable}
-DCMAKE_CXX_FLAGS_INIT:STRING=%{Qt:QML_DEBUG_FLAG}
-DCMAKE_GENERATOR:STRING=Ninja
-DCMAKE_C_COMPILER:FILEPATH=%{Compiler:Executable:C}
-DCMAKE_PREFIX_PATH:PATH=%{Qt:QT_INSTALL_PREFIX}
-DCMAKE_BUILD_TYPE:STRING=Debug
-DCMAKE_CXX_COMPILER:FILEPATH=%{Compiler:Executable:Cxx}
-DCMAKE_CXX_FLAGS_INIT:STRING=%{Qt:QML_DEBUG_FLAG}
-DCMAKE_PROJECT_INCLUDE_BEFORE:FILEPATH=%{BuildConfig:BuildDirectory:NativeFilePath}/.qtc/package-manager/auto-setup.cmake
-DCMAKE_PREFIX_PATH:PATH=%{Qt:QT_INSTALL_PREFIX}
-DQT_QMAKE_EXECUTABLE:FILEPATH=%{Qt:qmakeExecutable}</value>
-DCMAKE_PROJECT_INCLUDE_BEFORE:FILEPATH=%{BuildConfig:BuildDirectory:NativeFilePath}/.qtc/package-manager/auto-setup.cmake</value>
<value type="QString" key="CMake.Source.Directory">/data/Code/Qt/Notepad--</value>
<value type="int" key="EnableQmlDebugging">0</value>
<value type="QString" key="ProjectExplorer.BuildConfiguration.BuildDirectory">/data/Code/Qt/Notepad--/build/Desktop_Qt_6_8_1-Debug</value>
Expand Down
7 changes: 6 additions & 1 deletion src/codeeditor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,10 @@
#include <QTabWidget>
#include "settings.h"

CodeEditor::CodeEditor(QWidget *parent)
CodeEditor::CodeEditor(QWidget *parent, QString filePath)
: QPlainTextEdit(parent), lineNumberArea(new LineNumberArea(this)) {

m_filePath = filePath;
QTabWidget* doc = qobject_cast<QTabWidget*>(parent);
m_documentsTab = doc;
QPalette p = this->palette();
Expand Down Expand Up @@ -48,6 +49,10 @@ CodeEditor::CodeEditor(QWidget *parent)
}
}

QString CodeEditor::filePath() {
return m_filePath;
}

int CodeEditor::lineNumberAreaWidth() {
int digits = 1;
int max = qMax(1, blockCount());
Expand Down
4 changes: 3 additions & 1 deletion src/codeeditor.h
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ class CodeEditor : public QPlainTextEdit {
Q_OBJECT

public:
explicit CodeEditor(QWidget *parent = nullptr);
explicit CodeEditor(QWidget *parent, QString filePath);

void lineNumberAreaPaintEvent(QPaintEvent *event);
int lineNumberAreaWidth();
Expand All @@ -35,6 +35,7 @@ class CodeEditor : public QPlainTextEdit {
void zoomOut();
void defaultZoom();
void setShowMathRendering(bool enabled);
QString filePath();

protected:
void resizeEvent(QResizeEvent *event) override;
Expand All @@ -61,6 +62,7 @@ private slots:
bool m_showWrapSymbol = false;
int m_tabWidth;
bool m_showMathRendering = false;
QString m_filePath;

void paintTabs(QPainter& painter, const QTextBlock& block, int top);
void paintSpaces(QPainter& painter, const QTextBlock& block, int top);
Expand Down
2 changes: 1 addition & 1 deletion src/document.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ Document::Document(const QString &filePath, QWidget *parent)

qDebug() << "Document created for file: " << filePath;
// Initialize the code editor and layout
m_editor = new CodeEditor(this);
m_editor = new CodeEditor(this, filePath);

QVBoxLayout *layout = new QVBoxLayout(this);
layout->addWidget(m_editor);
Expand Down
3 changes: 2 additions & 1 deletion src/encoding/interpret_as_dialog.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,8 @@ InterpreteAsDialog::InterpreteAsDialog(QWidget* parent)
"TIS-620",
"SHIFT-JTS",
"SCSU",
"KOI8-U"
"KOI8-U",
"KOI8-R"
});

// Create OK and Cancel buttons using QDialogButtonBox
Expand Down
79 changes: 79 additions & 0 deletions src/encoding/interpret_as_koi8_r.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
#include "interpret_as_koi8_r.h"
#include <QFile>
#include <QDebug>
#include <QPlainTextEdit>
#include "../codeeditor.h"

// Singleton instance
Interpret_As_KOI8_R& Interpret_As_KOI8_R::instance() {
static Interpret_As_KOI8_R instance;
return instance;
}

// KOI8-R to Unicode mapping (with explicit casting)
const QMap<uint8_t, QChar> koi8rToUnicode = {
{ uint8_t(0xC0), QChar(0x0410) }, { uint8_t(0xC1), QChar(0x0411) },
{ uint8_t(0xC2), QChar(0x0412) }, { uint8_t(0xC3), QChar(0x0413) },
{ uint8_t(0xC4), QChar(0x0414) }, { uint8_t(0xC5), QChar(0x0415) },
{ uint8_t(0xC6), QChar(0x0416) }, { uint8_t(0xC7), QChar(0x0417) },
{ uint8_t(0xC8), QChar(0x0418) }, { uint8_t(0xC9), QChar(0x0419) },
{ uint8_t(0xCA), QChar(0x041A) }, { uint8_t(0xCB), QChar(0x041B) },
{ uint8_t(0xCC), QChar(0x041C) }, { uint8_t(0xCD), QChar(0x041D) },
{ uint8_t(0xCE), QChar(0x041E) }, { uint8_t(0xCF), QChar(0x041F) },
{ uint8_t(0xD0), QChar(0x0420) }, { uint8_t(0xD1), QChar(0x0421) },
{ uint8_t(0xD2), QChar(0x0422) }, { uint8_t(0xD3), QChar(0x0423) },
{ uint8_t(0xD4), QChar(0x0424) }, { uint8_t(0xD5), QChar(0x0425) },
{ uint8_t(0xD6), QChar(0x0426) }, { uint8_t(0xD7), QChar(0x0427) },
{ uint8_t(0xD8), QChar(0x0428) }, { uint8_t(0xD9), QChar(0x0429) },
{ uint8_t(0xDA), QChar(0x042A) }, { uint8_t(0xDB), QChar(0x042B) },
{ uint8_t(0xDC), QChar(0x042C) }, { uint8_t(0xDD), QChar(0x042D) },
{ uint8_t(0xDE), QChar(0x042E) }, { uint8_t(0xDF), QChar(0x042F) },

{ uint8_t(0xE0), QChar(0x0430) }, { uint8_t(0xE1), QChar(0x0431) },
{ uint8_t(0xE2), QChar(0x0432) }, { uint8_t(0xE3), QChar(0x0433) },
{ uint8_t(0xE4), QChar(0x0434) }, { uint8_t(0xE5), QChar(0x0435) },
{ uint8_t(0xE6), QChar(0x0436) }, { uint8_t(0xE7), QChar(0x0437) },
{ uint8_t(0xE8), QChar(0x0438) }, { uint8_t(0xE9), QChar(0x0439) },
{ uint8_t(0xEA), QChar(0x043A) }, { uint8_t(0xEB), QChar(0x043B) },
{ uint8_t(0xEC), QChar(0x043C) }, { uint8_t(0xED), QChar(0x043D) },
{ uint8_t(0xEE), QChar(0x043E) }, { uint8_t(0xEF), QChar(0x043F) },
{ uint8_t(0xF0), QChar(0x0440) }, { uint8_t(0xF1), QChar(0x0441) },
{ uint8_t(0xF2), QChar(0x0442) }, { uint8_t(0xF3), QChar(0x0443) },
{ uint8_t(0xF4), QChar(0x0444) }, { uint8_t(0xF5), QChar(0x0445) },
{ uint8_t(0xF6), QChar(0x0446) }, { uint8_t(0xF7), QChar(0x0447) },
{ uint8_t(0xF8), QChar(0x0448) }, { uint8_t(0xF9), QChar(0x0449) },
{ uint8_t(0xFA), QChar(0x044A) }, { uint8_t(0xFB), QChar(0x044B) },
{ uint8_t(0xFC), QChar(0x044C) }, { uint8_t(0xFD), QChar(0x044D) },
{ uint8_t(0xFE), QChar(0x044E) }, { uint8_t(0xFF), QChar(0x044F) }
};

// KOI8-R Decoding Logic
QString Interpret_As_KOI8_R::decodeKOI8R(const QByteArray& koi8Data) {
QString result;
for (char byte : koi8Data) {
uint8_t koi8Char = static_cast<uint8_t>(byte);
result.append(koi8rToUnicode.value(koi8Char, QChar(0xFFFD))); // U+FFFD for unmapped bytes
}
return result;
}

// Execute KOI8-R Interpretation
void Interpret_As_KOI8_R::execute(QPlainTextEdit* editor) {
if (!editor) return;

CodeEditor* codeEditor = qobject_cast<CodeEditor*>(editor);
QString filePath = codeEditor->filePath();

QFile file(filePath);
if (!file.open(QIODevice::ReadOnly)) {
qWarning() << "[ERROR] Cannot open file: " << filePath;
return;
}

QByteArray koi8Data = file.readAll();
file.close();

QString decodedText = decodeKOI8R(koi8Data);
codeEditor->setPlainText(decodedText);
qDebug() << "[DEBUG] KOI8-R Decoding Applied to File:" << filePath;
}
24 changes: 24 additions & 0 deletions src/encoding/interpret_as_koi8_r.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
#pragma once

#include <QString>
#include <QByteArray>
#include <QPlainTextEdit>

// Singleton class to interpret files as KOI8-R
class Interpret_As_KOI8_R {
public:
static Interpret_As_KOI8_R& instance();

// Main decoding method
QString decodeKOI8R(const QByteArray& koi8Data);

// Executes KOI8-R interpretation for the given editor
void execute(QPlainTextEdit* editor);

private:
Interpret_As_KOI8_R() = default;
~Interpret_As_KOI8_R() = default;

Interpret_As_KOI8_R(const Interpret_As_KOI8_R&) = delete;
Interpret_As_KOI8_R& operator=(const Interpret_As_KOI8_R&) = delete;
};
38 changes: 31 additions & 7 deletions src/encoding/interpret_as_koi8_u.cpp
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
#include "interpret_as_koi8_u.h"
#include "../codeeditor.h"
#include <QFile>
#include <QDebug>

Expand Down Expand Up @@ -40,19 +41,42 @@ QString Interpret_As_KOI8_U::decodeKOI8U(const QByteArray& koi8uData) {
}

// Execute the KOI8-U interpretation

void Interpret_As_KOI8_U::execute(QPlainTextEdit* editor) {
if (!editor) {
qWarning() << "[ERROR] No editor instance provided.";
return;
}

// Access the raw QByteArray from the editor's document
QTextDocument* doc = editor->document();
QByteArray rawBytes = doc->toRawText().toLocal8Bit();
CodeEditor* codeEditor = qobject_cast<CodeEditor*>(editor);
if (!codeEditor) {
qWarning() << "[ERROR] Editor is not a CodeEditor instance.";
return;
}

QString filePath = codeEditor->filePath();
if (filePath.isEmpty()) {
qWarning() << "[ERROR] No file path associated with the editor.";
return;
}

QFile file(filePath);
if (!file.open(QIODevice::ReadOnly)) {
qWarning() << "[ERROR] Cannot open file: " << filePath;
return;
}

QByteArray koi8uData = file.readAll();
file.close();

// Use QStringDecoder to decode KOI8-U
QStringDecoder decoder("KOI8-U");

// Decode KOI8-U data to QString
QString decodedText = decoder.decode(koi8uData);

// Decode KOI8-U from raw bytes
QString decodedText = decodeKOI8U(rawBytes);
// Replace text in the editor with the correctly decoded text
codeEditor->setPlainText(decodedText);

// Replace the text in the editor with the decoded text
editor->setPlainText(decodedText);
qDebug() << "[DEBUG] Successfully reloaded and decoded as KOI8-U:" << filePath;
}
54 changes: 22 additions & 32 deletions src/encoding/interpret_as_tis_620.cpp
Original file line number Diff line number Diff line change
@@ -1,60 +1,50 @@
#include "interpret_as_tis_620.h"
#include <QStringDecoder>
#include <QFile>
#include <QDebug>
#include "interpret_as_tis_620.h"
#include "../codeeditor.h"

// Singleton instance
// Singleton instance definition
Interpret_As_TIS_620& Interpret_As_TIS_620::instance() {
static Interpret_As_TIS_620 instance;
return instance;
}

// TIS-620 to Unicode mapping
uint32_t Interpret_As_TIS_620::tis620ToUnicode(uint8_t tis620Char) {
if (tis620Char < 0x80) {
return tis620Char; // ASCII range
} else if (tis620Char >= 0xA1 && tis620Char <= 0xDA) {
return 0x0E01 + (tis620Char - 0xA1); // Thai characters
} else if (tis620Char >= 0xDF && tis620Char <= 0xFB) {
return 0x0E3F + (tis620Char - 0xDF); // Thai punctuation and symbols
}
return 0xFFFD; // Replacement character for invalid mappings
}

// Decode the TIS-620 data
QString Interpret_As_TIS_620::decodeTIS620(const QByteArray& tis620Data) {
QString result;

for (char byte : tis620Data) {
uint32_t unicodeChar = tis620ToUnicode(static_cast<uint8_t>(byte));
result.append(QChar(unicodeChar));
}

return result;
}

// Execute the TIS-620 interpretation
void Interpret_As_TIS_620::execute(QPlainTextEdit* editor) {
if (!editor) {
qWarning() << "[ERROR] No editor instance provided.";
return;
}

QString filePath = editor->property("filePath").toString();
CodeEditor* codeEditor = qobject_cast<CodeEditor*>(editor);
if (!codeEditor) {
qWarning() << "[ERROR] Editor is not a CodeEditor instance.";
return;
}

QString filePath = codeEditor->filePath();
if (filePath.isEmpty()) {
qWarning() << "[ERROR] No file path associated with the editor.";
return;
}

QFile file(filePath);
if (!file.open(QIODevice::ReadOnly)) {
qWarning() << "[ERROR] Cannot open file:" << filePath;
qWarning() << "[ERROR] Cannot open file: " << filePath;
return;
}

QByteArray tis620Data = file.readAll();
file.close();

QString decodedText = decodeTIS620(tis620Data);
editor->setPlainText(decodedText);
}
// Use QStringDecoder to decode TIS-620
QStringDecoder decoder("TIS-620");

// Decode TIS-620 data to QString
QString decodedText = decoder.decode(tis620Data);

// Replace the text in the editor with the correctly decoded text
codeEditor->setPlainText(decodedText);

qDebug() << "[DEBUG] Successfully reloaded and decoded as TIS-620:" << filePath;
}
Loading

0 comments on commit fb0dc84

Please sign in to comment.