here is a very simple app.
I would like te to scroll the view automatically while it's being spoken. As of right now, I am highlighting the text while it's spoken. However, when the text is long, I would like the text container to scroll down the text automatically while it's been spoken.
Imagine like subtitles showing in a movie. However, instead of subtitles, I have text. And instead of an actor speaking something, I have TTS. Any help is appreciated.
Here is my code:
The XML design:
<TextView
android:id="@+id/text_view_id"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:gravity="top"
android:textSize="60dp"
android:textStyle="bold"
android:text="It's possible to perform frequency separation just like in Photoshop, and there are three types of healing tools. Photopea supports actions as well, so it's possible to create frequency separation layers with a single click."
android:hint=""
/>
<Button
android:id="@+id/botao"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:layout_gravity="right"
android:text="Rodar" />
And here is my java code: package com.example.myapplication;
import android.graphics.Color; import android.os.Bundle; import android.speech.tts.TextToSpeech; import android.speech.tts.UtteranceProgressListener; import android.text.Spannable; import android.text.SpannableString; import android.text.Spanned; import android.text.method.ScrollingMovementMethod; import android.text.style.BackgroundColorSpan; import android.text.style.ForegroundColorSpan; import android.util.Log; import android.view.View; import android.widget.Button; import android.widget.EditText; import android.widget.TextView;
import androidx.appcompat.app.AppCompatActivity;
import com.example.myapplication.R;
public class MainActivity extends AppCompatActivity implements TextToSpeech.OnInitListener, View.OnClickListener {
TextToSpeech tts;
String sentence = "It's possible to perform frequency separation just like in Photoshop, and there are three types of healing tools. Photopea supports actions as well, so it's possible to create frequency separation layers with a single click.";
TextView textView;
Button botao;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
textView = findViewById(R.id.text_view_id);
textView.setText(sentence);
tts = new TextToSpeech(this, this);
botao = (Button) findViewById(R.id.botao) ;
botao.setOnClickListener(MainActivity.this);
}
// TextToSpeech.OnInitListener (for our purposes, the "main method" of this activity)
public void onInit(int status) {
tts.setOnUtteranceProgressListener(new UtteranceProgressListener() {
@Override
public void onStart(String utteranceId) {
Log.i("XXX", "utterance started");
}
@Override
public void onDone(String utteranceId) {
Log.i("XXX", "utterance done");
}
@Override
public void onError(String utteranceId) {
Log.i("XXX", "utterance error");
}
@Override
public void onRangeStart(String utteranceId,
final int start,
final int end,
int frame) {
Log.i("XXX", "onRangeStart() ... utteranceId: " + utteranceId + ", start: " + start
+ ", end: " + end + ", frame: " + frame);
// onRangeStart (and all UtteranceProgressListener callbacks) do not run on main thread
// ... so we explicitly manipulate views on the main thread:
runOnUiThread(new Runnable() {
@Override
public void run() {
Spannable textWithHighlights = new SpannableString(sentence);
textWithHighlights.setSpan(new BackgroundColorSpan(Color.YELLOW), start, end, Spanned.SPAN_INCLUSIVE_INCLUSIVE);
textView.setText(textWithHighlights);
textView.setMovementMethod(new ScrollingMovementMethod());
}
});
}
});
}
public void startClicked(View ignored) {
tts.speak(sentence, TextToSpeech.QUEUE_FLUSH, null, "doesn't matter yet");
}
@Override
public void onClick(View view) {
tts.speak(sentence, TextToSpeech.QUEUE_FLUSH, null, "doesn't matter yet");
}
}
Any advice?