2011-07-08 31 views
12

Czy jest możliwe wybranie tekstu (tj. Zaznaczenie go tak, aby można było skopiować i wkleić) każdej komórki w jednej pionowej kolumnie tabeli HTML.Zaznaczanie tekstu w kolumnie tabeli html

Czy istnieje metoda JavaScript, lub odpowiednik w niektórych przeglądarkach dla skrótu Alt-Click-Drag, używanego w wielu edytorach tekstu?

Czy to niemożliwe?

+2

+1 za dobre pytanie, ale podejrzewam, że to niemożliwe. Czy zdajesz sobie sprawę z tego, że użytkownik może ręcznie zrobić to samo? – nnnnnn

+0

Nie, nie w prosty sposób ... – cbp

Odpowiedz

8

To, czego szukasz, nazywa się obiektem Range (TextRange w IE).

Aktualizacja: Oto kod roboczych, aby robić to, co sugerujesz: http://jsfiddle.net/4BwGG/3/

podczas przechwytywania zawartości komórki, można formatować je w jakikolwiek sposób chcesz. Po prostu dodam nową linię za każdym razem.

Uwaga:

  • działa dobrze w FF 3 i powyżej
  • IE (przed 9) i Chrome nie obsługuje wielokrotnego wyboru.
  • Chrome nie podświetla wszystkich komórek (ale przechwytuje całą zawartość). To samo dotyczy IE9
  • IE 7 & 8 spowoduje błąd.

Alternatywą jest zastosowanie stylu CSS, który symulujepodświetlanie na kliknięcie nagłówka kolumny i pętli przez wszystkie komórki, aby uchwycić ich treść. Wygląd i styl tego podejścia mogą się różnić od wyglądu natywnego selekcji (chyba że w jakiś sposób uchwycisz wybrane wydarzenie i zmienisz jego wygląd).

Następnie użyj wtyczki jQuery copy, aby skopiować je do schowka.

+0

Czy to nie wystarczy wybrać jedną komórkę? Chcę wybrać całą kolumnę! – cbp

+0

To jest tylko kod demonstracyjny. Jeśli chcesz całą kolumnę, powtórz proces dla wszystkich 'TD's – Mrchief

+0

Dlaczego spadły? – Mrchief

3

Można mieć div, który pobiera wypełniona danymi kolumnowej na kliknięcia i zastosować klasę css dać kolumn z appearence zostanie wybrany

coś takiego:

var $mytable = $("#mytable"), 
    $copydiv = $("#copy_div"); 

$mytable.find("td").click(function(){ 

    //get the column index 
    var $this = $(this), 
     index = $this.parent().children().index($this); 

    //find all cells in the same column 
    $mytable.find("tr:nth-child(" + index + ")").removeClass("selected").each(function() { 
     var $this = $(this); 
     $this.addClass("selected"); 
     $copydiv.html($this.html() + "<br />"); 
    }); 
}); 

czy mógłbyś mieć oddzielną tabelę dla każdej kolumny, ale nie sądzę, że byłaby tego warta.

6

Niektóre narzędzia do sprawdzania kodu implementują to, aby umożliwić kopiowanie kodu z jednej strony porównania "na boku". Sprawdziłem, jak ReviewBoard wyciąga go.

Istotą jest:

  1. Gdy rozpoczyna się wybór kolumny, styl komórki we wszystkich innych kolumn z user-select: none (i jego warianty, if necessary prefiksem). Spowoduje to utworzenie wyglądu kolumny. Pozostałe kolumny są nadal potajemnie wybrane, więc musisz ...
  2. Przechwycić zdarzenie copy i zmienić jego ładunek, aby odzwierciedlić zawartość wybranej kolumny.

Kod weryfikacyjny w tym celu składa się z this CSS i this JavaScript.

Wyciągnąłem go do dość minimalnego jsbin demo.

Oto CSS do tworzenia wyglądu wyboru jednej kolumny (trzeba dodać klasę selecting-left do stołu, gdy lewa kolumna jest zaznaczona, lub selecting-right do prawej):

.selecting-left td.right, 
.selecting-left td.right *, 
.selecting-right td.left, 
.selecting-right td.left *, 
    user-select: none; 
} 

.selecting-left td.right::selection, 
.selecting-left td.right *::selection, 
.selecting-right td.left::selection, 
.selecting-right td.left *::selection, 
    background: transparent; 
} 

Oto JavaScript, żeby przechwycić zdarzenie copy i podłączyć wartości pojedynczej kolumny danych:

tableEl.addEventListener('copy', function(e) { 
    var clipboardData = e.clipboardData; 
    var text = getSelectedText(); 
    clipboardData.setData('text', text); 
    e.preventDefault(); 
}); 

function getSelectedText() { 
    var sel = window.getSelection(), 
     range = sel.getRangeAt(0), 
     doc = range.cloneContents(), 
     nodes = doc.querySelectorAll('tr'), 
     text = ''; 

    var idx = selectedColumnIdx; // 0 for left, 1 for right 

    if (nodes.length === 0) { 
    text = doc.textContent; 
    } else { 
    [].forEach.call(nodes, function(tr, i) { 
     var td = tr.cells[tr.cells.length == 1 ? 0 : idx]; 
     text += (i ? '\n' : '') + td.textContent; 
    }); 
    } 

    return text; 
} 

jest też kilka mniej interesujący kod, aby dodać selecting-left i selecting-right cl ocenia na początku selekcji. Wymagałoby to nieco więcej pracy do uogólnienia na tabele z kolumną n.

Wydaje się, że działa to dobrze w praktyce, ale to zaskakujące, jak trudne!

+1

To powinna być zaakceptowana odpowiedź. Wspomniany wyżej nie działa w ogóle. –

+0

Czy to działa na FF, Chome? – seebiscuit

+0

To zostało złamane w Firefoksie. Zaktualizowałem link do wersji demo i powinien działać już teraz. Zmiana polegała na usunięciu '-moz-user-select: -moz-none'. Nowe wersje Firefoksa rozumieją zwykły "none". Zachowanie kopiowania/wklejania zawsze działało w FF, był to tylko uszkodzony ekran. – danvk

Powiązane problemy