eterm: Refactor and fix.

This commit is contained in:
Martín Lucas Golini
2022-06-24 20:19:16 -03:00
parent 3dd1e92858
commit 75afbb58af
10 changed files with 54 additions and 1439 deletions
+2 -9
View File
@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE QtCreatorProject>
<!-- Written by QtCreator 7.0.2, 2022-06-23T02:40:37. -->
<!-- Written by QtCreator 7.0.2, 2022-06-24T01:49:18. -->
<qtcreator>
<data>
<variable>EnvironmentId</variable>
@@ -83,6 +83,7 @@
<valuemap type="QVariantMap" key="ClangTools">
<value type="bool" key="ClangTools.AnalyzeOpenFiles">false</value>
<value type="bool" key="ClangTools.BuildBeforeAnalysis">true</value>
<value type="QString" key="ClangTools.DiagnosticConfig"></value>
<value type="int" key="ClangTools.ParallelJobs">0</value>
<valuelist type="QVariantList" key="ClangTools.SelectedDirs"/>
<valuelist type="QVariantList" key="ClangTools.SelectedFiles"/>
@@ -1518,14 +1519,6 @@
<variable>ProjectExplorer.Project.Updater.FileVersion</variable>
<value type="int">22</value>
</data>
<data>
<variable>UserStickyKeys</variable>
<valuelist type="QVariantList">
<value type="QString">ProjectExplorer.Project.Target.1</value>
<value type="QString">ProjectExplorer.Project.Target.1/ProjectExplorer.ProjectConfiguration.DefaultDisplayName</value>
<value type="QString">ProjectExplorer.Project.Target.1/ProjectExplorer.ProjectConfiguration.DisplayName</value>
</valuelist>
</data>
<data>
<variable>Version</variable>
<value type="int">22</value>
+2 -2
View File
@@ -1133,8 +1133,6 @@
../../src/tools/ecode/version.hpp
../../src/tools/ecode/widgetcommandexecuter.hpp
../../src/tools/eterm/eterm.cpp
../../src/tools/eterm/eterminaldisplay.cpp
../../src/tools/eterm/eterminaldisplay.hpp
../../src/tools/eterm/system/autohandle.cpp
../../src/tools/eterm/system/autohandle.hpp
../../src/tools/eterm/system/ipipe.hpp
@@ -1149,6 +1147,8 @@
../../src/tools/eterm/terminal/boxdraw.hpp
../../src/tools/eterm/terminal/boxdrawdata.hpp
../../src/tools/eterm/terminal/ipseudoterminal.hpp
../../src/tools/eterm/terminal/iterminaldisplay.cpp
../../src/tools/eterm/terminal/iterminaldisplay.hpp
../../src/tools/eterm/terminal/nonspacing.hpp
../../src/tools/eterm/terminal/pseudoterminal.cpp
../../src/tools/eterm/terminal/pseudoterminal.hpp
+4 -4
View File
@@ -1,8 +1,8 @@
#include "eterminaldisplay.hpp"
#include "terminal/terminaldisplay.hpp"
#include <eepp/ee.hpp>
EE::Window::Window* win = NULL;
std::shared_ptr<ETerminalDisplay> terminal = nullptr;
std::shared_ptr<TerminalDisplay> terminal = nullptr;
void inputCallback( InputEvent* event ) {
if ( !terminal )
@@ -101,8 +101,8 @@ EE_MAIN_FUNC int main( int, char*[] ) {
shell = "/bin/bash";
}
terminal = ETerminalDisplay::create( win, fontMono, PixelDensity::dpToPx( 11 ),
win->getSize().asFloat(), shell, {}, "", 0 );
terminal = TerminalDisplay::create( win, fontMono, PixelDensity::dpToPx( 11 ),
win->getSize().asFloat(), shell, {}, "" );
}
win->getInput()->pushCallback( &inputCallback );
File diff suppressed because it is too large Load Diff
-215
View File
@@ -1,215 +0,0 @@
#ifndef ETERMINALDISPLAY_HPP
#define ETERMINALDISPLAY_HPP
#include "system/iprocessfactory.hpp"
#include "terminal/terminaldisplay.hpp"
#include "terminal/terminalemulator.hpp"
#include <eepp/config.hpp>
#include <eepp/graphics/font.hpp>
#include <eepp/system/clock.hpp>
#include <eepp/window/inputevent.hpp>
#include <eepp/window/keycodes.hpp>
#include <eepp/window/window.hpp>
#include <atomic>
#include <memory>
#include <unordered_map>
#include <vector>
using namespace EE;
using namespace EE::Terminal;
using namespace EE::Window;
using namespace EE::System;
enum class TerminalShortcutAction { PASTE, COPY };
enum TerminalOptions {
OPTION_NONE = 0,
OPTION_COLOR_EMOJI = 1 << 0,
OPTION_PASTE_CRLF = 1 << 1
};
struct TerminalConfig {
int options;
};
struct TerminalKey {
Keycode keysym;
Uint32 mask;
const char* string;
int appkey;
int appcursor;
};
struct TerminalScancode {
Scancode scancode;
Uint32 mask;
std::string string;
int appkey;
int appcursor;
};
struct TerminalShortcut {
Keycode keysym;
Uint32 mask;
TerminalShortcutAction action;
int appkey;
int appcursor;
};
struct TerminalKeyMapEntry {
Uint32 mask;
std::string string;
int appkey;
int appcursor;
};
struct TerminalKeyMapShortcut {
Uint32 mask;
TerminalShortcutAction action;
int appkey;
int appcursor;
};
class TerminalKeyMap {
private:
std::unordered_map<Keycode, std::vector<TerminalKeyMapEntry>> m_keyMap;
std::unordered_map<Scancode, std::vector<TerminalKeyMapEntry>> m_platformKeyMap;
std::unordered_map<Keycode, std::vector<TerminalKeyMapShortcut>> m_shortcuts;
public:
TerminalKeyMap( const TerminalKey keys[], size_t keysLen, const TerminalScancode platformKeys[],
size_t platformKeysLen, const TerminalShortcut shortcuts[],
size_t shortcutsLen );
inline const std::unordered_map<Keycode, std::vector<TerminalKeyMapEntry>>& KeyMap() const {
return m_keyMap;
}
inline const std::unordered_map<Scancode, std::vector<TerminalKeyMapEntry>>&
PlatformKeyMap() const {
return m_platformKeyMap;
}
inline const std::unordered_map<Keycode, std::vector<TerminalKeyMapShortcut>>&
Shortcuts() const {
return m_shortcuts;
}
};
constexpr int TerminalKeyModFlags_Any = 0xFFFFFFFF;
extern TerminalKeyMap terminalKeyMap;
static const Scancode asciiScancodeTable[] = {
SCANCODE_A, SCANCODE_B, SCANCODE_C, SCANCODE_D, SCANCODE_E, SCANCODE_F,
SCANCODE_G, SCANCODE_H, SCANCODE_I, SCANCODE_J, SCANCODE_K, SCANCODE_L,
SCANCODE_M, SCANCODE_N, SCANCODE_O, SCANCODE_P, SCANCODE_Q, SCANCODE_R,
SCANCODE_S, SCANCODE_T, SCANCODE_U, SCANCODE_V, SCANCODE_W, SCANCODE_X,
SCANCODE_Y, SCANCODE_Z, SCANCODE_LEFTBRACKET, SCANCODE_SLASH, SCANCODE_RIGHTBRACKET };
class ETerminalDisplay : public TerminalDisplay {
public:
static std::shared_ptr<ETerminalDisplay>
create( EE::Window::Window* window, Font* font, const Float& fontSize, const Sizef& pixelsSize,
std::shared_ptr<TerminalEmulator>&& terminalEmulator, TerminalConfig* config = 0 );
static std::shared_ptr<ETerminalDisplay>
create( EE::Window::Window* window, Font* font, const Float& fontSize, const Sizef& pixelsSize,
const std::string& program, const std::vector<std::string>& args,
const std::string& workingDir, uint32_t options = 0,
EE::System::IProcessFactory* processFactory = nullptr );
virtual void resetColors();
virtual int resetColor( int index, const char* name );
virtual void setTitle( const char* title );
virtual void setIconTitle( const char* title );
virtual void setClipboard( const char* text );
virtual const char* getClipboard() const;
virtual bool drawBegin( int columns, int rows );
virtual void drawLine( Line line, int x1, int y, int x2 );
virtual void drawCursor( int cx, int cy, TerminalGlyph g, int ox, int oy, TerminalGlyph og );
virtual void drawEnd();
virtual void update();
void action( TerminalShortcutAction action );
bool hasTerminated() const;
void draw();
virtual void onMouseDoubleClick( const Vector2i& pos, const Uint32& flags );
virtual void onMouseMotion( const Vector2i& pos, const Uint32& flags );
virtual void onMouseDown( const Vector2i& pos, const Uint32& flags );
virtual void onMouseUp( const Vector2i& pos, const Uint32& flags );
virtual void onTextInput( const Uint32& chr );
virtual void onKeyDown( const Keycode& keyCode, const Uint32& chr, const Uint32& mod,
const Scancode& scancode );
Float getFontSize() const;
void setFontSize( const Float& FontSize );
const Vector2f& getPosition() const;
void setPosition( const Vector2f& position );
const Sizef& getSize() const;
void setSize( const Sizef& size );
bool isDirty() const { return mDirty; }
void invalidate();
bool hasFocus() const { return mFocus; }
void setFocus( bool focus );
bool isBlinkingCursor();
protected:
EE::Window::Window* mWindow;
std::vector<TerminalGlyph> mBuffer;
std::vector<std::pair<Color, std::string>> mColors;
std::shared_ptr<TerminalEmulator> mTerminal;
mutable std::string mClipboard;
Font* mFont{ nullptr };
Float mFontSize{ 12 };
Vector2f mPosition;
Sizef mSize;
int mColumns{ 0 };
int mRows{ 0 };
std::atomic<bool> mDirty{ true };
std::atomic<bool> mDrawing{ false };
Vector2i mCursor;
TerminalGlyph mCursorGlyph;
bool mUseColorEmoji{ true };
bool mPasteNewlineFix{ true };
bool mFocus{ true };
Clock mClock;
Clock mLastDoubleClick;
ETerminalDisplay( EE::Window::Window* window, Font* font, const Float& fontSize,
const Sizef& pixelsSize, TerminalConfig* config );
void draw( Vector2f pos );
Vector2i positionToGrid( const Vector2i& pos );
void onSizeChange();
Float getYOffset() const;
};
#endif // ETERMINALDISPLAY_HPP
+14 -6
View File
@@ -22,6 +22,7 @@
#ifndef _WIN32
#include "process.hpp"
#include <eepp/system/filesystem.hpp>
#include <poll.h>
#include <pwd.h>
#include <signal.h>
@@ -31,8 +32,6 @@
#include <sys/wait.h>
#include <unistd.h>
#define DEFAULT( a, b ) ( a ) = ( a ) ? ( a ) : ( b )
#if defined( __linux )
#include <pty.h>
#elif defined( __OpenBSD__ ) || defined( __NetBSD__ ) || defined( __APPLE__ )
@@ -102,8 +101,9 @@ int Process::getExitCode() const {
Process::Process( int pid ) : m_pid( pid ) {}
static void execshell( const char* cmd, const char* const* args ) {
static void execshell( const char* cmd, const char* const* args, std::string workingDirectory ) {
const struct passwd* pw;
const char* sh;
errno = 0;
if ( ( pw = getpwuid( getuid() ) ) == NULL ) {
@@ -116,12 +116,20 @@ static void execshell( const char* cmd, const char* const* args ) {
}
}
if ( ( sh = getenv( "SHELL" ) ) == NULL )
sh = ( pw->pw_shell[0] ) ? pw->pw_shell : cmd;
if ( workingDirectory.empty() )
workingDirectory = pw->pw_dir;
FileSystem::changeWorkingDirectory( workingDirectory );
unsetenv( "COLUMNS" );
unsetenv( "LINES" );
unsetenv( "TERMCAP" );
setenv( "LOGNAME", pw->pw_name, 1 );
setenv( "USER", pw->pw_name, 1 );
// setenv( "SHELL", sh, 1 );
setenv( "SHELL", sh, 1 );
setenv( "HOME", pw->pw_dir, 1 );
setenv( "TERM", "st-256color", 1 );
@@ -147,7 +155,7 @@ std::unique_ptr<Process> Process::createWithPipe( const std::string& /*program*/
std::unique_ptr<Process>
Process::createWithPseudoTerminal( const std::string& program, const std::vector<std::string>& args,
const std::string& /*workingDirectory*/,
const std::string& workingDirectory,
Terminal::PseudoTerminal& pseudoTerminal ) {
int pid = fork();
if ( pid == -1 ) {
@@ -181,7 +189,7 @@ Process::createWithPseudoTerminal( const std::string& program, const std::vector
argsV.push_back( a.c_str() );
}
argsV.push_back( nullptr );
execshell( program.c_str(), argsV.data() );
execshell( program.c_str(), argsV.data(), workingDirectory );
} else {
pseudoTerminal.m_slave.release();
return std::unique_ptr<Process>( new Process( pid ) );
@@ -19,7 +19,7 @@
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
#include "../terminal/terminaldisplay.hpp"
#include "../terminal/iterminaldisplay.hpp"
#include "../terminal/terminalemulator.hpp"
#include <assert.h>
@@ -27,28 +27,28 @@
using namespace EE::Terminal;
TerminalDisplay::TerminalDisplay() :
ITerminalDisplay::ITerminalDisplay() :
mMode( MODE_VISIBLE ), mCursorMode( SteadyBar ), mEmulator( nullptr ) {}
void TerminalDisplay::attach( TerminalEmulator* terminal ) {
void ITerminalDisplay::attach( TerminalEmulator* terminal ) {
assert( mEmulator == nullptr );
mEmulator = terminal;
}
void TerminalDisplay::detach( TerminalEmulator* terminal ) {
void ITerminalDisplay::detach( TerminalEmulator* terminal ) {
assert( mEmulator == terminal );
mEmulator = nullptr;
}
void TerminalDisplay::bell() {}
void ITerminalDisplay::bell() {}
void TerminalDisplay::resetColors() {}
void ITerminalDisplay::resetColors() {}
int TerminalDisplay::resetColor( int /*index*/, const char* /*name*/ ) {
int ITerminalDisplay::resetColor( int /*index*/, const char* /*name*/ ) {
return 0;
}
void TerminalDisplay::setMode( TerminalWinMode mode, int set ) {
void ITerminalDisplay::setMode( TerminalWinMode mode, int set ) {
int m = mMode;
MODBIT( ( (int&)mMode ), set, mode );
if ( ( mMode & MODE_REVERSE ) != ( m & MODE_REVERSE ) && mEmulator ) {
@@ -56,20 +56,20 @@ void TerminalDisplay::setMode( TerminalWinMode mode, int set ) {
}
}
void TerminalDisplay::setCursorMode( TerminalCursorMode cursor ) {
void ITerminalDisplay::setCursorMode( TerminalCursorMode cursor ) {
mCursorMode = cursor;
}
TerminalCursorMode TerminalDisplay::getCursorMode() const {
TerminalCursorMode ITerminalDisplay::getCursorMode() const {
return mCursorMode;
}
void TerminalDisplay::setTitle( const char* ) {}
void ITerminalDisplay::setTitle( const char* ) {}
void TerminalDisplay::setIconTitle( const char* ) {}
void ITerminalDisplay::setIconTitle( const char* ) {}
void TerminalDisplay::setClipboard( const char* ) {}
void ITerminalDisplay::setClipboard( const char* ) {}
const char* TerminalDisplay::getClipboard() const {
const char* ITerminalDisplay::getClipboard() const {
return "";
}
@@ -27,19 +27,19 @@ namespace EE { namespace Terminal {
class TerminalEmulator;
class TerminalDisplay {
class ITerminalDisplay {
public:
TerminalDisplay();
ITerminalDisplay();
virtual ~TerminalDisplay() = default;
virtual ~ITerminalDisplay() = default;
TerminalDisplay( const TerminalDisplay& ) = delete;
ITerminalDisplay( const ITerminalDisplay& ) = delete;
TerminalDisplay( TerminalDisplay&& ) = delete;
ITerminalDisplay( ITerminalDisplay&& ) = delete;
TerminalDisplay& operator=( const TerminalDisplay& ) = delete;
ITerminalDisplay& operator=( const ITerminalDisplay& ) = delete;
TerminalDisplay& operator=( TerminalDisplay&& ) = delete;
ITerminalDisplay& operator=( ITerminalDisplay&& ) = delete;
virtual void attach( TerminalEmulator* terminal );
@@ -77,7 +77,7 @@ const static unsigned int worddelimiters[] = { ' ', 0 };
*/
static const unsigned int tabspaces = 4;
#ifdef WIN32
#ifdef _WIN32
#include <windows.h>
#endif
@@ -1268,7 +1268,7 @@ void TerminalEmulator::csihandle( void ) {
char buf[40];
int len;
std::shared_ptr<TerminalDisplay> dpy{};
std::shared_ptr<ITerminalDisplay> dpy{};
switch ( mCsiescseq.mode[0] ) {
default:
@@ -1509,7 +1509,7 @@ void TerminalEmulator::strhandle( void ) {
strparse();
par = ( narg = mStrescseq.narg ) ? atoi( mStrescseq.args[0] ) : 0;
std::shared_ptr<TerminalDisplay> dpy = mDpy.lock();
std::shared_ptr<ITerminalDisplay> dpy = mDpy.lock();
switch ( mStrescseq.type ) {
case ']': /* OSC -- Operating System Command */
@@ -2222,7 +2222,7 @@ void TerminalEmulator::resettitle( void ) {
dpy->setTitle( NULL );
}
void TerminalEmulator::drawregion( TerminalDisplay& dpy, int x1, int y1, int x2, int y2 ) {
void TerminalEmulator::drawregion( ITerminalDisplay& dpy, int x1, int y1, int x2, int y2 ) {
int y;
for ( y = y1; y < y2; y++ ) {
@@ -2369,7 +2369,7 @@ void TerminalEmulator::xsetpointermotion( int ) {
std::unique_ptr<TerminalEmulator>
TerminalEmulator::create( PtyPtr&& pty, ProcPtr&& process,
const std::shared_ptr<TerminalDisplay>& display ) {
const std::shared_ptr<ITerminalDisplay>& display ) {
if ( !pty || !process ) {
fprintf( stderr, "Must provide valid pseudoterminal and process" );
return nullptr;
@@ -2380,7 +2380,7 @@ TerminalEmulator::create( PtyPtr&& pty, ProcPtr&& process,
}
TerminalEmulator::TerminalEmulator( PtyPtr&& pty, ProcPtr&& process,
const std::shared_ptr<TerminalDisplay>& display ) :
const std::shared_ptr<ITerminalDisplay>& display ) :
mDpy( display ),
mPty( std::move( pty ) ),
mProcess( std::move( process ) ),
@@ -37,7 +37,7 @@
#include "../system/iprocess.hpp"
#include "ipseudoterminal.hpp"
#include "terminaldisplay.hpp"
#include "iterminaldisplay.hpp"
#include "types.hpp"
#include <eepp/math/vector2.hpp>
#include <eepp/window/keycodes.hpp>
@@ -103,7 +103,7 @@ enum class TerminalMouseEventType { MouseMotion, MouseButtonDown, MouseButtonRel
class TerminalEmulator final {
public:
using DpyPtr = std::weak_ptr<TerminalDisplay>;
using DpyPtr = std::weak_ptr<ITerminalDisplay>;
using PtyPtr = std::unique_ptr<IPseudoTerminal>;
using ProcPtr = std::unique_ptr<System::IProcess>;
@@ -120,7 +120,7 @@ class TerminalEmulator final {
TerminalEmulator& operator=( TerminalEmulator&& ) = delete;
static std::unique_ptr<TerminalEmulator>
create( PtyPtr&& pty, ProcPtr&& process, const std::shared_ptr<TerminalDisplay>& display );
create( PtyPtr&& pty, ProcPtr&& process, const std::shared_ptr<ITerminalDisplay>& display );
void resize( int columns, int rows );
@@ -266,7 +266,7 @@ class TerminalEmulator final {
void selsnap( int*, int*, int );
void _die( const char*, ... );
void drawregion( TerminalDisplay& dpy, int, int, int, int );
void drawregion( ITerminalDisplay& dpy, int, int, int, int );
void draw();
int tattrset( int );
@@ -296,7 +296,7 @@ class TerminalEmulator final {
void xximspot( int, int );
TerminalEmulator( PtyPtr&& pty, ProcPtr&& process,
const std::shared_ptr<TerminalDisplay>& display );
const std::shared_ptr<ITerminalDisplay>& display );
};
}} // namespace EE::Terminal