Potrzebuję dwóch sposobów wyświetlania etykiety pionowej w systemie Android:
- Etykieta pozioma obrócona o 90 stopni w kierunku przeciwnym do ruchu wskazówek zegara (litery z boku)
- Pozioma etykieta z literami jedna pod drugą (jak szyld sklepu)
Czy muszę opracować niestandardowe widżety dla obu przypadków (jeden przypadek), czy mogę sprawić, by TextView renderował w ten sposób i jaki byłby dobry sposób na zrobienie czegoś takiego, jeśli muszę przejść całkowicie niestandardowo?
android
label
textview
vertical-alignment
Bostone
źródło
źródło
Odpowiedzi:
Oto moja elegancka i prosta implementacja tekstu pionowego, rozszerzająca TextView. Oznacza to, że można używać wszystkich standardowych stylów TextView, ponieważ jest to rozszerzony TextView.
Domyślnie tekst obrócony jest od góry do dołu. Jeśli ustawisz android: gravity = "bottom", będzie rysowany od dołu do góry.
Technicznie rzecz biorąc, to oszukuje podstawowy TextView, myśląc, że jest to normalny obrót (zamiana szerokości / wysokości w kilku miejscach), podczas rysowania jest obracany. Działa dobrze również wtedy, gdy jest używany w układzie XML.
EDYCJA: wysyłanie innej wersji, powyżej ma problemy z animacjami. Ta nowa wersja działa lepiej, ale traci niektóre funkcje TextView, takie jak marquee i podobne specjalizacje.
EDYTUJ wersję Kotlin:
źródło
TextView
. Właściwie linki są podkreślone, ale nie reagują na kliknięcie.Zaimplementowałem to dla mojego projektu ChartDroid . Utwórz
VerticalLabelView.java
:A w
attrs.xml
:źródło
Jednym ze sposobów osiągnięcia tego byłoby:
źródło
\n
po każdym znaku lub jeśli masz czcionkę o stałej szerokości, ogranicz szerokość TextView, aby zmieściła się tylko na jednym znaku.Wypróbowałem obie klasy VerticalTextView w zatwierdzonej odpowiedzi i działały dość dobrze.
Ale bez względu na to, co próbowałem, nie mogłem umieścić tych VerticalTextViews w środku zawierającego układu (RelativeLayout, który jest częścią elementu zawyżonego dla RecyclerView).
FWIW, po rozejrzeniu się, znalazłem klasę VerticalTextView yoog568 na GitHub:
https://github.com/yoog568/VerticalTextView/blob/master/src/com/yoog/widget/VerticalTextView.java
które mogłem ustawić zgodnie z życzeniem. W swoim projekcie musisz również uwzględnić następujące definicje atrybutów:
https://github.com/yoog568/VerticalTextView/blob/master/res/values/attr.xml
źródło
To zadziałało dla mnie, po prostu dobrze. Co do liter opadających pionowo - nie wiem.
źródło
Jest kilka drobnych rzeczy, na które należy zwrócić uwagę.
Zależy to od zestawu znaków przy wybieraniu obrotu lub ścieżek. na przykład, jeśli docelowy zestaw znaków jest podobny do angielskiego, a oczekiwany efekt wygląda tak,
możesz uzyskać ten efekt, rysując każdą postać po kolei, bez obracania lub ścieżki.
aby uzyskać ten efekt, może być potrzebny obrót lub ścieżka.
trudna część polega na tym, że próbujesz renderować zestaw znaków, taki jak mongolski. glif w kroju pisma należy obrócić o 90 stopni, więc drawTextOnPath () będzie dobrym kandydatem do użycia.
źródło
Podążając za odpowiedzią Pointer Null , mogłem wyśrodkować tekst w poziomie, modyfikując
onDraw
metodę w ten sposób:Może być konieczne dodanie części elementu TextView MeasuringWidth, aby wyśrodkować tekst wielowierszowy.
źródło
Możesz po prostu dodać do swojego TextView lub innej wartości obrotu XML widoku. To najłatwiejszy sposób i jak dla mnie działa poprawnie.
źródło
Moje wstępne podejście do renderowania tekstu pionowego wewnątrz pionowego LinearLayout było następujące (jest to Kotlin, w Javie
setRoatation
itp.):Jak widać, problem polega na tym, że TextView przesuwa się pionowo, ale nadal traktuje swoją szerokość tak, jakby był zorientowany poziomo! = /
Zatem podejście nr 2 polegało na dodatkowym ręcznym przełączaniu szerokości i wysokości w celu uwzględnienia tego:
Spowodowało to jednak zawijanie etykiet do następnego wiersza (lub przycinanie, jeśli ty
setSingleLine
) po stosunkowo małej szerokości. Ponownie, sprowadza się to do pomylenia x z y.Moje podejście nr 3 polegało więc na zawinięciu TextView w RelativeLayout. Chodzi o to, aby pozwolić TextView na dowolną szerokość, rozszerzając go daleko w lewo i w prawo (tutaj 200 pikseli w obu kierunkach). Ale potem podaję ujemne marginesy RelativeLayout, aby upewnić się, że jest rysowany jako wąska kolumna. Oto mój pełny kod tego zrzutu ekranu:
Ogólnie rzecz biorąc, ta strategia polegająca na utrzymywaniu widoku w innym widoku była dla mnie bardzo przydatna w pozycjonowaniu rzeczy w systemie Android! Na przykład okno informacyjne poniżej paska akcji używa tej samej taktyki!
W przypadku tekstu wyglądającego jak znak sklepu wystarczy wstawić nowe linie po każdym znaku, np.
"N\nu\nt\ns"
Będzie:źródło
Podobało mi się podejście @ kostmo. Zmodyfikowałem to trochę, bo miałem problem - odcinanie obróconej w pionie etykiety, gdy ustawiłem jej parametry na
WRAP_CONTENT
. W związku z tym tekst nie był w pełni widoczny.Oto jak to rozwiązałem:
Jeśli chcesz mieć tekst od góry do dołu, użyj
topToDown(true)
metody.źródło