mirror of
https://github.com/xlmnxp/blue-recorder.git
synced 2024-11-23 17:13:11 +03:00
add delay timer
This commit is contained in:
parent
ad01c74bc6
commit
a3dbd2989b
43
Cargo.lock
generated
43
Cargo.lock
generated
@ -77,6 +77,7 @@ dependencies = [
|
||||
"gtk4",
|
||||
"regex",
|
||||
"rust-ini",
|
||||
"secfmt",
|
||||
"subprocess",
|
||||
]
|
||||
|
||||
@ -102,7 +103,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "cairo-rs"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"cairo-sys-rs 0.17.0",
|
||||
@ -126,7 +127,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "cairo-sys-rs"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"glib-sys 0.17.0",
|
||||
"libc",
|
||||
@ -400,7 +401,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "gdk-pixbuf"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"gdk-pixbuf-sys 0.17.0",
|
||||
@ -438,7 +439,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "gdk-pixbuf-sys"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"gio-sys 0.17.0",
|
||||
"glib-sys 0.17.0",
|
||||
@ -483,7 +484,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "gdk4"
|
||||
version = "0.6.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk4-rs.git#dd4d418dfe8872bacfe210b34b683530548b5d63"
|
||||
source = "git+https://github.com/gtk-rs/gtk4-rs.git#e47eca402b90322ec9e8c2fcc0f93d6a3a8b037e"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"cairo-rs 0.17.0",
|
||||
@ -515,7 +516,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "gdk4-sys"
|
||||
version = "0.6.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk4-rs.git#dd4d418dfe8872bacfe210b34b683530548b5d63"
|
||||
source = "git+https://github.com/gtk-rs/gtk4-rs.git#e47eca402b90322ec9e8c2fcc0f93d6a3a8b037e"
|
||||
dependencies = [
|
||||
"cairo-sys-rs 0.17.0",
|
||||
"gdk-pixbuf-sys 0.17.0",
|
||||
@ -600,7 +601,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "gio"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"futures-channel",
|
||||
@ -645,7 +646,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "gio-sys"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"glib-sys 0.17.0",
|
||||
"gobject-sys 0.17.0",
|
||||
@ -696,7 +697,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "glib"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"futures-channel",
|
||||
@ -748,7 +749,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "glib-macros"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"heck 0.4.0",
|
||||
@ -782,7 +783,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "glib-sys"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"system-deps 6.0.3",
|
||||
@ -813,7 +814,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "gobject-sys"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"glib-sys 0.17.0",
|
||||
"libc",
|
||||
@ -1024,9 +1025,9 @@ checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.135"
|
||||
version = "0.2.137"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "68783febc7782c6c5cb401fbda4de5a9898be1762314da0bb2c10ced61f18b0c"
|
||||
checksum = "fc7fcc620a3bff7cdd7a365be3376c97191aeaccc2a603e600951e452615bf89"
|
||||
|
||||
[[package]]
|
||||
name = "link-cplusplus"
|
||||
@ -1163,7 +1164,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "pango"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"gio 0.17.0",
|
||||
@ -1188,7 +1189,7 @@ dependencies = [
|
||||
[[package]]
|
||||
name = "pango-sys"
|
||||
version = "0.17.0"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#4f5e597590e30183c819c9cf15f74bd87e9ac687"
|
||||
source = "git+https://github.com/gtk-rs/gtk-rs-core#cc7a2b1de10b1bc65f1841f259b8c118fec4221c"
|
||||
dependencies = [
|
||||
"glib-sys 0.17.0",
|
||||
"gobject-sys 0.17.0",
|
||||
@ -1220,9 +1221,9 @@ checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
|
||||
|
||||
[[package]]
|
||||
name = "pkg-config"
|
||||
version = "0.3.25"
|
||||
version = "0.3.26"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1df8c4ec4b0627e53bdf214615ad287367e482558cf84b109250b37464dc03ae"
|
||||
checksum = "6ac9a59f73473f1b8d852421e59e64809f025994837ef743615c6d0c5b305160"
|
||||
|
||||
[[package]]
|
||||
name = "ppv-lite86"
|
||||
@ -1393,6 +1394,12 @@ version = "1.0.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9c8132065adcfd6e02db789d9285a0deb2f3fcb04002865ab67d5fb103533898"
|
||||
|
||||
[[package]]
|
||||
name = "secfmt"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c8c73432861711997c5d0a1f61275cb4e875884c820da5ff2cffad3d3577201c"
|
||||
|
||||
[[package]]
|
||||
name = "semver"
|
||||
version = "0.11.0"
|
||||
|
@ -16,6 +16,7 @@ gtk-sys = "0.15"
|
||||
glib = "0.10.3"
|
||||
rust-ini = "0.16"
|
||||
regex = "1.4.3"
|
||||
secfmt = "0.1.1"
|
||||
subprocess = "0.2.6"
|
||||
|
||||
[dependencies.gio]
|
||||
|
@ -103,6 +103,48 @@
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<object class="GtkWindow" id="delay_window">
|
||||
<property name="can-focus">True</property>
|
||||
<property name="transient-for">main_window</property>
|
||||
<property name="resizable">False</property>
|
||||
<property name="modal">True</property>
|
||||
<property name="default-height">200</property>
|
||||
<property name="default-width">200</property>
|
||||
<property name="decorated">False</property>
|
||||
<property name="deletable">False</property>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="orientation">vertical</property>
|
||||
<child type="top">
|
||||
<object class="GtkLabel" id="delay_window_title">
|
||||
<property name="name">delay_window_title</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="label" translatable="yes">Start Recording in…</property>
|
||||
<property name="margin-top">10</property>
|
||||
</object>
|
||||
</child>
|
||||
<child type="center">
|
||||
<object class="GtkLabel" id="delay_window_label">
|
||||
<property name="name">delay_window_label</property>
|
||||
<property name="vexpand">True</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="visible">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child type="bottom">
|
||||
<object class="GtkButton" id="delay_window_stopbutton">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
<property name="receives-default">True</property>
|
||||
<property name="margin-start">10</property>
|
||||
<property name="margin-end">10</property>
|
||||
<property name="margin-bottom">10</property>
|
||||
<property name="label" translatable="yes">Stop</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<object class="GtkImage" id="image3">
|
||||
<property name="visible">True</property>
|
||||
<property name="can-focus">True</property>
|
||||
|
@ -1,4 +1,5 @@
|
||||
extern crate subprocess;
|
||||
|
||||
use chrono::prelude::*;
|
||||
use gettextrs::gettext;
|
||||
use gtk::prelude::*;
|
||||
@ -53,7 +54,6 @@ pub struct Ffmpeg {
|
||||
pub record_mouse: CheckButton,
|
||||
pub follow_mouse: CheckButton,
|
||||
pub record_frames: SpinButton,
|
||||
pub record_delay: SpinButton,
|
||||
pub command: Entry,
|
||||
pub video_process_id: Option<u32>,
|
||||
pub audio_process_id: Option<u32>,
|
||||
@ -169,8 +169,6 @@ impl Ffmpeg {
|
||||
ffmpeg_command.arg("1");
|
||||
ffmpeg_command.arg(self.saved_filename.as_ref().unwrap());
|
||||
ffmpeg_command.arg("-y");
|
||||
// Sleep for delay
|
||||
sleep(Duration::from_secs(self.record_delay.value() as u64));
|
||||
// Start recording and return the process id
|
||||
self.video_process_id = Some(ffmpeg_command.spawn().unwrap().id());
|
||||
return (self.video_process_id, self.audio_process_id);
|
||||
|
66
src/main.rs
66
src/main.rs
@ -5,19 +5,22 @@ extern crate gtk;
|
||||
mod area_capture;
|
||||
mod config_management;
|
||||
mod ffmpeg_interface;
|
||||
mod timer;
|
||||
|
||||
use ffmpeg_interface::{Ffmpeg, ProgressWidget};
|
||||
use gettextrs::{bindtextdomain, gettext, LocaleCategory, setlocale, textdomain};
|
||||
use gtk::{prelude::*, Application};
|
||||
use gtk::{AboutDialog, Builder, Button, CheckButton, ComboBoxText, CssProvider, Entry, FileChooserNative, FileChooserAction, Image, Label, MessageDialog, ProgressBar, SpinButton, ToggleButton, Window};
|
||||
use gtk::{AboutDialog, Application, Builder, Button, CheckButton, ComboBoxText, CssProvider, Entry, FileChooserNative, FileChooserAction, Image, Label, MessageDialog, ProgressBar, SpinButton, ToggleButton, Window};
|
||||
use gtk::prelude::*;
|
||||
use gtk::glib;
|
||||
use std::cell::RefCell;
|
||||
use std::ops::Add;
|
||||
use std::path::Path;
|
||||
use std::process::{Command, Stdio};
|
||||
use std::rc::Rc;
|
||||
use timer::{recording_delay};
|
||||
|
||||
fn main() {
|
||||
//Create new application
|
||||
// Create new application
|
||||
let application = Application::new(Some("sa.sy.blue-recorder"), Default::default(),);
|
||||
application.connect_activate(build_ui);
|
||||
application.run();
|
||||
@ -70,6 +73,9 @@ pub fn build_ui(application: &Application) {
|
||||
let command_label: Label = builder.object("command_label").unwrap();
|
||||
let delay_label: Label = builder.object("delay_label").unwrap();
|
||||
let delay_spin: SpinButton = builder.object("delay").unwrap();
|
||||
let delay_window: Window = builder.object("delay_window").unwrap();
|
||||
let delay_window_label: Label = builder.object("delay_window_label").unwrap();
|
||||
let delay_window_button: Button = builder.object("delay_window_stopbutton").unwrap();
|
||||
let filename_entry: Entry = builder.object("filename").unwrap();
|
||||
let folder_chooser_button: Button = builder.object("folder_chooser").unwrap();
|
||||
let folder_chooser_image: Image = builder.object("folder_chooser_image").unwrap();
|
||||
@ -96,13 +102,13 @@ pub fn build_ui(application: &Application) {
|
||||
// Windows
|
||||
main_window.set_title(Some(&gettext("Blue Recorder")));
|
||||
main_window.set_application(Some(application));
|
||||
area_chooser_window.set_title(Some(&gettext("Area Chooser"))); //title is hidden
|
||||
area_chooser_window.set_title(Some(&gettext("Area Chooser"))); // Title is hidden
|
||||
|
||||
//Hide stop & play buttons
|
||||
// Hide stop & play buttons
|
||||
stop_button.hide();
|
||||
play_button.hide();
|
||||
|
||||
//Hide window grab button in Wayland
|
||||
// Hide window grab button in Wayland
|
||||
if is_wayland() {
|
||||
window_grab_button.hide();
|
||||
}
|
||||
@ -276,6 +282,18 @@ pub fn build_ui(application: &Application) {
|
||||
audio_source_label.set_label(&gettext("Audio Input Source:"));
|
||||
|
||||
// Spin
|
||||
frames_spin.set_value(
|
||||
config_management::get("default", "frame")
|
||||
.parse::<f64>()
|
||||
.unwrap(),
|
||||
);
|
||||
|
||||
delay_spin.set_value(
|
||||
config_management::get("default", "delay")
|
||||
.parse::<f64>()
|
||||
.unwrap(),
|
||||
);
|
||||
|
||||
let _frames_spin = frames_spin.to_owned();
|
||||
frames_spin.connect_value_changed(move |_| {
|
||||
config_management::set(
|
||||
@ -375,7 +393,6 @@ pub fn build_ui(application: &Application) {
|
||||
record_mouse: mouse_switch,
|
||||
follow_mouse: follow_mouse_switch,
|
||||
record_frames: frames_spin,
|
||||
record_delay: delay_spin,
|
||||
command: command_entry,
|
||||
video_process_id: None,
|
||||
audio_process_id: None,
|
||||
@ -386,30 +403,39 @@ pub fn build_ui(application: &Application) {
|
||||
overwrite: overwrite_switch,
|
||||
}));
|
||||
|
||||
let _delay_window = delay_window.clone();
|
||||
let mut _ffmpeg_record_interface = ffmpeg_record_interface.clone();
|
||||
let _stop_button = stop_button.clone();
|
||||
let _record_button = record_button.clone();
|
||||
let _stop_button = stop_button.clone();
|
||||
record_button.connect_clicked(move |_| {
|
||||
let _area_capture = area_capture.borrow_mut();
|
||||
match _ffmpeg_record_interface.borrow_mut().start_record(
|
||||
_area_capture.x,
|
||||
_area_capture.y,
|
||||
_area_capture.width,
|
||||
_area_capture.height,
|
||||
) {
|
||||
(None, None) => {
|
||||
if delay_spin.value()as u64 > 0 {
|
||||
recording_delay(delay_spin.clone(), delay_spin.value()as u64, delay_window.clone(), delay_window_label.clone(), _record_button.clone());
|
||||
}
|
||||
if delay_spin.value()as u64 == 0 {
|
||||
let _area_capture = area_capture.borrow_mut();
|
||||
match _ffmpeg_record_interface.borrow_mut().start_record(
|
||||
_area_capture.x,
|
||||
_area_capture.y,
|
||||
_area_capture.width,
|
||||
_area_capture.height,
|
||||
) {
|
||||
(None, None) => {
|
||||
// Do nothing if the start_record function return nothing
|
||||
}
|
||||
_ => {
|
||||
_record_button.hide();
|
||||
_stop_button.show();
|
||||
_ => {
|
||||
_record_button.hide();
|
||||
_stop_button.show();
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
delay_window_button.connect_clicked(move |_| {
|
||||
});
|
||||
|
||||
let mut _ffmpeg_record_interface = ffmpeg_record_interface.clone();
|
||||
let _stop_button = stop_button.clone();
|
||||
let _play_button = play_button.clone();
|
||||
let _stop_button = stop_button.clone();
|
||||
stop_button.connect_clicked(move |_| {
|
||||
_ffmpeg_record_interface.borrow_mut().clone().stop_record();
|
||||
record_button.show();
|
||||
|
@ -22,3 +22,13 @@
|
||||
color: @theme_selected_fg_color;
|
||||
background: @theme_selected_bg_color;
|
||||
}
|
||||
|
||||
#delay_window_label{
|
||||
font-size: 350%;
|
||||
font-weight: 250;
|
||||
}
|
||||
|
||||
#delay_window_title{
|
||||
font-size: 120%;
|
||||
font-weight: 50;
|
||||
}
|
||||
|
35
src/timer.rs
35
src/timer.rs
@ -1 +1,34 @@
|
||||
// TODO: add timer
|
||||
extern crate secfmt;
|
||||
|
||||
use gtk::glib;
|
||||
use gtk::{Button, Label, SpinButton, Window};
|
||||
use gtk::prelude::*;
|
||||
|
||||
pub fn recording_delay(delay_spin: SpinButton, mut delay_time: u64, delay_window: Window, delay_window_label: Label, record_button: Button) {
|
||||
// Keep time label alive and update every 1sec
|
||||
let default_value = delay_time;
|
||||
let capture_label = move || {
|
||||
// Show delay window if delay time is not zero
|
||||
delay_window.show();
|
||||
if delay_time > 0 {
|
||||
delay_window_label.set_text(¤t_time(delay_time));
|
||||
delay_time -= 1;
|
||||
glib::source::Continue(true)
|
||||
} else {
|
||||
// Hide delay window and start recording
|
||||
delay_window.hide();
|
||||
delay_spin.set_value(0.0);
|
||||
record_button.emit_clicked();
|
||||
// Keep the input value
|
||||
delay_spin.set_value(default_value as f64);
|
||||
glib::source::Continue(false)
|
||||
}
|
||||
};
|
||||
// Execute capture_label every 1sec
|
||||
glib::source::timeout_add_seconds_local(1, capture_label);
|
||||
}
|
||||
|
||||
fn current_time(delay_time: u64) -> String {
|
||||
let delay = secfmt::from(delay_time);
|
||||
format!("{}:{}", delay.minutes, delay.seconds)
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user