Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/cpp.yml
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ jobs:
- name: Set up C++ environment (macOS)
if: matrix.os == 'macos-latest'
run: |
brew install make cmake yaml-cpp
brew install yaml-cpp
echo 'export PATH="/usr/local/opt/gcc/bin:$PATH"' >> ~/.bash_profile
source ~/.bash_profile
g++ --version
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ jobs:
- name: Set up C++ environment (macOS)
if: matrix.os == 'macos-latest'
run: |
brew install make cmake yaml-cpp
brew install yaml-cpp
echo 'export PATH="/usr/local/opt/gcc/bin:$PATH"' >> ~/.bash_profile
source ~/.bash_profile
g++ --version
Expand Down
1 change: 0 additions & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -32,4 +32,3 @@ find_package(yaml-cpp REQUIRED CONFIG)
# Add subdirectories
add_subdirectory(src)
add_subdirectory(tests)

5 changes: 3 additions & 2 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
DEBUG ?= OFF
PROJECT = CodeAstra
BUILD_DIR = $(PWD)/build

Expand All @@ -10,7 +11,7 @@ all: install
build:
@echo "Building $(PROJECT)..."
@mkdir -p $(BUILD_DIR)
@cd $(BUILD_DIR) && cmake $(CMAKE_OPTIONS)
@cd $(BUILD_DIR) && cmake $(CMAKE_OPTIONS) -DDEBUG=$(DEBUG)

clean:
@echo "Cleaning the build directory..."
Expand All @@ -36,4 +37,4 @@ test: build_tests

run:
@echo "Running $(PROJECT)..."
@./build/bin/$(PROJECT)
@./build/bin/$(PROJECT)
1 change: 1 addition & 0 deletions include/SyntaxManager.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ class SyntaxManager
* @return A unique pointer to the appropriate syntax highlighter, or nullptr if not available.
*/
static std::unique_ptr<QSyntaxHighlighter> createSyntaxHighlighter(const QString &extension, QTextDocument *doc);
static void initializeUserSyntaxConfig();

private:
static std::unique_ptr<QSyntaxHighlighter> createHighlighter(QTextDocument *doc, const std::vector<YAML::Node> &config, const QString &extension);
Expand Down
6 changes: 6 additions & 0 deletions resources.qrc
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,11 @@
<qresource prefix="/">
<file>resources/app_icon.png</file>
<file>resources/themes/dark.qss</file>
<file>resources/syntax/cxx.syntax.yaml</file>
<file>resources/syntax/python.syntax.yaml</file>
<file>resources/syntax/go.syntax.yaml</file>
<file>resources/syntax/tsx.syntax.yaml</file>
<file>resources/syntax/yaml.syntax.yaml</file>
<file>resources/syntax/markdown.syntax.yaml</file>
</qresource>
</RCC>
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ keywords:
color: "#FFDE00" # Yellow

number:
- regex: "\\b\\d+\\b"
- regex: "\\b(0b[01]+|0o[0-7]+|0x[0-9a-fA-F]+|\\d+(\\.\\d+)?)\\b"
color: "#0000FF" # Blue

parenthesis:
Expand Down
2 changes: 1 addition & 1 deletion config/go.syntax.yaml → resources/syntax/go.syntax.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -10,5 +10,5 @@ keywords:
color: "#E37100" # Orange

number:
- regex: "\\b\\d+\\b"
- regex: "\\b(0b[01]+|0o[0-7]+|0x[0-9a-fA-F]+|\\d+(\\.\\d+)?)\\b"
color: "#0000FF" # Blue
File renamed without changes.
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,5 @@ keywords:
color: "#E37100" # Orange

number:
- regex: "\\b\\d+\\b"
- regex: "\\b(0b[01]+|0o[0-7]+|0x[0-9a-fA-F]+|\\d+(\\.\\d+)?)\\b"
color: "#0000FF" # Blue
36 changes: 36 additions & 0 deletions resources/syntax/tsx.syntax.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
extensions: [tsx, ts, js]

keywords:
comment:
- regex: "//.*"
color: "#6A9955" # Green
- regex: "/\\*[^*]*\\*+(?:[^/*][^*]*\\*+)*/"
color: "#6A9955" # Green

string:
- regex: "'(?:\\\\.|[^'\\\\])*'"
color: "#CE9178" # Reddish
- regex: "\"(?:\\\\.|[^\"\\\\])*\""
color: "#CE9178" # Reddish
- regex: "`(?:\\\\.|[^`\\\\])*`"
color: "#DCDCAA" # Yellow for template literals

number:
- regex: "\\b(0b[01]+|0o[0-7]+|0x[0-9a-fA-F]+|\\d+(\\.\\d+)?)\\b"
color: "#B5CEA8" # Light green

keyword:
- regex: "\\b(?:let|const|var|function|class|interface|extends|implements|public|private|protected|static|new|return|if|else|for|while|do|switch|case|break|continue|try|catch|finally|throw|typeof|instanceof|in|of|void|async|await|import|from|export|default|as|enum|type|declare|namespace|abstract|readonly|get|set|yield|with|super|this)\\b"
color: "#569CD6" # Blue

type:
- regex: "\\b(?:string|number|boolean|any|unknown|never|void|object|undefined|null|bigint|symbol)\\b"
color: "#4EC9B0" # Cyan

boolean:
- regex: "\\b(?:true|false)\\b"
color: "#569CD6" # Blue

operator:
- regex: "\\+|-|\\*|\\/|=|==|===|!=|!==|<|>|<=|>=|\\?|:|\\.|,|\\||&|\\^|~|!"
color: "#D4D4D4" # Light gray
File renamed without changes.
14 changes: 7 additions & 7 deletions src/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -43,16 +43,16 @@ qt_add_resources(APP_RESOURCES ${CMAKE_SOURCE_DIR}/resources.qrc)
target_sources(${EXECUTABLE_NAME} PRIVATE ${APP_RESOURCES})

# OS-specific flags
option(DEBUG "Enable debug mode" OFF)

if(MSVC)
target_compile_options(${EXECUTABLE_NAME} PRIVATE /W4 /WX /analyze /sdl /guard:cf)
elseif(APPLE OR UNIX)
target_compile_options(${EXECUTABLE_NAME} PRIVATE -Wall -Wextra -Wpedantic -Werror -Wshadow -Wconversion -Wsign-conversion -fsanitize=address,undefined -fstack-protector)
target_link_options(${EXECUTABLE_NAME} PRIVATE -fsanitize=address,undefined)
endif()

# Copy config files
file(GLOB YAML_FILES "${CMAKE_SOURCE_DIR}/config/*.yaml")
file(MAKE_DIRECTORY ${CMAKE_BINARY_DIR}/config)
foreach(YAML_FILE ${YAML_FILES})
configure_file(${YAML_FILE} ${CMAKE_BINARY_DIR}/config/ COPYONLY)
endforeach()
# Add the preprocessor symbol only when DEBUG is ON
if (DEBUG)
target_compile_definitions(${EXECUTABLE_NAME} PRIVATE DEBUG=1)
endif()
endif()
92 changes: 73 additions & 19 deletions src/SyntaxManager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,44 +5,93 @@
#include <QFile>
#include <QDebug>

std::unique_ptr<QSyntaxHighlighter> SyntaxManager::createSyntaxHighlighter(const QString &extension, QTextDocument *doc)
void SyntaxManager::initializeUserSyntaxConfig()
{
QString configPath = qgetenv("CONFIG_DIR");
if (configPath.isEmpty())
QString userSyntaxDir = QDir::homePath() + "/.config/codeastra/syntax";
QDir dir(userSyntaxDir);
Comment on lines -10 to +11
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we still provide a way to change the default config location?

It could be a good idea to keep a universal location for these files for simplicity (and security) reasons as is done here now.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe this is the universal location. I took the same example as Neo Vim, where the config is located at /.config/nvim/*


if (!dir.exists())
{
configPath = "config";
}
qDebug() << "[Setup] First run detected. Creating syntax config directory:" << userSyntaxDir;

if (!dir.mkpath("."))
{
qWarning() << "[Setup] Failed to create user syntax config directory:" << userSyntaxDir;
return;
}

// List of default syntax files to copy
QDir defaultDir(":/resources/syntax/");
QStringList defaultSyntaxFiles = defaultDir.entryList({"*.yaml", "*.yml"}, QDir::Files);

for (const QString &fileName : defaultSyntaxFiles)
{
QString resourcePath = ":/resources/syntax/" + fileName;
QString destPath = userSyntaxDir + "/" + fileName;

QDir syntaxDir(configPath);
QFile resFile(resourcePath);
if (resFile.copy(destPath))
{
qDebug() << "[Setup] Copied default config:" << fileName;
}
else
{
qWarning() << "[Setup] Failed to copy:" << resourcePath << "to" << destPath;
}
}
}
else
{
qDebug() << "[Setup] User syntax directory already exists. Skipping first-run config.";
}
}

QStringList yamlFiles = syntaxDir.entryList({"*.yaml", "*.yml"}, QDir::Files);
qDebug() << "Directory being scanned: " << syntaxDir.absolutePath();
std::unique_ptr<QSyntaxHighlighter> SyntaxManager::createSyntaxHighlighter(const QString &extension, QTextDocument *doc)
{
QString baseDir;

if (syntaxDir.exists())
if (qEnvironmentVariableIsSet("CONFIG_DIR"))
{
qDebug() << "Directory exists.";
baseDir = qEnvironmentVariable("CONFIG_DIR");
}
else
{
qDebug() << "Directory does not exist.";
QString userSyntaxDir = QDir::homePath() + "/.config/codeastra/syntax";
if (QDir(userSyntaxDir).exists())
{
baseDir = userSyntaxDir;
}
else
{
baseDir = "config";
}
}

#ifdef DEBUG
qDebug() << "[SyntaxManager] Using config directory:" << baseDir;
#endif

QDir syntaxDir(baseDir);
QStringList yamlFilePath = syntaxDir.entryList({"*.yaml", "*.yml"}, QDir::Files);

std::vector<YAML::Node> config;
// Iterate over all YAML files and store their contents as separate nodes
for (const QString &fileName : yamlFiles)
for (const QString &fileName : yamlFilePath)
{
QFile file(syntaxDir.filePath(fileName));
if (file.open(QIODevice::ReadOnly | QIODevice::Text))
{
YAML::Node fileConfig = YAML::Load(file.readAll().toStdString());
file.close();
qDebug() << "Loaded YAML from: " << file.fileName();

#ifdef DEBUG
qDebug() << "[SyntaxManager] Loaded config for extension:" << extension << "from:" << file.fileName();
#endif
config.push_back(fileConfig);
}
else
{
qDebug() << "Failed to open file: " << file.fileName();
qWarning() << "[SyntaxManager] Failed to open syntax config for extension:" << extension << "at:" << yamlFilePath;
return nullptr;
}
}

Expand All @@ -51,7 +100,11 @@ std::unique_ptr<QSyntaxHighlighter> SyntaxManager::createSyntaxHighlighter(const

std::unique_ptr<QSyntaxHighlighter> SyntaxManager::createHighlighter(QTextDocument *doc, const std::vector<YAML::Node> &config, const QString &extension)
{
qDebug() << "Creating highlighter for extension:" << extension;

#ifdef DEBUG
qDebug() << "[SyntaxManager] Creating highlighter for extension:" << extension;
#endif

for (const auto &node : config)
{
if (node["extensions"])
Expand All @@ -67,10 +120,11 @@ std::unique_ptr<QSyntaxHighlighter> SyntaxManager::createHighlighter(QTextDocume
}
else
{
qDebug() << "No extensions key in YAML config.";
qDebug() << "[SyntaxManager] No extensions key in YAML config.";
}
}

qDebug() << "No matching highlighter found for extension:" << extension;
#ifdef DEBUG
qDebug() << "[SyntaxManager] No matching highlighter found for extension:" << extension;
#endif
return nullptr;
}
2 changes: 2 additions & 0 deletions src/main.cpp
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
#include "MainWindow.h"
#include "SyntaxManager.h"

#include <QApplication>
#include <QMainWindow>
Expand Down Expand Up @@ -34,6 +35,7 @@ QIcon createRoundIcon(const QString &iconPath)

QFont setFont()
{
SyntaxManager::initializeUserSyntaxConfig();
QStringList preferreFontFamilies = {"Monaco", "Menlo", "Consolas", "Courier New", "Monospace"};
QStringList availableFamilies = QFontDatabase::families();

Expand Down
Loading