2015-07-14 13 views
5

Próbowałem zaimplementować komponent RadialProgress (https://components.xamarin.com/view/radialprogress) w mojej aplikacji. Udało mi się uzyskać to na ekranie i zmienić kolor postępu, ale nie mogę znaleźć sposobu na zmianę wewnętrznego koloru koła.Xamarin - Radial Progress Component Issue

Sam obiekt RadialProgressView ma pole BackgroundTintMode, które pobiera tryb DuffPorter.Mode, ale za każdym razem, gdy próbuję ustawić tryb odcienia tła, aplikacja zrywa z tym komunikatem (Message = "brak metody o nazwie =" setBackgroundTintMode "signature = '(Landroid/grafika/PorterDuff $ Tryb;?!))

Czy istnieje jeszcze sposób, aby robić to, co chcę

Dzięki

+0

masz jakieś rozwiązanie? – SARATH

+0

Niestety, nie zrobiłem Saratha. Jeszcze nie próbowałem sugestii Miny, więc kiedy to zrobię, dam ci znać. – Zez3

Odpowiedz

8

Tak, można to zrobić. Chociaż nie w bardzo prosty sposób, a nawet możliwy do utrzymania.

Po pierwsze, niech kopać trochę w kodzie rysunku RadialProgressView „s (jak wystawiony przez Xamarin Studio Assembly Browser):

protected override void OnDraw(Canvas canvas) 
    { 
     // ... there's more stuff here, but you get the idea 
     canvas.DrawCircle(this.bgCx, this.bgCy, this.radius, this.bgCirclePaint); 
     canvas.DrawCircle(this.bgCx, this.bgCy, this.innerLineRadius, this.bgBorderPaint); 
     canvas.DrawText(this.valueText, this.textX, this.textY, this.textPaint); 
    } 

Widzimy tu pewne kolory, jak bgCirclePaint i bgBorderPaint. Jeśli będziemy w stanie zmienić wartość tych zmiennych, będziemy mogli zmienić kolor, z którym malowany jest ProgressView.

Problem polega na tym, że RadialProgressView nie eksponuje pól - wszystkie są prywatne, więc zwyczajne dziedziczenie po RadialProgressView nie pozwoli nam ustawić ich na nową wartość.

Możemy jednak skorzystać z reflection zmienić te prywatne pola, tak jak poniżej:

 var textPaintMember = typeof(RadialProgressView).GetField("textPaint", BindingFlags.Instance | BindingFlags.NonPublic); 
     textPaintMember.SetValue(Instance, MyNewSuperCoolColorPaint); 

Łącząc dwa, możemy wymyślić nowe, niestandardowe klasy jak ten:

public class CustomizableRadialProgressView : RadialProgressView 
{ 
    public CustomizableRadialProgressView(Context context) : base(context) 
    { 
    } 

    public void SetTextColor(Color color) 
    { 
     var paint = new Paint(); 
     paint.SetTypeface(Typeface.DefaultBold); 
     paint.Color = color; 
     paint.AntiAlias = true; 

     var textPaintMember = typeof(RadialProgressView).GetField("textPaint", BindingFlags.Instance | BindingFlags.NonPublic); 

     textPaintMember.SetValue(this, paint); 
    } 

    public void SetCircleColor(Color color) 
    { 
     var paint = new Paint(); 
     paint.SetStyle(Paint.Style.Fill); 
     paint.Color = color; 
     paint.AntiAlias = true; 

     var circlePaintMember = typeof(RadialProgressView).GetField("bgCirclePaint", BindingFlags.Instance | BindingFlags.NonPublic); 

     circlePaintMember.SetValue(this, paint); 
    } 

    public void SetBorderColor(Color color) 
    { 
     var paint = new Paint(); 
     paint.SetStyle(Paint.Style.Stroke); 
     paint.Color = color; 
     paint.AntiAlias = true; 

     var circlePaintMember = typeof(RadialProgressView).GetField("bgBorderPaint", BindingFlags.Instance | BindingFlags.NonPublic); 

     circlePaintMember.SetValue(this, paint); 
    } 


    public void SetProgressPackgroundColor(Color color) 
    { 
     var paint = new Paint(); 
     paint.SetStyle(Paint.Style.Stroke); 
     paint.Color = color; 
     paint.AntiAlias = true; 

     var circlePaintMember = typeof(RadialProgressView).GetField("bgProgressPaint", BindingFlags.Instance | BindingFlags.NonPublic); 

     circlePaintMember.SetValue(this, paint); 
    } 
} 

to dostanie nam wynik jesteśmy po:

2

Uwaga: Prawdopodobnie mądrze jest zauważyć, że niewłaściwie używamy prywatnych pól: manipulujemy nimi spoza klasy, w której żyją. Jeśli Xamarin kiedykolwiek zdecyduje się zmienić sposób, w jaki zaimplementowano RadialProgressView, lub nawet zmienia nazwy jedną ze zmiennych prywatnych, nasz kod nie powiedzie się w czasie wykonywania. Lepszym sposobem podejścia do tego problemu byłoby prawdopodobnie poproszenie Xamarina o dostarczenie potrzebnych programów pobierających/ustawiających. Ale, hej, jest o wiele chłodniej w ten sposób;)

+0

czy możemy zmienić tylko środkową część pierścień ? – SARATH

+0

@SarathiOS: Nie jestem pewien, czy rozumiem twoje pytanie. Którą część chciałbyś zmienić? –

+0

widok wokół tej etykiety (40), którą widok muszę zmienić. Czy to możliwe ? – SARATH

1

można spróbować realizacji niestandardowych klasy ViewRenderer i dostęp do podstawowych rodzimych Android poglądy zmodyfikuj je tak, jak chcesz. https://blog.xamarin.com/using-custom-controls-in-xamarin.forms-on-android/

błąd co do „metody” setBackgroundTintMode wskazuje, że być może trzeba zaktualizować platformę Xamarin, aby upewnić się, że najnowsze API są dostępne

+0

Zaimplementowałem ten radialny widok postępu w mojej aplikacji ios. Ale niestety nie znalazłem żadnej możliwości zmiany jego tła. Obszar wewnętrzny.Muszę zmienić jego tło na biały – SARATH

+0

Masz pomysł, aby zmienić tło z widoku promieniowy postęp. Z góry dziękuję – SARATH

+0

Wierzę, że musisz uzyskać dostęp do podstawowych komponentów i zmienić ich właściwości, w Androidzie, jeśli możesz rzucić RadialProgressView do ViewGroup, możesz uzyskać dostęp do dzieci za pomocą metody getChildAt (int index). –