Commit 060190cd authored by René Rössler's avatar René Rössler 😍
Browse files

Merge branch 'update-dependencies' into 'master'

Update dependencies

See merge request !2
parents 254c930c 55bb3162
Pipeline #165606471 passed with stage
in 6 minutes and 33 seconds
This diff is collapsed.
......@@ -2,7 +2,7 @@
name = "gled"
description = "GTK interface to controll animations with libgled to send them over Art-Net to custom made lamps/installations"
repository = "https://gitlab.com/pentagonum/gled"
version = "1.1.0"
version = "1.2.0"
authors = ["René Rössler <rene@freshx.de>"]
edition = "2018"
license = "GPL-3.0-or-later"
......@@ -11,38 +11,43 @@ license = "GPL-3.0-or-later"
log = "0.4.8"
elapsed = "0.1.2"
floating-duration = "0.1.2"
glib = "0.9.3"
chrono = "0.4.11"
glib = "0.10.1"
chrono = "0.4.13"
crossbeam-channel = "0.4.2"
structopt = "0.3.13"
dirs = "2.0.2"
structopt = "0.3.15"
dirs = "3.0.1"
resvg = "0.11.0"
usvg = "0.11.0"
lazy_static = "1.4.0"
itertools = "0.9.0"
[dependencies.cairo-rs]
version = "0.8.1"
features = ["v1_14"]
version = "0.9.1"
features = ["v1_14", "png"]
[dependencies.gio]
version = "0.8.1"
version = "0.9.0"
[dependencies.gdk]
version = "0.12.1"
version = "0.13.0"
[dependencies.gtk]
version = "0.8.1"
version = "0.9.0"
features = ["v3_18"]
[dependencies.gdk-pixbuf]
version = "0.9.0"
features = ["v2_32"]
[dependencies.fern]
version = "0.6.0"
features = ["colored"]
[dependencies.libgled]
version = "^1.1.0"
version = "^1.2.0"
path = "lib/gled"
[dependencies.resvg]
version = "0.9.0"
features = ["cairo-backend"]
[profile.release]
lto = "fat"
panic = 'abort'
......
This diff is collapsed.
......@@ -3,7 +3,7 @@ name = "libgled"
description = "Create animations for Art-Net lamps orientated on a SVG file"
repository = "https://gitlab.com/pentagonum/gled"
license = "GPL-3.0-or-later"
version = "1.1.0"
version = "1.2.0"
authors = ["René Rössler <rene@freshx.de>"]
edition = "2018"
......@@ -12,27 +12,29 @@ name = "gled"
[dependencies]
crossbeam-channel = "0.4.2"
cairo-rs = "0.8.1"
log = "0.4.8"
elapsed = "0.1.2"
svgdom = "0.18.0"
artnet_protocol = "0.2.0"
lazy_static = "1.4.0"
delta_e = "0.2.1"
serde_json = "1.0.51"
serde_derive = "1.0.106"
serde_json = "1.0.56"
serde_derive = "1.0.114"
rand = "0.7.3"
floating-duration = "0.1.2"
strum = "0.18.0"
strum_macros = "0.18.0"
kurbo = "0.5.11"
kurbo = "0.6.2"
resvg = "0.11.0"
usvg = "0.11.0"
itertools = "0.9.0"
[dependencies.resvg]
version = "0.9.0"
features = ["cairo-backend"]
[dependencies.cairo-rs]
version = "0.9.1"
features = ["png"]
[dependencies.serde]
version = "1.0.106"
version = "1.0.114"
features = ["rc"]
[profile.release]
......
......@@ -3,7 +3,7 @@
use super::types::Parameter;
use lazy_static::lazy_static;
use log::info;
use resvg::usvg::Tree;
use usvg::Tree;
use std::{
collections::{HashMap, HashSet},
fs::File,
......@@ -95,7 +95,7 @@ pub fn tree(file_path: &PathBuf) -> (HashMap<String, Parameter>, Tree) {
let mut parameters = HashMap::new();
traverse_node(&mut parameters, &doc.root(), 0, &HashSet::new());
let opt = resvg::usvg::Options {
let opt = usvg::Options {
keep_named_groups: true,
..Default::default()
};
......
......@@ -7,15 +7,13 @@ use super::{
use crate::{animation, svg, STATE};
use cairo::Context;
use elapsed::measure_time;
use iter::repeat;
use itertools::Itertools;
use log::{debug, info};
use resvg::{
prelude::NodeExt,
usvg::{self, NodeKind, PathData, PathSegment},
ScreenSize,
};
use serde_derive::{Deserialize, Serialize};
use std::{
collections::HashMap,
iter,
rc::Rc,
sync::{
atomic::{AtomicBool, Ordering},
......@@ -23,6 +21,7 @@ use std::{
},
time::Instant,
};
use usvg::{self, NodeExt, NodeKind, PathData, PathSegment};
#[derive(Deserialize, Serialize)]
#[serde(default)]
......@@ -247,7 +246,7 @@ fn leds_on_path(
.iter()
.map(|curve| {
let curves = curve.subdivide();
std::iter::once(curves.0).chain(std::iter::once(curves.1))
iter::once(curves.0).chain(iter::once(curves.1))
})
.flatten()
.collect();
......@@ -304,18 +303,73 @@ fn render_svg(
info!("Render svg");
let (elapsed, _) = measure_time(|| {
if let Some(image_svg) = image_svg.lock().unwrap().as_mut() {
image_svg.with_surface(|image_svg| {
let opt = resvg::Options::default();
let context = Context::new(&image_svg);
resvg::backend_cairo::render_to_canvas(
let screen_size = tree.svg_node().size.to_screen_size();
if let (Some(image_svg_data), Some(image)) = (
image_svg.data.as_mut(),
resvg::render(
&tree,
&opt,
ScreenSize::new(size.width as u32, size.height as u32)
.expect("Wrong screen size"),
&context,
if size.width as u32 * screen_size.height() / screen_size.width()
< size.height as u32
{
usvg::FitTo::Width(size.width as u32)
} else {
usvg::FitTo::Height(size.height as u32)
},
None,
),
) {
let height = image.height();
let (add_top_lines, add_bottom_lines) = if (height as usize) < size.height {
let top = (size.height - height as usize) / 2;
(top, size.height - height as usize - top)
} else {
(0, 0)
};
let width = image.width();
let (add_left_cols, add_right_cols) = if (width as usize) < size.width {
let left = (size.width - width as usize) / 2;
(left, size.width - width as usize - left)
} else {
(0, 0)
};
image_svg_data.copy_from_slice(
repeat(0)
.take(add_top_lines * size.width * 4)
.chain(
image
.take()
.into_iter()
.chunks(width as usize * 4)
.into_iter()
.map(|line| {
repeat(0)
.take(add_left_cols * 4)
.chain(
line.tuples()
.map(|(r, g, b, a)| {
vec![
(b as u16 * a as u16 / 255) as u8,
(g as u16 * a as u16 / 255) as u8,
(r as u16 * a as u16 / 255) as u8,
a,
]
.into_iter()
})
.flatten(),
)
.chain(repeat(0).take(add_right_cols * 4))
.collect::<Vec<u8>>()
.into_iter()
})
.flatten(),
)
.chain(repeat(0).take(add_bottom_lines * size.width * 4))
.collect::<Vec<u8>>()
.as_slice(),
);
image_svg.flush();
}
image_svg.with_surface(|image_svg| {
let context = Context::new(&image_svg);
let mut measurement_points = measurement_points.write().unwrap();
*measurement_points = {
let mut measurement_points = HashMap::new();
......
use super::opts::Opts;
use super::opts::OPTS;
use fern::colors::{Color, ColoredLevelConfig};
use std::io;
pub fn init(opts: &Opts) {
pub fn init() {
let mut base_config = fern::Dispatch::new();
base_config = match opts.verbose.max(
base_config = match OPTS.verbose.max(
match std::env::var("RUST_LOG")
.unwrap_or_else(|_| "".to_string())
.to_lowercase()
......
......@@ -5,13 +5,12 @@ mod opts;
mod ui;
use gio::prelude::*;
use opts::Opts;
use opts::OPTS;
use std::{thread, time::Duration};
use structopt::StructOpt;
#[cfg(feature = "installer")]
fn install(opts: &Opts) {
if opts.install {
fn install() {
if OPTS.install {
if let Err(err) = installer::install() {
println!("Error installing gled: {:?}", err)
} else {
......@@ -21,7 +20,7 @@ fn install(opts: &Opts) {
std::process::exit(0);
}
if opts.uninstall {
if OPTS.uninstall {
if let Err(err) = installer::uninstall() {
println!("Error uninstalling gled: {:?}", err)
} else {
......@@ -36,19 +35,15 @@ fn install(opts: &Opts) {
fn install(_opts: &Opts) {}
fn main() {
let opts = Opts::from_args();
logging::init(&opts);
logging::init();
install(&opts);
install();
gled::init();
let application = if opts.noui { None } else { Some(ui::init()) };
let application = if OPTS.noui { None } else { Some(ui::init()) };
if let Some(file) = opts.file.as_ref() {
if let Some(file) = OPTS.file.as_ref() {
gled::load_state(file.to_path_buf()).expect("Could not open project");
if !opts.noui {
ui::add_recent(file);
}
} else if opts.noui {
} else if OPTS.noui {
panic!("Can not start without ui and without project");
}
......
use std::path::PathBuf;
use structopt::StructOpt;
use lazy_static::lazy_static;
lazy_static! {
pub static ref OPTS: Opts = Opts::from_args();
}
#[derive(StructOpt)]
#[structopt(name = "gled")]
......
......@@ -26,6 +26,7 @@ use gled::{Renderer, STATE};
use gtk::{prelude::*, Application, Builder, RecentData, RecentManager, Window};
pub use icon::ICON;
use log::{debug, info};
use crate::opts::OPTS;
use rgba_conversion::RGBAConversion;
use std::{
path::Path,
......@@ -47,7 +48,7 @@ fn create_window(renderer: &Arc<RwLock<Renderer>>, application: &Application) {
presets: AtomicBool::new(true),
palettes: AtomicBool::new(true),
});
let builder = Builder::new_from_string(include_str!("ui/gled.glade"));
let builder = Builder::from_string(include_str!("ui/gled.glade"));
let update_ui = update_ui::init(&builder, renderer, &ignore_signals, &dirty);
about_dialog::init(&builder);
......@@ -91,6 +92,9 @@ pub fn init() -> Application {
.expect("Initialization failed...");
application.connect_activate(|application| {
if let Some(file) = OPTS.file.as_ref() {
add_recent(file);
}
let quit = gio::SimpleAction::new("quit", None);
quit.connect_activate(|_, _| std::process::exit(0));
application.add_action(&quit);
......
......@@ -44,7 +44,7 @@ pub fn update_ui(builder: &Builder, renderer: &Renderer, update_ui: &Sender<Upda
AnimationSetting::Range(range) => {
let label = Label::new(Some(&range.label));
animation_settings.add(&label);
let scale = Scale::new_with_range(
let scale = Scale::with_range(
Orientation::Horizontal,
range.min,
range.max,
......
......@@ -49,7 +49,7 @@ pub fn init(
let _ = update_ui.send(UpdateUiConfig::default());
}
dialog.destroy();
dialog.close();
}));
dialog.show_all();
}),
......
......@@ -39,7 +39,7 @@ pub fn init(builder: &Builder, renderer: &Arc<RwLock<Renderer>>, application: &A
super::add_recent(&path);
}
file_chooser.destroy();
file_chooser.close();
}));
save.connect_activate(clone!(window => move |_| {
......@@ -61,7 +61,7 @@ pub fn init(builder: &Builder, renderer: &Arc<RwLock<Renderer>>, application: &A
gled::set_path(path);
gled::save_state().unwrap();
}
file_chooser.destroy();
file_chooser.close();
} else {
gled::save_state().unwrap();
}
......@@ -85,7 +85,7 @@ pub fn init(builder: &Builder, renderer: &Arc<RwLock<Renderer>>, application: &A
gled::save_state_at(path).unwrap();
}
file_chooser.destroy();
file_chooser.close();
}));
open_svg.connect_activate(clone!(renderer => move |_| {
......@@ -111,6 +111,6 @@ pub fn init(builder: &Builder, renderer: &Arc<RwLock<Renderer>>, application: &A
renderer.configure();
}
file_chooser.destroy();
file_chooser.close();
}));
}
use gtk::{prelude::*, AboutDialog, Builder, Image, Window};
use cairo::{Format, ImageSurface};
use gdk_pixbuf::{Colorspace, Pixbuf};
use gtk::{prelude::*, AboutDialog, Builder, Image, ImageExt, Window};
use itertools::Itertools;
use log::info;
use resvg::usvg::{Options, Tree};
use std::ops::Deref;
use usvg::{Options, Tree};
pub static ICON: &[u8] = include_bytes!("../../book/src/logo.svg");
......@@ -9,45 +12,61 @@ pub fn init(builder: &Builder) {
info!("Rendering icons");
let tree = Tree::from_data(ICON, &Options::default()).expect("Could not parse logo.svg");
let render_icon_to_surface = |size: u32| {
resvg::backend_cairo::render_to_image(
&tree,
&resvg::Options {
background: None,
usvg: resvg::usvg::Options::default(),
fit_to: resvg::FitTo::Width(size),
},
)
.expect("Could not render icon")
let render_icon_to_vec = |width: u32| {
resvg::render(&tree, usvg::FitTo::Width(width), None)
.expect("Could not render logo")
.take()
};
let render_icon_to_image = |size: u32| {
gdk::pixbuf_get_from_surface(
render_icon_to_surface(size).deref(),
0,
0,
size as i32,
size as i32,
let render_icon_to_pixbuf = |width: u32| {
let data = glib::Bytes::from_owned(render_icon_to_vec(width));
let height = data.len() as i32 / (4 * width as i32);
Pixbuf::from_bytes(
&data,
Colorspace::Rgb,
true,
8,
width as i32,
height,
width as i32 * 4,
)
.expect("Could not convert surface to pixbuf")
};
let window = builder.get_object::<Window>("window").unwrap();
window.set_icon_list(&[
render_icon_to_image(16),
render_icon_to_image(32),
render_icon_to_image(48),
render_icon_to_image(64),
render_icon_to_image(128),
render_icon_to_pixbuf(16),
render_icon_to_pixbuf(32),
render_icon_to_pixbuf(48),
render_icon_to_pixbuf(64),
render_icon_to_pixbuf(128),
]);
let logo = builder.get_object::<Image>("logo").unwrap();
let scale_factor = window.get_scale_factor();
let surface = render_icon_to_surface(32 * scale_factor as u32);
surface.set_device_scale(f64::from(scale_factor), f64::from(scale_factor));
logo.set_from_surface(Some(surface.deref()));
let size = 32 * scale_factor as u32;
let data = render_icon_to_vec(size)
.into_iter()
.tuples()
.map(|(r, g, b, a)| {
vec![
(b as u16 * a as u16 / 255) as u8,
(g as u16 * a as u16 / 255) as u8,
(r as u16 * a as u16 / 255) as u8,
a,
]
.into_iter()
})
.flatten()
.collect::<Vec<u8>>();
let height = data.len() as i32 / (4 * size as i32);
if let Ok(surface) =
ImageSurface::create_for_data(data, Format::ARgb32, size as i32, height, size as i32 * 4)
{
surface.set_device_scale(f64::from(scale_factor), f64::from(scale_factor));
logo.set_from_surface(Some(surface.deref()));
}
let about_dialog = builder.get_object::<AboutDialog>("about_dialog").unwrap();
about_dialog.set_logo(Some(&render_icon_to_image(256)));
about_dialog.set_logo(Some(&render_icon_to_pixbuf(256)));
info!("Done rendering icons");
}
......@@ -255,7 +255,7 @@ pub fn update_ui(builder: &Builder, renderer: &Renderer, dirty: &Arc<Dirty>) {
let is_dirty = dirty.palettes.load(Relaxed)
|| palettes_model
.get_iter(&TreePath::new_from_indicesv(&[config.live_palette as i32]))
.get_iter(&TreePath::from_indicesv(&[config.live_palette as i32]))
.map_or(false, |iter| {
!palettes_model
.get_value(&iter, 2)
......@@ -293,7 +293,7 @@ pub fn update_ui(builder: &Builder, renderer: &Renderer, dirty: &Arc<Dirty>) {
palettes_cycle_duration.set_value(config.palettes_cycle.duration.as_secs() as f64);
palettes
.get_selection()
.select_path(&TreePath::new_from_indicesv(&[
.select_path(&TreePath::from_indicesv(&[
config.preview_palette as i32
]));
}
......@@ -31,9 +31,7 @@ pub fn init(builder: &Builder, renderer: &Arc<RwLock<Renderer>>, ignore_signals:
}
let mut state = STATE.write().unwrap();
if let Some(text) = artnet_broadcast_address.get_text() {
state.config.artnet_broadcast = text.into();
}
state.config.artnet_broadcast = artnet_broadcast_address.get_text().into();
}),
);
......
......@@ -257,7 +257,7 @@ pub fn update_ui(builder: &Builder, renderer: &Renderer, dirty: &Arc<Dirty>) {
let is_dirty = dirty.presets.load(Relaxed)
|| presets_model
.get_iter(&TreePath::new_from_indicesv(&[config.live_preset as i32]))
.get_iter(&TreePath::from_indicesv(&[config.live_preset as i32]))
.map_or(false, |iter| {
!presets_model
.get_value(&iter, 2)
......@@ -293,7 +293,7 @@ pub fn update_ui(builder: &Builder, renderer: &Renderer, dirty: &Arc<Dirty>) {
presets
.get_selection()
.select_path(&TreePath::new_from_indicesv(
.select_path(&TreePath::from_indicesv(
&[config.preview_preset as i32],
));
}
......@@ -136,7 +136,7 @@ pub fn update_ui(builder: &Builder, renderer: &Renderer) {
.unwrap_or(0);
render_groups
.get_selection()
.select_path(&TreePath::new_from_indicesv(&[active_render_group as i32]));
.select_path(&TreePath::from_indicesv(&[active_render_group as i32]));
}
render_group_cycle_on.set_active(config.render_group_cycle.on);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment