Home > Mobile >  Optimised Function to copy columns of selected data by a variable amount (up/down)
Optimised Function to copy columns of selected data by a variable amount (up/down)

Time:05-31

Is it possible to create a javascript function that can be used in macros, that can move data by an amount when moving columns of data by variable rows. For example, by passing a parameter (iRow?) to something like setcolumn and it would insert the data either above (-1 to lose the first value and then insert which is like moving the column data up one line up for example) or 2 (to blank the first 2 rows column data and then paste the rest of the data, which is like moving it down 2 columns?

Ideally optimised for speed when working on very large amounts of data (millions of rows). Couple of examples. Col1 is source data, Col2 is copying that column and moving up by one row (-1). Col3 is copying that initial col and moving down by two ( 2):

Data Data-1 Data 2
00000001 00000002
00000002 00000003
00000003 00000004 00000001
00000004 00000005 00000002
00000005 00000006 00000003
00000006 00000007 00000004
00000007 00000008 00000005
00000008 00000009 00000006
00000009 00000010 00000007
00000010 00000008

CodePudding user response:

I wrote a JavaScript for EmEditor macro. MoveCells( -1, true ) copies the selected cells up to right, and MoveCells( 1, false ) moves the selected cells down.

// yShift : Specify how many rows to shift (move) the cell selection ( >0 : down, <0 : up )
function MoveCells( yShift, bCopy )
{
    if( !yShift || yShift == 0 ) {
        Quit();
    }
    if( !document.CellMode ) {   // Must be cell selection mode
        alert( "Cell selection mode must be turned on" );
        Quit();
    }

    xTop = document.selection.GetTopPointX(eePosCellLogical);
    yTop = document.selection.GetTopPointY(eePosCellLogical);
    xBottom = document.selection.GetBottomPointX(eePosCellLogical);
    yBottom = document.selection.GetBottomPointY(eePosCellLogical);

    yLines = document.GetLines();   // retrieve the number of lines
    if( document.GetLine( yLines ).length == 0 ) {  // -1 if the last line is empty
        --yLines;
    }

    if( yTop < 0 || xTop < 0 || xBottom < 0 || yBottom < 0 ) {
        alert( "Incorrect selection" );
        Quit();
    }
    if( xTop != xBottom ) {
        alert( "More than one columns are selected" );
        Quit();
    }

    bOldRedraw = Redraw;
    Redraw = false;
    bOldCombineHistory = CombineHistory;
    CombineHistory = false;
    yFirstLine = document.HeadingLines   1;
    if( (yShift < 0 && yTop   yShift < yFirstLine) || (yShift > 0 && yBottom   yShift > yLines) ) {
        if( yShift < 0 ) {
            document.selection.SetActivePoint( eePosCellLogical, xTop, yFirstLine );  // move to the first line
            nCount = yFirstLine - (yTop   yShift);
            for( i = 0; i < nCount;   i ) {
                document.selection.LineOpen(true);
            }
            yTop  = nCount;
            yBottom  = nCount;
        }
        else {
            document.selection.SetActivePoint( eePosCellLogical, xTop, yLines );  // move to the first line
            nCount = yBottom   yShift - yLines;
            for( i = 0; i < nCount;   i ) {
                document.selection.LineOpen(false);
            }
        }
    }

    sDelimiter = document.Csv.Delimiter;  // retrieve the delimiter
    str = document.GetColumn( xTop, sDelimiter, eeCellIncludeQuotes, yTop, yBottom - yTop   1 );  // get cell selections from top to bottom, separated by delimiter

    if( bCopy ) {
          xTop
        document.InsertColumn( xTop );
    }

    if( yShift > 0 ) {  // shift down
        for( i = 0; i < yShift;   i ) {  // insert delimiters before the copied string
            str = sDelimiter   str;
        }
        document.SetColumn( xTop, str, sDelimiter, eeDontQuote, yTop );
    }
    else {              // shift up
        for( i = 0; i < -yShift;   i ) {  // add delimiters to the copied string
            str  = sDelimiter;
        }
        document.SetColumn( xTop, str, sDelimiter, eeDontQuote, yTop   yShift );
    }

    document.selection.SetActivePoint( eePosCellLogical, xTop, yTop   yShift );  // move the current selection
    document.selection.SetActivePoint( eePosCellLogical, xTop, yBottom   yShift, true );

    Redraw = bOldRedraw;
    CombineHistory = bOldCombineHistory;
}

// Here is the main code
MoveCells( -1, true );  // Copy the selection up to right
MoveCells( 2, false );  // Move the selection down

To run this, save this code as, for instance, Macro.jsee, and then select this file from Select... in the Macros menu. Finally, select Run Macro.jsee in the Macros menu while the current CSV document is active.

References:

  • Related