Créer un éditeur de ligne simple

19

In: une chaîne sans saut de ligne *
Autoriser l'utilisateur à modifier et soumettre la ligne
Out: saut de la chaîne modifiée (éventuellement avec un saut de ligne de fin)

L'éditeur de ligne doit au minimum permettre à l'utilisateur de:

  1. déplacer un curseur visible de gauche à droite

  2. insérer et / ou écraser des caractères à la position du curseur

  3. supprimer les caractères à la position du curseur

  4. soumettre la nouvelle chaîne, c.-à-d. cesser de modifier la chaîne modifiée doit être retournée / imprimée / affichée / enregistrée… (sans autre texte)

Apprécié, mais pas obligatoire:

  • explication de votre code.

  • lien vers un site de test en ligne qui peut démontrer votre programme / fonction

  • une image animée démontrant l'utilisation (TIO, par exemple, ne permet pas l'interactivité)

Remarque:

  • les raccourcis clavier ne sont que des suggestions

  • Une interface graphique ou un style visuel n'est pas requis

Exemples

Dans ce qui suit, le curseur est illustré par _.

In: Just some text
Autoriser l'utilisateur à modifier: L'
Just some text_  utilisateur appuie neuf fois sur la touche (flèche gauche) L'
Just ̲some text  utilisateur appuie Delquatre fois L'
Just ̲ text  utilisateur appuie L'  utilisateur appuie sur Out:any
Just any_text Enter
Just any text

In: Remove me
Autoriser l'utilisateur à modifier: L'
Remove me_  utilisateur appuie Backspaceneuf fois L'
_  utilisateur appuie sur Out: (chaîne vide)Enter
 


* Pour éviter des solutions d'édition triviales, celles-ci doivent soit être fournies via une méthode d'entrée différente de celle des commandes d'édition, soit être séparées d'elles par une nouvelle ligne ou similaire.

Adam
la source
Faut-il utiliser ces touches exactes pour les E / S? Aussi, pouvons-nous créer un fichier dans lequel enregistrer le texte?
Rɪᴋᴇʀ
1
Les raccourcis clavier @Riker ne sont que des suggestions . Les méthodes d'entrée et de sortie suivent les valeurs par défaut PPCG .
2017
La chaîne peut-elle contenir des sauts de ligne? Et une nouvelle ligne peut-elle être utilisée pour «soumettre»?
Conor O'Brien
@ ConorO'Brien Non; Éditeur de ligne simple . Oui; L'éditeur doit au minimum permettre à l'utilisateur de: (...) 4. soumettre la nouvelle chaîne
Adám
1
Ce serait bien si vous spécifiez une ligne dans le corps même de la question, car les titres sur ce site ne sont pas exactement des spécifications ...
Conor O'Brien

Réponses:

3

APL (Dyalog) , 5 octets

⍞←⍞⋄⍞

Ceci est un tradfn, donc pour l'utiliser, faites

a
⍞←⍞⋄⍞

Et puis appelez-le en utilisant a, après quoi vous fournissez la chaîne de départ, puis vous pouvez modifier la chaîne.

Kritixi Lithos
la source
8

JavaScript (ES6), 15 14 octets

Je ne comprends pas pourquoi cela fait autant de votes positifs!

s=>prompt(s,s)

Enregistrement d 'un octet grâce à la suggestion d' Adám d 'afficher l' entrée originale dans le prompt.


Essayez-le

f=
s=>prompt(s,s)
console.log(f("Edit this ..."))

Hirsute
la source
1
Enregistrez un octet en le remplaçant ""par 0ou même s(afin que l'utilisateur puisse toujours voir le texte d'origine lors de l'édition - une fonctionnalité intéressante).
2017
5

Bash 4.x, 25 caractères

read -ei "$*" t
echo "$t"

Exemple d'exécution:

bash-4.3$ bash interactive.sh hello world
hello golfing world
hello golfing world

(La ligne 2 ci-dessus était l'édition interactive, la ligne 3 la sortie du texte résultant.)

homme au travail
la source
1
Ça ne marche pas, pour moi -bash: read: -i: invalid option,? mandit que seuls ersles drapeaux sont autorisés.
Rɪᴋᴇʀ
Ouais, j'étais sur le point de poser des questions sur-ei
Adam
-ia été introduit dans Bash 4.0 (publié en février 2009) - «-i text Utilisez TEXT comme texte initial pour Readline».
manatwork
Je me demande, est-ce que le chat fonctionnerait?
Matthew Roh
catn'attend que le flux entrant, pour lequel le shell ne fournira aucune fonctionnalité d'édition. Du moins pas par défaut.
manatwork
3

Bash + Vi / Vim, 14 octets

echo $1>a;vi a

viest aliasé vimsur macOS, je ne connais pas les autres OS.

Rɪᴋᴇʀ
la source
Peut-être que je manque quelque chose, mais cela répond-il à l'exigence de sortie de la chaîne modifiée?
Grayson Kent
1
@GraysonKent vous pouvez enregistrer et quitter en appuyant sur :wq!ou :x, donc je pense que oui. OP n'est pas clair sur ce qui peut être qualifié de cela.
Rɪᴋᴇʀ
3

HTML + JavaScript (ES6), 77 66 64 octets

HTML

<input id=t

Javascript

onkeyup=e=>e.which-13||alert(t.value);f=a=>t.value=a;

10 octets enregistrés grâce à Jörg Hülsermann et 2 octets grâce à Luke.

onkeyup=e=>e.which-13||alert(t.value);f=a=>t.value=a;

f("Remove Me");
<input id=t>

À M
la source
2
vous pouvez supprimer l'attribut de type pour l'élément d'entrée
Jörg Hülsermann
Vous devriez probablement utiliser à la oninputplace.
Matthew Roh
@SIGSEGV Je ne pense pas qu'il se oninputdéclenche quand Enteron appuie dessus
Tom
1
e.which==13?alert(t.value):0-> e.which-13||alert(t.value)enregistre deux octets.
Luke
3

Python 2 , 275 200 octets

Pas un gagnant, mais le voici:

from msvcrt import*
s=list(input())[::-1]
c=i=0
def p(a):print''.join(a)[::-1]
while'\r'!=c:p(s[:i]+['<']+s[i:]);c=getch();x=c!='\b';exec["s[i:i+1-x]=c*x","i=(i-1+2*(c<'\\t'))%-~len(s)"][x*' '>c]
p(s)

Explication:

Il fonctionne en inversant l'entrée (avec [::-1] ), et en excluant et en insérant des caractères dans cette entrée inversée afin que le curseur n'ait pas à se déplacer. Inverse à nouveau lors de l'impression.

Usage:

Touche [Tab] pour se déplacer vers la droite
[Ctrl + C] pour déplacer vers la gauche
[Retour arrière] pour effacer
[Retour] pour terminer l'édition
Toute autre touche sera insérée dans le texte

Exemple:

Utilisation de l'exemple d'OP

In: l' Just some text
Just some text>
Just some> text  utilisateur appuie Ctrl+Ccinq fois l'
Just > text  utilisateur appuie Backspacequatre fois l'
Just any> text  utilisateur appuie l'  utilisateur appuie sur Out:any
Just any> text Enter
Just any text

Version de l'éditeur en ligne:

Si vous souhaitez que le texte soit édité en ligne, ajoutez ,'\r',à la fin de l' printinstruction:

def p(a):print''.join(a)[::-1],'\r',
Felipe Nardi Batista
la source
6
+1 Très sympa. Première réponse qui implémente réellement un véritable éditeur, au lieu de s'appuyer sur des fonctionnalités préexistantes. J'envisageais de publier un autre défi pour faire exactement cela.
2017
Vous ne pouvez pas enregistrer des octets en utilisant d'autres touches pour la gauche et la droite?
2017
Je pourrais assumer des personnages au fur -et +à mesure, mais l'éditeur ne serait pas en mesure d'accepter ces personnages à ce moment
Felipe Nardi Batista
Que diriez-vous \tet \v?
2017
1
C'est le problème de l'utilisateur, non? Contrôle + K, peut-être?
2017 à 13h17
3

C + NCURSES, 573 octets

#include <curses.h>
i;j;k;s;c;p;int main(a,b)char**b;{char*q;char t[999];if(a&&(q=b[1]))while(*q)t[s++]=*q++;i=s;initscr();noecho();keypad(stdscr,1);do{for(j=0;j<i;j++)addch(t[j]);addch('|');for(j=i;t[j];j++)addch(t[j]);c=getch();switch(c){case KEY_LEFT:if(i)i--;break;case KEY_RIGHT:if(i<s)i++;break;case 8:case 127:case KEY_BACKSPACE:if(i){for(k=i-1;k<s;k++)t[k]=t[k+1];i--;s--;}break;case KEY_DC:if(i<s){for(k=i;k<s;k++)t[k]=t[k+1];s--;}break;default:if(c>31&c<127){for(k=s;k>i;k--)t[k]=t[k-1];t[i]=c;i++;s++;}}clear();}while(c!=10);printw(t);getch();endwin();return 0;}

Tester

  • Compiler et exécuter avec entrée Just some text.

enter image description here

enter image description here

  • Appuyez neuf fois sur le bouton Flèche gauche.

enter image description here

  • Appuyez quatre fois sur le bouton Supprimer.

enter image description here

  • Appuyez aensuite nalors y.

enter image description here

  • Appuyez Enterpour terminer.

enter image description here

Détaillé

#include <curses.h>

int main(int argc, char ** argv)
{
    char*q = 0;
    char t[999] = {0};
    int j = 0, k = 0;
    int i = 0; // cursor before first char
    int s = 0; // current size
    int c = 0; // current input
    int p = 0;

    // copy first command-line argument
    if(argc>0 && (q=argv[1]))while(*q)t[s++]=*q++; i=s;

    initscr(); // initiate NCURSES
    noecho(); // input does not echo on entry
    keypad(stdscr,TRUE); // handle all input

    do
    {
        // print current content with cursor
        for(j=0;j<i;j++) addch(t[j]);
        addch('|'); for(j=i;t[j];j++) addch(t[j]);

//      printw("\n\n> key %d pressed",c); // debug

        c = getch(); // read next char

        switch(c)
        {
            case KEY_LEFT: // left arrow; cursor left
            if(i > 0) i--;
            break;

            case KEY_RIGHT: // right arrow; cursor right
            if(i < s) i++;
            break;

            case 8: // backspace; remove previous char
            case 127:
            case KEY_BACKSPACE:
            if(i > 0)
            {
                for(k=i-1; k<s; k++) t[k]=t[k+1];
                i--;s--;
            }
            break;

            case KEY_DC: // delete; remove next char
            if(i < s)
            {
                for(k=i; k<s; k++) t[k]=t[k+1];
                s--;
            }
            break;

            default: // none of the above

            if(c > 31 && c < 127) // printable char
            {
                for(k=s; k>i; k--) t[k]=t[k-1];
                t[i] = c;i++;s++;
            }
        }

        clear(); // clear screen
        if(c == 10) break;
    }
    while(c);

    addch('\n');
    printw(t); // print final result
    getch(); // wait for any input
    endwin();
    return 0;
}
Khaled.K
la source
Ne pouvez-vous pas remplacer KEY_*par les entiers respectifs pour enregistrer quelques octets?
sergiol
2

VBScript, 23 40 octets

MsgBox InputBox("",,Wscript.Arguments(0))

enter image description here

Johan du Toit
la source
2

C #, 53 octets

s=>{SendKeys.SendWait(s);return Console.ReadLine();};

sest une chaîne à modifier et la sortie est la nouvelle valeur.

SendKeys.SendWait : envoie les clés données à l'application active, puis attend que les messages soient traités.

ou 74 octets si nous ne sommes pas dans un contexte Windows Forms:

s=>{System.Windows.Forms.SendKeys.SendWait(s);return Console.ReadLine();};

gif demo

aloisdg dit Réintégrer Monica
la source
2

Rubis, 9 19 22 84 octets

->s{r=Readline;r.pre_input_hook=->{r.insert_text s;r.redisplay};r.readline}

Cela crée un crochet de pré-entrée Readline qui insère le texte s puis réaffiche. Après cela, irb est gâché alors assurez-vous de l'exécuter à partir d'un fichier. Exécuté en tant que lambda, il prend la chaîne d'entrée comme argument et renvoie la chaîne de sortie.

puts Readline.readline

Cela utilise la bibliothèque Readline pour effectuer la modification de ligne. Ma réponse précédente ne permettait que les backspaces.

puts gets

C'est vraiment, vraiment explicite.

Edit: on m'a demandé une explication. C'est équivalent à puts(gets). getssaisit une chaîne avec un éditeur de ligne. putsle produit.

dkudriavtsev
la source
Enchaînez les appels de méthode: r.insert_text(s).redisplayet supprimez les éléments suivants ;. BTW, si je comprends bien notre politique, vous devez mentionner que votre code s'exécute irb, car sinon vous auriez besoin de l'exiger Readlinedans votre code.
manatwork du
1

PHP + HTML, 26 octets

<input value=<?=$_GET[0]?>

Le navigateur ajoute automatiquement la balise de fermeture

$ _GET Utiliser une URL comme http://example.com?0=inputentrée crée dans un HTML<input value=input

Et ceci est la sortie pour l'entrée de chaîne

<input value=input

Jörg Hülsermann
la source
Dois-je supposer que cela fonctionne? Peut-être pouvez-vous ajouter une explication, un lien ou une animation?
2017
@ Adám Oui, vous pouvez assumer cela Peut-être que vous améliorerez et définissez l'attribut autofocuspour avoir le curseur au début. D'autres éléments HTML que vous pouvez également modifier si vous définissez l'attributcontenteditable
Jörg Hülsermann
Entrée =test></input><script>alert("Hi");//some malicious code\n</script>
Roman Gräf
@ RomanGräf Bad Boy. Oui, il vaut mieux filtrer Javascript
Jörg Hülsermann
1

Tcl, 17

puts [gets stdin]

Les interprètes en ligne craignent de le démontrer, puis je présente quelques images à partir d'un shell de commande Windows:

Cas de test 1

enter image description hereenter image description hereenter image description hereenter image description hereenter image description here

Cas de test 2

enter image description hereenter image description here enter image description here

sergiol
la source
Pouvez-vous expliquer celui-ci?
2017
1
Je peux en ajouter des images exécutées sur une ligne de commande Windows.
sergiol
@ Adám: Voulez-vous toujours que j'explique ce que fait le code ou les images sont-elles suffisantes?
sergiol
C'est assez.
2017
1

AHK , 32 octets

InputBox,s,,,,,,,,,,%1%
Send,%s%

InputBoxstocke tout ce qui est tapé comme variable set donne une invite de démarrage de la variable 1qui est le premier paramètre passé.
Sendenvoie des frappes à la fenêtre actuelle. Dans ce cas, ce sera le contenu de s.
MsgBoxétait une option mais, pour le golf, Sendest de 2 octets plus court.

Animation

Ingénieur Toast
la source
@ Adám, j'ai mal lu cette partie. J'ai mis à jour la réponse.
Ingénieur Toast
Maintenant c'est bon.
2017
1

Commande de fenêtre immédiate Excel VBA - 22 octets

[a1]=inputbox(0,,[a1])

enter image description here

Rohan
la source
2
Ce n'est qu'une solution partielle, car votre valeur initiale ("Hi") est codée en dur. La valeur initiale doit être lue quelque part (une cellule ou une invite ou un fichier ...) et la valeur finale doit être placée quelque part (une cellule, une boîte de message, un fichier, ...).
Adám
inputbox(0,,"Hi")sauve un octet
Felipe Nardi Batista
@ Adám Merci. Correction de la lecture de la cellule A1
Rohan
Je pense que vous avez besoin [a1]=inputbox(0,,[a1])ou quelque chose, sinon, où va a-t-il? Le stockage dans une variable n'est pas une méthode de sortie valide .
2017
Il va d'où il vient de la cellule A1
Rohan
0

ZX Spectrum BASIC, 7 octets

Trivial, inclus pour être complet ( INPUTet PRINTsont des jetons d'un octet chacun).

INPUT a$: PRINT a$
Radovan Garabík
la source
1
Comment obtient-il la valeur initiale de a$?
2017
@ Adám, il obtient la valeur initiale de a$par saisie au clavier; a$sera remplacé par le INPUTmot clé.
Shaun Bebbers
0

SmileBASIC, 138 octets

DEF E S@L
WAIT
B=BUTTON(1)C=C-(B==4&&C)+(B>7&&C<LEN(S))I$=INKEY$()IF"\u0008"<I$THEN B=I$<"\u000E"S=SUBST$(S,C,B,I$*!B)?S?" "*C;1IF"\u0008"!=I$GOTO@L
END

Crée une fonction E avec 1 argument et 0 sorties. (La sortie est affichée dans la console)

Les caractères échappés devraient être les symboles réels, mais ils n'apparaîtraient pas ici.

Contrôles:

Normal keys: Insert a character before the cursor.
Enter: Delete the character at the cursor.
Backspace: Submit.
D-pad left: Move cursor left.
All buttons except up, down, and left on the d-pad: Move cursor right.

L'insertion / suppression de caractères est à l'envers, donc c'est très ennuyeux à utiliser (mais devrait toujours répondre aux exigences).

Just some text
1             
'(press right 5 times)
Just some text
     1
'(press enter 4 times)
Just  text
     1
'(press a)
Just a text
     1
'(press right)
Just a text
      1
'(...)
Just any text
       1
'(press backspace)
12Me21
la source
0

Interpréteur de commandes Windows, 16 octets

set/pa=
echo %a%

C'est très trivial; l'interpréteur de commandes est trivialement un "éditeur de ligne".

UNE
la source
0

Commodore BASIC (C64Mini, C64 / 128, VIC-20 etc ...) 179 octets BASIC tokenisés

Cela doit être tapé en mode entreprise (caractères majuscules / minuscules)

 0a$="Just some text":?"{SHIFT+CLR/HOME}"a$"_":fOi=0to1step0:getk$:on-(k$<>"")goS2:goS1:nE
 1?"{CTRL+N}{CLR/HOME}"a$"_  ";:return
 2ifasc(k$)<>20thena$=a$+k$:on-(asc(k$)=13)goS4:return
 3if-(len(a$))thena$=leF(a$,len(a$)-1):goS4:return
 4?"{ARROW LEFT}{ARROW LEFT}{ARROW LEFT}  ":return

Permet l'édition de texte de base + suppression + nouvelle ligne. La taille maximale de a$comme toutes les chaînes dans Commodore BASIC est de 255 caractères, donc plus que cela plantera le programme. Je trouverai un moyen de faire> 255 caractères si cela est nécessaire.

Simple type-em-up simulator

Simple type-em-up simulator in action

Shaun Bebbers
la source