瀏覽代碼

[3.x] Backport VideoLooping and fix for initial black frame

Patrick 2 年之前
父節點
當前提交
58d76c117e
共有 3 個文件被更改,包括 27 次插入0 次删除
  1. 3 0
      doc/classes/VideoPlayer.xml
  2. 20 0
      scene/gui/video_player.cpp
  3. 4 0
      scene/gui/video_player.h

+ 3 - 0
doc/classes/VideoPlayer.xml

@@ -61,6 +61,9 @@
 		<member name="expand" type="bool" setter="set_expand" getter="has_expand" default="true">
 			If [code]true[/code], the video scales to the control size. Otherwise, the control minimum size will be automatically adjusted to match the video stream's dimensions.
 		</member>
+		<member name="loop" type="bool" setter="set_loop" getter="has_loop" default="false">
+			If [code]true[/code], the video restarts when it reaches its end.
+		</member>
 		<member name="paused" type="bool" setter="set_paused" getter="is_paused" default="false">
 			If [code]true[/code], the video is paused.
 		</member>

+ 20 - 0
scene/gui/video_player.cpp

@@ -161,6 +161,10 @@ void VideoPlayer::_notification(int p_notification) {
 			playback->update(delta); // playback->is_playing() returns false in the last video frame
 
 			if (!playback->is_playing()) {
+				if (loop) {
+					play();
+					return;
+				}
 				emit_signal(SceneStringNames::get_singleton()->finished);
 			}
 
@@ -199,6 +203,14 @@ bool VideoPlayer::has_expand() const {
 	return expand;
 }
 
+void VideoPlayer::set_loop(bool p_loop) {
+	loop = p_loop;
+}
+
+bool VideoPlayer::has_loop() const {
+	return loop;
+}
+
 void VideoPlayer::set_stream(const Ref<VideoStream> &p_stream) {
 	stop();
 
@@ -261,6 +273,9 @@ void VideoPlayer::play() {
 	//	AudioServer::get_singleton()->stream_set_active(stream_rid,true);
 	//	AudioServer::get_singleton()->stream_set_volume_scale(stream_rid,volume);
 	last_audio_time = 0;
+
+	// We update the playback to render the first frame immediately.
+	playback->update(0);
 };
 
 void VideoPlayer::stop() {
@@ -418,6 +433,9 @@ void VideoPlayer::_bind_methods() {
 	ClassDB::bind_method(D_METHOD("set_paused", "paused"), &VideoPlayer::set_paused);
 	ClassDB::bind_method(D_METHOD("is_paused"), &VideoPlayer::is_paused);
 
+	ClassDB::bind_method(D_METHOD("set_loop", "loop"), &VideoPlayer::set_loop);
+	ClassDB::bind_method(D_METHOD("has_loop"), &VideoPlayer::has_loop);
+
 	ClassDB::bind_method(D_METHOD("set_volume", "volume"), &VideoPlayer::set_volume);
 	ClassDB::bind_method(D_METHOD("get_volume"), &VideoPlayer::get_volume);
 
@@ -456,6 +474,7 @@ void VideoPlayer::_bind_methods() {
 	ADD_PROPERTY(PropertyInfo(Variant::BOOL, "autoplay"), "set_autoplay", "has_autoplay");
 	ADD_PROPERTY(PropertyInfo(Variant::BOOL, "paused"), "set_paused", "is_paused");
 	ADD_PROPERTY(PropertyInfo(Variant::BOOL, "expand"), "set_expand", "has_expand");
+	ADD_PROPERTY(PropertyInfo(Variant::BOOL, "loop"), "set_loop", "has_loop");
 	ADD_PROPERTY(PropertyInfo(Variant::INT, "buffering_msec", PROPERTY_HINT_RANGE, "10,1000"), "set_buffering_msec", "get_buffering_msec");
 	ADD_PROPERTY(PropertyInfo(Variant::REAL, "stream_position", PROPERTY_HINT_RANGE, "0,1280000,0.1", 0), "set_stream_position", "get_stream_position");
 
@@ -468,6 +487,7 @@ VideoPlayer::VideoPlayer() {
 	paused = false;
 	autoplay = false;
 	expand = true;
+	loop = false;
 
 	audio_track = 0;
 	bus_index = 0;

+ 4 - 0
scene/gui/video_player.h

@@ -63,6 +63,7 @@ class VideoPlayer : public Control {
 	float volume;
 	double last_audio_time;
 	bool expand;
+	bool loop;
 	bool loops;
 	int buffering_ms;
 	int audio_track;
@@ -93,6 +94,9 @@ public:
 	void stop();
 	bool is_playing() const;
 
+	void set_loop(bool p_loop);
+	bool has_loop() const;
+
 	void set_paused(bool p_paused);
 	bool is_paused() const;