Add ace editor (#269)

This commit is contained in:
Ahmet Bedir
2024-08-07 22:12:31 +03:00
committed by GitHub
parent a67e586a5d
commit 8c487a64fa
20 changed files with 1262 additions and 755 deletions

View File

@ -0,0 +1,40 @@
import ace from 'brace';
import 'brace/mode/javascript';
import 'brace/mode/plain_text';
import 'brace/mode/sh';
import 'brace/mode/ini';
import 'brace/ext/searchbox'
import './theme-vito'
import './mode-env';
import './mode-nginx';
window.initAceEditor = function (options = {}) {
const editorValue = JSON.parse(options.value || '');
const editor = ace.edit(options.id);
editor.setTheme("ace/theme/vito");
editor.getSession().setMode(`ace/mode/${options.lang || 'plain_text'}`);
editor.setValue(editorValue, -1);
editor.clearSelection();
editor.focus();
editor.setOptions({
enableBasicAutocompletion: true,
enableSnippets: true,
enableLiveAutocompletion: true,
printMargin: false,
});
editor.renderer.setScrollMargin(15, 15, 0, 0)
editor.renderer.setPadding(15);
editor.getSession().on('change', function () {
document.getElementById(`textarea-${options.id}`).value = editor.getValue();
});
window.addEventListener('resize', function () {
editor.resize();
})
document.getElementById(`textarea-${options.id}`).innerHTML = editorValue;
return editor;
}

View File

@ -0,0 +1,136 @@
ace.define("ace/mode/env", ["require", "exports", "module", "ace/lib/oop", "ace/mode/text", "ace/mode/env_highlight_rules", "ace/mode/folding/ini","ace/mode/behaviour"], function (require, exports) {
var oop = require("../lib/oop");
var TextMode = require("./text").Mode;
var Behaviour = require("./behaviour").Behaviour;
var envHighlightRules = require("./env_highlight_rules").envHighlightRules;
var Mode = function () {
this.HighlightRules = envHighlightRules;
this.$behaviour = new Behaviour
};
oop.inherits(Mode, TextMode);
(function() {
this.lineCommentStart = "#",
this.blockComment = null,
this.$id = "ace/mode/env"
}).call(Mode.prototype),
exports.Mode = Mode;
})
ace.define("ace/mode/env_highlight_rules", ["require", "exports", "module", "ace/lib/oop", "ace/mode/text_highlight_rules"], function (require, exports, module) {
"use strict";
var oop = require("../lib/oop");
var TextHighlightRules =
require("./text_highlight_rules").TextHighlightRules;
var envHighlightRules = function () {
this.$rules = {
start: [
{
token: "punctuation.definition.comment.env",
regex: "#.*",
push_: [
{
token: "comment.line.number-sign.env",
regex: "$|^",
next: "pop",
},
{
defaultToken: "comment.line.number-sign.env",
},
],
},
{
token: "punctuation.definition.comment.env",
regex: "#.*",
push_: [
{
token: "comment.line.semicolon.env",
regex: "$|^",
next: "pop",
},
{
defaultToken: "comment.line.semicolon.env",
},
],
},
{
token: [
"keyword.other.definition.env",
"text",
"punctuation.separator.key-value.env",
],
regex: "\\b([a-zA-Z0-9_.-]+)\\b(\\s*)(=)",
},
{
token: [
"punctuation.definition.entity.env",
"constant.section.group-title.env",
"punctuation.definition.entity.env",
],
regex: "^(\\[)(.*?)(\\])",
},
{
token: "punctuation.definition.string.begin.env",
regex: "'",
push: [
{
token: "punctuation.definition.string.end.env",
regex: "'",
next: "pop",
},
{
token: "constant.language.escape",
regex: "\\\\(?:[\\\\0abtrn;#=:]|x[a-fA-F\\d]{4})",
},
{
defaultToken: "string.quoted.single.env",
},
],
},
{
token: "punctuation.definition.string.begin.env",
regex: '"',
push: [
{
token: "constant.language.escape",
regex: "\\\\(?:[\\\\0abtrn;#=:]|x[a-fA-F\\d]{4})",
},
{
token: "support.constant.color",
regex: /\${[\w]+}/,
},
{
token: "punctuation.definition.string.end.env",
regex: '"',
next: "pop",
},
{
defaultToken: "string.quoted.double.env",
},
],
},
{
token: "constant.language.boolean",
regex: /(?:true|false)\b/,
},
],
};
this.normalizeRules();
};
envHighlightRules.metaData = {
fileTypes: ["env"],
keyEquivalent: "^~I",
name: "Env",
scopeName: "source.env",
};
oop.inherits(envHighlightRules, TextHighlightRules);
exports.envHighlightRules = envHighlightRules;
});

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,47 @@
ace.define(
"ace/theme/vito",
["require", "exports", "module", "ace/lib/dom"],
function (require, exports) {
(exports.isDark = true),
(exports.cssClass = "ace-vito rounded-lg w-full"),
(exports.cssText = `
.ace-vito .ace_scrollbar::-webkit-scrollbar { width: 12px;}
.ace-vito .ace_scrollbar::-webkit-scrollbar-track { background: #111827;}
.ace-vito .ace_scrollbar::-webkit-scrollbar-thumb { background: #374151; border-radius: 4px;}
.ace-vito .ace_gutter {background: #151c27;color: rgb(128,145,160)}
.ace-vito .ace_print-margin {width: 1px;background: #555555}
.ace-vito {background-color: #0f172a;color: #F9FAFB}
.ace-vito .ace_cursor {color: #F9FAFB}
.ace-vito .ace_marker-layer .ace_selection {background: rgba(179, 101, 57, 0.75)}
.ace-vito.ace_multiselect .ace_selection.ace_start {box-shadow: 0 0 3px 0px #002240;}
.ace-vito .ace_marker-layer .ace_step {background: rgb(127, 111, 19)}
.ace-vito .ace_marker-layer .ace_bracket {margin: -1px 0 0 -1px;border: 1px solid rgba(255, 255, 255, 0.15)}
.ace-vito .ace_marker-layer .ace_active-line {background: rgba(24, 182, 155, 0.10)}
.ace-vito .ace_gutter-active-line {background-color: rgba(0, 0, 0, 0.35)}
.ace-vito .ace_marker-layer .ace_selected-word {border: 1px solid rgba(179, 101, 57, 0.75)}
.ace-vito .ace_invisible {color: rgba(255, 255, 255, 0.15)}
.ace-vito .ace_keyword,.ace-vito .ace_meta {color: #FF9D00}
.ace-vito .ace_constant,.ace-vito .ace_constant.ace_character,.ace-vito .ace_constant.ace_character.ace_escape,.ace-vito .ace_constant.ace_other {color: #FF628C}
.ace-vito .ace_invalid {color: #F8F8F8;background-color: #800F00}
.ace-vito .ace_support {color: #80FFBB}
.ace-vito .ace_support.ace_constant {color: #EB939A}
.ace-vito .ace_fold {background-color: #FF9D00;border-color: #F9FAFB}
.ace-vito .ace_support.ace_function {color: #FFB054}
.ace-vito .ace_storage {color: #FFEE80}
.ace-vito .ace_entity {color: #FFDD00}
.ace-vito .ace_string {color: #7cd827}
.ace-vito .ace_string.ace_regexp {color: #80FFC2}
.ace-vito .ace_comment {font-style: italic;color: #6B7280}
.ace-vito .ace_heading,.ace-vito
.ace_markup.ace_heading {color: #C8E4FD;background-color: #001221}
.ace-vito .ace_list,.ace-vito .ace_markup.ace_list {background-color: #130D26}
.ace-vito .ace_variable {color: #CCCCCC}
.ace-vito .ace_variable.ace_language {color: #FF80E1}
.ace-vito .ace_meta.ace_tag {color: #9EFFFF}
.ace-vito .ace_indent-guide {background: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbYnAAAAEklEQVQImWNgYGBgYHCLSvkPAAP3AgSDTRd4AAAAAElFTkSuQmCC) right repeat-y}
`);
var dom = require("../lib/dom");
dom.importCssString(exports.cssText, exports.cssClass);
},
);

View File

@ -1,5 +1,6 @@
import 'flowbite';
import 'flowbite/dist/datepicker.js';
import './ace-editor/ace-editor';
import Alpine from 'alpinejs';
window.Alpine = Alpine;

View File

@ -16,9 +16,8 @@ class="p-6"
<div class="mt-6">
<x-input-label for="script" :value="__('Script')" />
<x-textarea id="script" name="script" class="mt-1 min-h-[400px] w-full font-mono">
{{ old("script", $site->deploymentScript?->content) }}
</x-textarea>
@php($value = old("script", $site->deploymentScript?->content))
<x-editor id="script" name="script" lang="sh" :value="$value" />
@error("script")
<x-input-error class="mt-2" :messages="$message" />
@enderror

View File

@ -21,9 +21,8 @@ class="mt-6"
>
<x-input-label for="env" :value="__('.env')" />
<div id="env-content">
<x-textarea id="env" name="env" rows="10" class="mt-1 block min-h-[400px] w-full font-mono">
{{ old("env", session()->get("env") ?? "Loading...") }}
</x-textarea>
@php($envValue = old("env", session()->get("env") ?? "Loading..."))
<x-editor id="env" name="env" lang="env" :value="$envValue" />
</div>
@error("env")
<x-input-error class="mt-2" :messages="$message" />

View File

@ -0,0 +1,17 @@
<div>
<div
id="{{ $id }}"
{{ $attributes->merge(["class" => "mt-1 min-h-[400px] w-full"]) }}
class="ace-vito ace_dark"
></div>
<textarea id="textarea-{{ $id }}" name="{{ $name }}" style="display: none"></textarea>
<script>
if (window.initAceEditor) {
window.initAceEditor(@json($options));
} else {
document.addEventListener('DOMContentLoaded', function () {
window.initAceEditor(@json($options));
});
}
</script>
</div>

View File

@ -40,7 +40,7 @@ class="cursor-pointer"
@foreach ([\App\Enums\PHPIniType::FPM, \App\Enums\PHPIniType::CLI] as $type)
<x-dropdown-link
class="cursor-pointer"
x-on:click="version = '{{ $php->version }}'; $dispatch('open-modal', 'update-php-ini-{{ $type }}'); document.getElementById('ini').value = 'Loading...';"
x-on:click="version = '{{ $php->version }}'; $dispatch('open-modal', 'update-php-ini-{{ $type }}');"
hx-get="{{ route('servers.php.get-ini', ['server' => $server, 'version' => $php->version, 'type' => $type]) }}"
hx-swap="outerHTML"
hx-target="#update-php-ini-{{ $type }}-form"

View File

@ -15,9 +15,8 @@ class="p-6"
<div class="mt-6">
<x-input-label for="ini" value="php.ini" />
<x-textarea id="ini" name="ini" class="mt-1 w-full font-mono" rows="15">
{{ old("ini", session()->get("ini")) }}
</x-textarea>
@php($ini = old("ini", session()->get("ini") ?? "Loading..."))
<x-editor id="ini" name="ini" lang="ini" :value="$ini" />
@error("ini")
<x-input-error class="mt-2" :messages="$message" />
@enderror

View File

@ -1,7 +1,5 @@
<x-input-label for="content" :value="__('Content')" />
<x-textarea id="content" name="content" class="mt-1 min-h-[400px] w-full font-mono">
{{ $value }}
</x-textarea>
<x-editor name="content" lang="sh" :value="$value" />
@error("content")
<x-input-error class="mt-2" :messages="$message" />
@enderror

View File

@ -22,9 +22,8 @@ class="space-y-6"
hx-swap="outerHTML"
>
<div id="vhost-container">
<x-textarea id="vhost" name="vhost" rows="10" class="mt-1 block min-h-[400px] w-full font-mono">
{{ session()->has("vhost") ? session()->get("vhost") : "Loading..." }}
</x-textarea>
@php($vhost = old("vhost", session()->get("vhost") ?? "Loading..."))
<x-editor id="vhost" name="vhost" lang="nginx" :value="$vhost" />
</div>
@error("vhost")
<x-input-error class="mt-2" :messages="$message" />