/* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ use gecko_bindings::structs::{nsTimingFunction, nsTimingFunction_Type}; use std::mem; use values::computed::ToComputedValue; use values::computed::transform::TimingFunction as ComputedTimingFunction; use values::generics::transform::{StepPosition, TimingKeyword}; use values::generics::transform::TimingFunction as GenericTimingFunction; use values::specified::transform::TimingFunction; impl nsTimingFunction { fn set_as_step(&mut self, function_type: nsTimingFunction_Type, steps: u32) { debug_assert!( function_type == nsTimingFunction_Type::StepStart || function_type == nsTimingFunction_Type::StepEnd, "function_type should be step-start or step-end" ); self.mType = function_type; unsafe { self.__bindgen_anon_1 .__bindgen_anon_1 .as_mut() .mStepsOrFrames = steps; } } fn set_as_frames(&mut self, frames: u32) { self.mType = nsTimingFunction_Type::Frames; unsafe { self.__bindgen_anon_1 .__bindgen_anon_1 .as_mut() .mStepsOrFrames = frames; } } fn set_as_bezier( &mut self, function_type: nsTimingFunction_Type, x1: f32, y1: f32, x2: f32, y2: f32, ) { self.mType = function_type; unsafe { let ref mut gecko_cubic_bezier = self.__bindgen_anon_1.mFunc.as_mut(); gecko_cubic_bezier.mX1 = x1; gecko_cubic_bezier.mY1 = y1; gecko_cubic_bezier.mX2 = x2; gecko_cubic_bezier.mY2 = y2; } } } impl From for nsTimingFunction { fn from(function: ComputedTimingFunction) -> nsTimingFunction { TimingFunction::from_computed_value(&function).into() } } impl From for nsTimingFunction { fn from(function: TimingFunction) -> nsTimingFunction { let mut tf: nsTimingFunction = unsafe { mem::zeroed() }; match function { GenericTimingFunction::Steps(steps, StepPosition::Start) => { debug_assert!(steps.value() >= 0); tf.set_as_step(nsTimingFunction_Type::StepStart, steps.value() as u32); }, GenericTimingFunction::Steps(steps, StepPosition::End) => { debug_assert!(steps.value() >= 0); tf.set_as_step(nsTimingFunction_Type::StepEnd, steps.value() as u32); }, GenericTimingFunction::Frames(frames) => { debug_assert!(frames.value() >= 2); tf.set_as_frames(frames.value() as u32); }, GenericTimingFunction::CubicBezier { x1, y1, x2, y2 } => { tf.set_as_bezier( nsTimingFunction_Type::CubicBezier, x1.get(), y1.get(), x2.get(), y2.get(), ); }, GenericTimingFunction::Keyword(keyword) => { let (x1, y1, x2, y2) = keyword.to_bezier(); tf.set_as_bezier(keyword.into(), x1, y1, x2, y2); }, } tf } } impl From for ComputedTimingFunction { fn from(function: nsTimingFunction) -> ComputedTimingFunction { match function.mType { nsTimingFunction_Type::StepStart => GenericTimingFunction::Steps( unsafe { function .__bindgen_anon_1 .__bindgen_anon_1 .as_ref() .mStepsOrFrames }, StepPosition::Start, ), nsTimingFunction_Type::StepEnd => GenericTimingFunction::Steps( unsafe { function .__bindgen_anon_1 .__bindgen_anon_1 .as_ref() .mStepsOrFrames }, StepPosition::End, ), nsTimingFunction_Type::Frames => GenericTimingFunction::Frames(unsafe { function .__bindgen_anon_1 .__bindgen_anon_1 .as_ref() .mStepsOrFrames }), nsTimingFunction_Type::Ease => GenericTimingFunction::Keyword(TimingKeyword::Ease), nsTimingFunction_Type::Linear => GenericTimingFunction::Keyword(TimingKeyword::Linear), nsTimingFunction_Type::EaseIn => GenericTimingFunction::Keyword(TimingKeyword::EaseIn), nsTimingFunction_Type::EaseOut => { GenericTimingFunction::Keyword(TimingKeyword::EaseOut) }, nsTimingFunction_Type::EaseInOut => { GenericTimingFunction::Keyword(TimingKeyword::EaseInOut) }, nsTimingFunction_Type::CubicBezier => unsafe { GenericTimingFunction::CubicBezier { x1: function.__bindgen_anon_1.mFunc.as_ref().mX1, y1: function.__bindgen_anon_1.mFunc.as_ref().mY1, x2: function.__bindgen_anon_1.mFunc.as_ref().mX2, y2: function.__bindgen_anon_1.mFunc.as_ref().mY2, } }, } } } impl From for nsTimingFunction_Type { fn from(keyword: TimingKeyword) -> Self { match keyword { TimingKeyword::Linear => nsTimingFunction_Type::Linear, TimingKeyword::Ease => nsTimingFunction_Type::Ease, TimingKeyword::EaseIn => nsTimingFunction_Type::EaseIn, TimingKeyword::EaseOut => nsTimingFunction_Type::EaseOut, TimingKeyword::EaseInOut => nsTimingFunction_Type::EaseInOut, } } }