Мой UIWebView перезагружается лениво.Как я могу заставить его перезагрузить / обновить, когда я хочу, чтобы данные отображались? - PullRequest
2 голосов
/ 10 ноября 2010

Я пытаюсь заставить UIWebView динамически обновляться, что-то вроде караоке-бокса, поскольку он повторяет цикл while.Слово, которое говорит движок tts, должно быть оранжевым (или html, .style2).

Однако происходит то, что UIWebView не обновляет свой дисплей при каждой итерации строки htmlKaraoke, а только последнюю в цикле while.UIWebView, кажется, перезагружается ленивым образом и ждет завершения цикла while, прежде чем обновлять свой дисплей.Я включил в свой код все различные способы, которыми я пытался обойти это (setNeedsDisplay, setNeedsLayout, сброс строки htmlKaraoke, перезагрузка UIWebView), но я не могу заставить его делать то, что я хочу.

HTML-код обновляется, как и должно (с произносимым словом оранжевым цветом), но веб-просмотр этого не отражает.

Как получить обновление веб-вида после каждого обновления строки htmlKaraoke?

i = 0;
NSString *htmlHead              = @"<html><head><style type='text/css'><!-- .style1 { font-size: 24px; font-weight: bold; font-family: Helvetica; } .style2 {color: #FF9900} --> </style></head><body><span class='style1'>";
NSString *htmlFoot              = @"</span></body></html>";
NSString *htmlEmpHead           = @"<span class='style2'>";
NSString *htmlEmpFoot           = @"</span>";
NSMutableString *htmlKaraoke = [[NSMutableString alloc] init];

while(i <= wordWeAreUpToInt){
    //wait until the tts is finished talking.
    if(![[fliteEngine audioPlayer] isPlaying]){
        //NSLog(@"flite is finished!");

        //Add the word and highlight in the karaoke

            /*  Clear the html string
                Make a for loop, where n = 0, n<i, n++
                    append black word
                when for loop ends, and n == i, add an emph word (n==i when i is the currently spoken word). 
             */
        [karaokeWebView loadHTMLString:@" " baseURL:nil];
        [karaokeWebView reload]; //doesn't do anything. These two lines are a waste of breath. 

        [htmlKaraoke setString:htmlHead];
        for (int n = 0; n<i; n++) {
            [htmlKaraoke appendString:[wordsArray objectAtIndex:n]];
            [htmlKaraoke appendString:@" "];
        }
        [htmlKaraoke appendString:htmlEmpHead];
        [htmlKaraoke appendString:[wordsArray objectAtIndex:i]];
        [htmlKaraoke appendString:@" "];
        [htmlKaraoke appendString:htmlEmpFoot];
        NSLog(@"Emphasis: %@", [wordsArray objectAtIndex:i]);           
        [htmlKaraoke appendString:htmlFoot];


        NSLog(@"htmlKaraoke: %@", htmlKaraoke);

        [karaokeWebView loadHTMLString:htmlKaraoke baseURL:nil];
        [karaokeWebView setNeedsDisplay];
        [karaokeWebView setNeedsLayout]; //getting desperate....!

        //speak the word
        [self readSentence:[wordsArray objectAtIndex:i]];
        i++;
    }
}

[htmlKaraoke release];
wordWeAreUpToInt++;
}

1 Ответ

3 голосов
/ 10 ноября 2010

Я думаю, что ваша проблема в том, что UIWebView отображает представление только после того, как элемент управления возвращается обратно в основной цикл NSRunLoop / Event Loop. Итак, если вы делаете все свои обновления в цикле while, указанном выше, то загружается только последняя строка, поскольку у нее никогда не было возможности загрузить другие (и поэтому мы просто будем использовать последний запрос на загрузку).

Вам нужно будет вернуться из любого написанного вами кода (не только этого метода, но и того, что вызвало этот вызываемый и т. Д.) И вернуть управление обратно в ОС, прежде чем UIWebView обновится с вашими изменениями.

Предполагая, что какой-либо объект, в котором находится этот код, все еще присутствует после возвращения элемента управления, вы можете проверить это, добавив его в свой класс:

- (void)loadHTMLString:(NSString *)string {
    [karaokeWebView loadHTMLString:string baseURL:nil];
}

А затем измените ваши -[loadHTMLString:baseURL:] звонки на:

[self performSelector:@selector(loadHTMLString:) withObject:htmlKaraoke afterDelay:_delay_increasing_by_a_second_for_each_string];

Подробнее о главном цикле событий можно прочитать в разделе « Жизненный цикл приложения » в «Руководстве по программированию приложений iOS».

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...