2012-07-14 11 views
5

Sono alle prese con setNeedsDisplay. Ho pensato che avrebbe dovuto attivare chiamate di drawRect: per la vista per la quale è stato chiamato e la gerarchia sotto quella se è all'interno dei limiti della vista, ma non lo trovo. Ecco il mio setup:setNeedsDisplay non attiva drawRect nelle sottoview come previsto

Dal delegato dell'applicazione, creo una vista la cui dimensione è un quadrato che copre essenzialmente l'intero spazio dello schermo. Questa vista è denominata TrollCalendarView. Non succede molto a TrollCalendarView tranne per una rotazione innescata dalla bussola.

Ci sono 7 sottoview di TrollCalendarView chiamati PlatformView destinati a contenere oggetti di disegno 2D disposti attorno al centro di TrollCalendarView in una disposizione a 7 lati. Quindi, quando l'iPad viene ruotato, queste 7 viste ruotano in modo tale da essere sempre orientate con le direzioni cardinali.

Ciascuna sottoview di PlatformView contiene 3 sottopagine chiamate Tower. Ogni torre contiene oggetti di disegno 2D implementati in drawRect:.

Così, in sintesi, ho TrollCalendarView con vuoto drawRect: e subviews PlatformView e Platformview -> Torre che ogni hanno implementazioni drawRect. Inoltre, Tower si trova all'interno dei limiti della piattaforma e Platform si trova all'interno dei limiti di TrollCalendarView.

In TrollCalendarView Ho aggiunto un indicatore di scorrimento. Quando si esegue lo scorrimento, una proprietà viene aggiornata e io chiamo [self setNeedsDisplay] ma non sembra che accada nulla. Ho aggiunto voci NSLog al metodo drawRect: in ciascuna di queste visualizzazioni e viene chiamato solo il metodo . Ironicamente, questa è l'unica vista il cui metodo drawRect sarà vuoto.

Non esiste un file xib.

Cosa devo fare per garantire che venga chiamato il metodo drawRect nelle altre visualizzazioni secondarie? C'è documentazione da qualche parte che descrive tutte le sfumature che potrebbero influenzare questo?

risposta

7

Sono in difficoltà con setNeedsDisplay. Ho pensato che avrebbe dovuto attivare chiamate di drawRect per la vista per cui è chiamato e la seguente gerarchia se è entro i limiti della vista

No, non è questo il caso. Dove hai preso quell'idea?

-setNeedsDisplay: si applica solo alla vista a cui è stato inviato. Se è necessario invalidare altre visualizzazioni, è necessario aggiungere del codice per inviare anche -setNeedsDisplay:. Questo è tutto ciò che c'è da fare.

+0

Ho avuto questa idea dalle risposte a domande simili proprio qui su StackOverflow. Basta cercare sottoview setNeedsDisplay per i campioni. Ce ne sono diversi. –

+0

Seguirò questo suggerimento a meno che non impari in un altro modo. Almeno corrisponde alle mie conclusioni nei test. –

+1

Sfortunatamente c'è un sacco di rumore in SO e in molti ciechi. Le domande che stai guardando hanno pochissimi voti, quindi probabilmente non molte persone li hanno visti o hanno avuto la possibilità di correggerli. Se hai appena iniziato, i documenti Apple sono molto più affidabili. –

5

Penso che questa sia un'ottimizzazione nel framework; se la tua sottoview non ha il bisogno di per disegnare di nuovo, allora questo è un importante miglioramento delle prestazioni. Renditi conto che quasi tutto ciò che è animabile non richiede drawrect (spostamento, ridimensionamento, ecc.).

Se sa che tutti i vostri subviews deve essere ridisegnato (e non semplicemente spostato), poi ignorare setNeedsDisplay nella visualizzazione principale e fare così:

-(void) setNeedsDisplay { 
    [self.subviews makeObjectsPerformSelector:@selector(setNeedsDisplay)]; 
    [super setNeedsDisplay]; 
} 

Ho testato questo, ed è fa sì che anche tutte le sottoview vengano ridisegnate. Ti preghiamo di notare che guadagnerai punti karma di efficienza se in qualche modo filtri le tue sottoview e assicurati di inviarlo solo a subviews che hanno effettivamente bisogno di ridisegnare ... e ancora di più se riesci a capire come non è necessario aggiornarlo di nuovo a . :-)

+0

Grazie. Ci proverò. Nel mio scenario, non è necessario ridisegnare le 7 sottoview della piattaforma. Saranno rideterminati esattamente i due terzi dei restanti 21 sottopiani. Sapere quale dei 21 deve essere ridisegnato viene calcolato in modo efficiente in drawRect e non può essere eseguito in modo più efficiente altrove. Solo curioso - come fa il quadro a porre il veto sulla mia decisione (il tuo commento sull'ottimizzazione)? Sembra che sconfigge lo scopo di avere setNeedsDisplay in primo luogo. –

+0

No. Non funziona Questo ottiene solo le sottoview. Ho bisogno che le sottoview di quelle sottoview vengano ridisegnate. Ho deciso di fare il lavoro di camminare l'albero nel punto in cui ho bisogno di impostare setNeedsDisplay. Grazie per il suggerimento, però. –