Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Die Delphi-IDE (https://www.delphipraxis.net/62-die-delphi-ide/)
-   -   Feature: Block oder Zeile duplizieren (https://www.delphipraxis.net/166096-feature-block-oder-zeile-duplizieren.html)

s.h.a.r.k 30. Jan 2012 11:36

Feature: Block oder Zeile duplizieren
 
Hallo zusammen,

ich arbeite hin und wieder mit PhpED nur NuSphere und dort gibt es die nette Funktion, den markierten Block zu duplizieren bzw. wenn nichts markiert ist, dann wird die aktuelle Zeile dupliziert. Gibt es sowas eigentlich auch für die Delphi IDE? Ich habe leider bisher nicht weiteres gefunden, nicht im CnPack und auch nichts bei GExperts.

Bitte keine Diskussion über Copy-and-Paste-Fehler anfangen! Danke :stupid:

bernau 30. Jan 2012 11:46

AW: Feature: Block oder Zeile duplizieren
 
Ctrl-K C

Oder war was anderes gemeint?

s.h.a.r.k 30. Jan 2012 11:49

AW: Feature: Block oder Zeile duplizieren
 
Sehr hässlicher Shortcut, wie ich finde, aber genau das wars, was ich gesucht hatte :thumb:

Kann man den nicht zufälligerweise umbelegen?! *grml*

Hm... Und das "Zeile duplizieren" unterstützt die IDE auch nicht direkt...

Der.Kaktus 30. Jan 2012 12:14

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Gibt es sowas eigentlich auch für die Delphi IDE?
Aber ja doch.."Editoreigenschaften-IDE-Klassisch" :-D

Luckie 30. Jan 2012 12:28

AW: Feature: Block oder Zeile duplizieren
 
Und so bald man darüber nachdenkt diese Funktion zu benutzt, sollten alle Alarmglocken schrillen.

jaenicke 30. Jan 2012 12:29

AW: Feature: Block oder Zeile duplizieren
 
CnWizards: Strg + Alt + D

Alien426 30. Jan 2012 12:31

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von Luckie (Beitrag 1148246)
Und so bald man darüber nachdenkt diese Funktion zu benutzt, sollten alle Alarmglocken schrillen.

...wegen DRY.

haentschman 30. Jan 2012 12:46

AW: Feature: Block oder Zeile duplizieren
 
Ähmmm...

Copy Paste hat noch lange nix mit DRY zu tun.
Wenn ich eine Procedure kopiere die Daten holt, Objekte erzeugt und in einer Liste ablegt und diesen "Rumpf" mit der Erzeugung der Query etc. kopiere und anpasse auf das jeweilige Objekt wird nicht gegen DRY verstoßen. 8-)

Meine Meinungen gegen das Verteufeln von C&P ... :thumb: Dem Erfinder gehört ein Denkmal gesetzt...

Luckie 30. Jan 2012 12:52

AW: Feature: Block oder Zeile duplizieren
 
Ich habe es ja auch nicht verteufelt, nur sollte man sich dann fragen, ob man es nicht in eine Routine mit entsprechenden Parameteraufruf auslagern sollte.

DeddyH 30. Jan 2012 12:54

AW: Feature: Block oder Zeile duplizieren
 
Es kommt doch sehr darauf, was ich eigentlich kopieren will.

haentschman 30. Jan 2012 13:09

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

nur sollte man sich dann fragen, ob man es nicht in eine Routine mit entsprechenden Parameteraufruf auslagern sollte.
Klar kann man alles in eine Procedure packen. Aber bei 20 verschieden Listen mit 20 verschiedenen Objektypen der dazugehörigen SQL aus 20 verschiedenen Tabellen... sind mir 20 kleine übersichtliche Prozeduren allemal lieber.

himitsu 30. Jan 2012 13:16

AW: Feature: Block oder Zeile duplizieren
 
Ich würde es anders ausdrücken.

Diese Zeilen-/Block Kopierfunktion kompiert ja untereinanderliegende Zeilen/Blöcke.
Und so nh zusammenliegend sollte man nicht kopieren (das schreit regelrecht nach DRY).

Und ja, auch ich kopiere hin und wieder. (verändere danach aber auch so Einiges daran, also nicht 1:1)
Aber das ich dafür eine extra Tastenkombi benötige, ist mir noch nicht vorgekommen ... sooooooooo oft kopiere ich dann auch nicht :roll:

DeddyH 30. Jan 2012 13:20

AW: Feature: Block oder Zeile duplizieren
 
Folgendes Beispiel:
Delphi-Quellcode:
type
  IDings = interface
  ['{DCA3F4EE-8DDF-422C-8235-1AB3ADC70596}']
    procedure Machwas;
    procedure MachNochwas;
    procedure MachGarnix;
  end;

  TTest = class(TInterfacedObject, IDings)

  end;

  TNochnTest = class(TInterfacedObject, IDings)

  end;
Wenn mir nun jemand den Shortcut nennt, mit dem die Methoden aus dem Interface, die ja in den Klassen durch Einbinden desselben implementiert werden müssen, in die Klassendeklarationen kopiert werden, dann behaupte ich auch, C&P braucht man eigentlich nie. Es müssen auch nicht unbedingt Interfaces sein, Elternklassen mit abstrakten Methoden genügen auch.

himitsu 30. Jan 2012 14:26

AW: Feature: Block oder Zeile duplizieren
 
Hier wäre das Refactoring doch gut, also wenn man wie bei Strg+Shift+C die Methoden des Interfaces kopieren lassen könnte.
Ansonsten helfen doch auch die normalen Kopierfunktionen (Strg+C und Co.) oder was wölltest du einer spezialisierten Tastenkombo nich mitgeben wollen?

Ansonsten wäre sowas schön, wo Delphi die Public-Methoden und Property als Interface veröffentlicht und bei TTest dieses Interface mit verknüpft.
Delphi-Quellcode:
type
  TTest = class(TInterfacedObject)

  end;

  ITest = generate interface for TTest;

DeddyH 30. Jan 2012 14:32

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von himitsu (Beitrag 1148329)
Hier wäre das Refactoring doch gut, also wenn man wie bei Strg+Shift+C die Methoden des Interfaces kopieren lassen könnte.

Eben.
Zitat:

Zitat von himitsu (Beitrag 1148329)
Ansonsten helfen doch auch die normalen Kopierfunktionen (Strg+C und Co.)

Und genau darum geht es doch die ganze Zeit.

himitsu 30. Jan 2012 14:48

AW: Feature: Block oder Zeile duplizieren
 
Ich dachte jemand wollte eine Blockkopierfunktion, also einen eigenen Shortcut dafür?

DeddyH 30. Jan 2012 14:51

AW: Feature: Block oder Zeile duplizieren
 
Ab #5 kam der "Beigeschmack" auf, dass C&P beinahe zwangsgerade auf einen Verstoß gegen DRY hinweist/hinweisen könnte. Manchmal kommt man aber ohne nicht aus (C&P meine ich, nicht DRY), einfach weil die IDE keine Alternative bietet, das wollte ich mit meinem Beispiel zeigen.

ChrisE 30. Jan 2012 14:54

AW: Feature: Block oder Zeile duplizieren
 
Aber er hat doch extra drum gebeten:
Zitat:

Zitat von s.h.a.r.k (Beitrag 1148240)
Bitte keine Diskussion über Copy-and-Paste-Fehler anfangen! Danke :stupid:

Es ging doch nur um die Möglichkeit - um sonst nichts :-D

jaenicke 30. Jan 2012 16:35

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von DeddyH (Beitrag 1148269)
Wenn mir nun jemand den Shortcut nennt, mit dem die Methoden aus dem Interface, die ja in den Klassen durch Einbinden desselben implementiert werden müssen, in die Klassendeklarationen kopiert werden, dann behaupte ich auch, C&P braucht man eigentlich nie. Es müssen auch nicht unbedingt Interfaces sein, Elternklassen mit abstrakten Methoden genügen auch.

Dafür habe ich einen Experten geschrieben. Leider kann der die neue Syntax noch nicht. Der ist bei D2006 stehen geblieben. Und ich glaube auch nicht, dass ich den in absehbarer Zeit auf den Stand von XE2 bringen kann.
Aber ich könnte das Ding ja einfach mal veröffentlichen, vielleicht macht ja jemand weiter...

madtom 30. Jan 2012 17:14

AW: Feature: Block oder Zeile duplizieren
 
Hallo,

ein Stichwort wäre Key Binding über die ToolsAPI:
Delphi-Quellcode:
// Duplicate Line Key Binding
// Copyright (c) 2001-2010 Cary Jensen, Jensen Data Systems, Inc.


unit Dupline;

// Duplicate Line Key Binding
// Copyright (c) 2001-2010 Cary Jensen, Jensen Data Systems, Inc.
//
// You may freely distribute this unit, so long as this comment
// section is retained, and no fee is charged for it.
//
// This key binding is provided as a demonstration of key bindings.
//
// To use this key binding, install it into a design-time package.
//
// Once installed, this key binding adds a Ctrl-Shift-D (duplicate line) function to the code editor.
//
// No warranty is intended or implied concerning the
// appropriateness of this code example for any other use. If you use
// this examples, or any part of it, you assume all responsibility
// for ensuring that it works as intended.
//
// For information concerning Delphi training, visit www.jensendatasystems.com.

interface

uses
  SysUtils, Classes, Dialogs, Controls, Windows, Menus, ToolsAPI;

procedure register;

implementation

type
  TDupLineBinding = class(TNotifierObject, IOTAKeyboardBinding)
  private
  public
    procedure Dupline(const Context: IOTAKeyContext; KeyCode: TShortcut;
      var BindingResult: TKeyBindingResult);
    procedure AppendComment(const Context: IOTAKeyContext; KeyCode: TShortcut;
      var BindingResult: TKeyBindingResult);
    procedure CommentToggle(const Context: IOTAKeyContext; KeyCode: TShortcut;
      var BindingResult: TKeyBindingResult);
    procedure CommentToggle1(const Context: IOTAKeyContext; KeyCode: TShortcut;
      var BindingResult: TKeyBindingResult);

    { IOTAKeyboardBinding }
    function GetBindingType: TBindingType;
    function GetDisplayName: string;
    function GetName: string;
    procedure BindKeyboard(const BindingServices: IOTAKeyBindingServices);
  end;

procedure register;
begin
  (BorlandIDEServices as IOTAKeyboardServices).AddKeyboardBinding(TDupLineBinding.Create);
end;

{ TKeyBindingImpl }

function TDupLineBinding.GetBindingType: TBindingType;
begin
  Result := btPartial;
end;

function TDupLineBinding.GetDisplayName: string;
begin
  Result := 'Duplicate Line Binding';
end;

function TDupLineBinding.GetName: string;
begin
  Result := 'jdsi.dupline';
end;

procedure TDupLineBinding.BindKeyboard(const BindingServices: IOTAKeyBindingServices);
begin
  BindingServices.AddKeyBinding([Shortcut(Ord('D'), [ssShift, ssCtrl])], Dupline, nil);
  // BindingServices.AddKeyBinding([Shortcut(Ord('C'), [ssShift, ssCtrl])], AppendComment, nil);
  BindingServices.AddKeyBinding([Shortcut(VK_F1, [ssShift, ssCtrl])], CommentToggle, nil);
  // BindingServices.AddKeyBinding([Shortcut(VK_F1, [ssShift, ssCtrl])], CommentToggle1, nil);
  // Add additional key bindings here
end;

procedure TDupLineBinding.Dupline(const Context: IOTAKeyContext; KeyCode: TShortcut;
  var BindingResult: TKeyBindingResult);
var
  EditPosition: IOTAEditPosition;
  EditBlock: IOTAEditBlock;
  CurrentRow: Integer;
  CurrentRowEnd: Integer;
  BlockSize: Integer;
  IsAutoIndent: Boolean;
  CodeLine: string;
begin
  EditPosition := Context.EditBuffer.EditPosition;
  EditBlock := Context.EditBuffer.EditBlock;
  // Save the current edit block and edit position
  EditBlock.Save;
  EditPosition.Save;
  try
    // Store original cursor row
    CurrentRow := EditPosition.Row;
    // Length of the selected block (0 means no block)
    BlockSize := EditBlock.Size;
    // Store AutoIndent property
    IsAutoIndent := Context.EditBuffer.BufferOptions.AutoIndent;
    // Turn off AutoIndent, if necessary
    if IsAutoIndent then
      Context.EditBuffer.BufferOptions.AutoIndent := False;
    // If no block is selected, or the selected block is a single line,
    // then duplicate just the current line
    if (BlockSize = 0) or (EditBlock.StartingRow = EditPosition.Row) or
      ((BlockSize <> 0) and ((EditBlock.StartingRow + 1) = (EditPosition.Row)) and
        (EditBlock.EndingColumn = 1)) then
    begin
      // Only a single line to duplicate
      // Move to end of current line
      EditPosition.MoveEOL;
      // Get the column position
      CurrentRowEnd := EditPosition.Column;
      // Move to beginning of current line
      EditPosition.MoveBOL;
      // Get the text of the current line, less the EOL marker
      CodeLine := EditPosition.read(CurrentRowEnd - 1);
      // Add a line
      EditPosition.InsertText(#13);
      // Move to column 1
      EditPosition.Move(CurrentRow, 1);
      // Insert the copied line
      EditPosition.InsertText(CodeLine);
    end
    else
    begin
      // More than one line selected. Get block text
      CodeLine := EditBlock.Text;
      // Move to the end of the block
      EditPosition.Move(EditBlock.EndingRow, EditBlock.EndingColumn);
      // Add a line
      EditPosition.InsertText(#13);
      // Insert block text
      EditPosition.InsertText(CodeLine);
    end;
    // Restore AutoIndent, if necessary
    if IsAutoIndent then
      Context.EditBuffer.BufferOptions.AutoIndent := True;
    BindingResult := krHandled;
  finally
    // Move cursor to original position
    EditPosition.Restore;
    // Restore the original block (if one existed)
    EditBlock.Restore;
  end;
end;

procedure TDupLineBinding.AppendComment(const Context: IOTAKeyContext; KeyCode: TShortcut;
  var BindingResult: TKeyBindingResult);
var
  EditPosition: IOTAEditPosition;
  eColumn: Integer;
begin
  EditPosition := Context.EditBuffer.EditPosition;
  EditPosition.MoveEOL;
  eColumn := EditPosition.Column;
  EditPosition.InsertText(' // ' + DateTimeToStr(Now) + #13);
  EditPosition.Move(EditPosition.Row, eColumn);
  EditPosition.InsertText(' // Author: Cary Jensen');
  BindingResult := krHandled;
end;

procedure TDupLineBinding.CommentToggle(const Context: IOTAKeyContext; KeyCode: TShortcut;
  var BindingResult: TKeyBindingResult);
var
  EditPosition: IOTAEditPosition;
  EditBlock: IOTAEditBlock;
  StartRow: Integer;
  EndRow: Integer;
  Comment: Boolean;
begin
  // original edit position
  EditPosition := Context.EditBuffer.EditPosition;
  EditPosition.Save;
  // edit block
  EditBlock := Context.EditBuffer.EditBlock;
  // find the starting and ending rows to operate on
  if EditBlock.Size = 0 then
  begin
    StartRow := EditPosition.Row;
    EndRow := EditPosition.Row;
  end

  else if (EditBlock.EndingColumn = 1) then
  begin
    StartRow := EditBlock.StartingRow;
    EndRow := EditBlock.EndingRow - 1;
  end

  else
  begin
    StartRow := EditBlock.StartingRow;
    EndRow := EditBlock.EndingRow;
  end;

  // toggle comments
  repeat
  begin
    EditPosition.Move(StartRow, 1);
    while EditPosition.IsWhiteSpace do
      EditPosition.MoveRelative(0, 1);
    if EditPosition.Character = '/' then
    begin
      EditPosition.MoveRelative(0, 1);
      if EditPosition.Character = '/' then
        Comment := True
      else
        Comment := False
    end
    else
      Comment := False;

    if Comment then
    begin
      EditPosition.MoveRelative(0, -1);
      EditPosition.Delete(2);
    end
    else
    begin
      EditPosition.MoveBOL;
      EditPosition.InsertText('//');
    end;
    Inc(StartRow);
  end;
  until
    (StartRow > EndRow);
  // update caret position
  EditPosition.Restore;
  EditPosition.Move(StartRow, EditPosition.Column);
  // All done
  BindingResult := krHandled;
end;

procedure TDupLineBinding.CommentToggle1(const Context: IOTAKeyContext; KeyCode: TShortcut;
  var BindingResult: TKeyBindingResult);
begin
  //
end;

end.

s.h.a.r.k 30. Jan 2012 17:42

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von ChrisE (Beitrag 1148350)
Aber er hat doch extra drum gebeten:
Zitat:

Zitat von s.h.a.r.k (Beitrag 1148240)
Bitte keine Diskussion über Copy-and-Paste-Fehler anfangen! Danke :stupid:

Es ging doch nur um die Möglichkeit - um sonst nichts :-D

Genau darum hatte ich gebeten, ja ;)

Ich kläre hier auf, wofür ich es benötige und vor allem Pascal-Nutzer sollten sowas eigentlich häufiger nutzen, da es eine sehr schreibintensive Sprache ist. Beispiel:
Delphi-Quellcode:
procedure TMyClass.Test();
begin

end;
So... das habe ich geschrieben, halte Shift gedrückt und drücke vier mal auf die Pfeil-Nach-Oben-Taste und dann Ctrl+K+C. Ich füge nicht immer erst Methoden in die Klasse im type-Teil ein, sondern implementiere diese teilweise schon -- ob das nun richtig oder falsch ist darf jeder für sich entscheiden. Der Vorteil der Block-Duplicate-Methode sollte nun doch auf der Hand liegen, oder?

Und ja, ich kenne das DRY-Prinzip und beachte ich auch :) Danke für alles! :thumb:

Sir Rufo 30. Jan 2012 18:05

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von DeddyH (Beitrag 1148269)
Wenn mir nun jemand den Shortcut nennt, mit dem die Methoden aus dem Interface, die ja in den Klassen durch Einbinden desselben implementiert werden müssen, in die Klassendeklarationen kopiert werden, dann behaupte ich auch, C&P braucht man eigentlich nie. Es müssen auch nicht unbedingt Interfaces sein, Elternklassen mit abstrakten Methoden genügen auch.

Delphi-Quellcode:
type
  IDings = interface
  ['{DCA3F4EE-8DDF-422C-8235-1AB3ADC70596}']
    procedure Machwas;
    procedure MachNochwas;
    procedure MachGarnix;
  end;

  TTest = class(TInterfacedObject, IDings)
    // Please Press STRG-Space :o)
  end;

  TNochnTest = class(TInterfacedObject, IDings)

  end;

DeddyH 30. Jan 2012 18:18

AW: Feature: Block oder Zeile duplizieren
 
Gemacht, passiert ist... nichts oder gar noch weniger.

Sir Rufo 30. Jan 2012 18:22

AW: Feature: Block oder Zeile duplizieren
 
Liste der Anhänge anzeigen (Anzahl: 3)
ich versuche mal einen Screenshot zu machen ... sodele
nach dem Drücken von STRG-Leertaste sieht das so aus
Anhang 36155
jetzt die gewünschten Einträge markieren
Anhang 36156
und dann mit ENTER bestätigen
Anhang 36157
Schneller geht's nimmer :)

Installiert habe ich CnPack ... ich meine aber das ist ein Feature der IDE selber ... egal, es ist da :mrgreen:

einbeliebigername 30. Jan 2012 21:31

AW: Feature: Block oder Zeile duplizieren
 
Hallo,

in Delphi 7 ging das glaube ich noch einfacher. Nur Strg+Space und Enter. In der Liste, die bei Strg+Space auf geht, waren alle nicht überschriebenen abstrakten Methoden und alle fehlenden Interface-Implementierungen vorselektiert. Vieleicht bekommt Emba das mal wieder so hin. Ansonsten hilft da nur Copy and Paste. Denn wer kennt in jedem Fall alle Methoden des Interface, um sie in der Liste zu suchen. Und in den seltensten Fällen stehen die so schön zusammen. Mach das mal mit einem großen Interface bei einem anständigen WinControl. Viel Spaß beim Suchen.

einbeliebigername.

Sir Rufo 30. Jan 2012 21:36

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von einbeliebigername (Beitrag 1148398)
in Delphi 7 ging das glaube ich noch einfacher. Nur Strg+Space und Enter.

Wie jetzt noch einfacher? :gruebel:
Noch einfacher als STRG-Space, so wie ich gezeigt?

Ich habe nur gezeigt, wie man mehrere gleichzeitig auswählt und einfügt.
Will man nur einen Eintrag dann STRG-Leertaste, den richtigen auswählen und dann ENTER.

Achso, Delphi 7 weiß sofort welchen Eintrag ich will ... na dann ist das echt ein Rückschritt :mrgreen:

himitsu 30. Jan 2012 21:37

AW: Feature: Block oder Zeile duplizieren
 
Oh, man kann mehreres markieren :shock:

Wollte grade sagen, daß ich es ausprobiert hab, mir die alle möglichen Methoden vorgeschlagen wurden, welche man implementieren und eventuell sogar überschreiben könnte.
Aber wollte dann noch erwähnen, daß es etwas umständlich sei, wenn man jede Methode einzeln hinzufügen müßte ... also nix mit schneller geht's nimmer :lol:

ChrisE 31. Jan 2012 06:37

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von Sir Rufo (Beitrag 1148381)
Schneller geht's nimmer :)

Danach noch ein zünftiges STRG+C (Cursor sollte in der Klasse sein) und die Methoden sind mit den Rümpfen auch bereits im Implementationteil :thumb:

Sir Rufo 31. Jan 2012 06:53

AW: Feature: Block oder Zeile duplizieren
 
[klugscheiss]
shift+strg+c
[/klugscheiss]
;)

ChrisE 31. Jan 2012 08:20

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von Sir Rufo (Beitrag 1148429)
[klugscheiss]
shift+strg+c
[/klugscheiss]
;)

:-( - Natürlich - genau das meinte ich :oops:

himitsu 31. Jan 2012 08:36

AW: Feature: Block oder Zeile duplizieren
 
Zitat:

Zitat von ChrisE (Beitrag 1148428)
und die Methoden sind mit den Rümpfen auch bereits im Implementationteil :thumb:

Geht auch andersrum.
Du schreibs die Rümpfe und schwups sind sie auch in der Implementation.


Alle Zeitangaben in WEZ +1. Es ist jetzt 02:34 Uhr.

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz