[vlc-devel] [PATCH 1/2] macosx: Add VLCDefaultValueSlider
Marvin Scholz
epirat07 at gmail.com
Sun Dec 11 18:21:04 CET 2016
This is a new VLCDefaultSlider which allows setting a default
value, to which the knob will snap and a tick mark will be drawn for.
It's useful in VLC for things like volume sliders, which have a
default value (100%) to which we want the slider to snap.
Additionally this class is controllable with the scrollwheel by default.
---
.../package/macosx/vlc.xcodeproj/project.pbxproj | 12 ++
modules/gui/macosx/Makefile.am | 4 +-
modules/gui/macosx/VLCDefaultValueSlider.h | 62 ++++++++
modules/gui/macosx/VLCDefaultValueSlider.m | 83 +++++++++++
modules/gui/macosx/VLCDefaultValueSliderCell.h | 58 ++++++++
modules/gui/macosx/VLCDefaultValueSliderCell.m | 156 +++++++++++++++++++++
6 files changed, 374 insertions(+), 1 deletion(-)
create mode 100644 modules/gui/macosx/VLCDefaultValueSlider.h
create mode 100644 modules/gui/macosx/VLCDefaultValueSlider.m
create mode 100644 modules/gui/macosx/VLCDefaultValueSliderCell.h
create mode 100644 modules/gui/macosx/VLCDefaultValueSliderCell.m
diff --git a/extras/package/macosx/vlc.xcodeproj/project.pbxproj b/extras/package/macosx/vlc.xcodeproj/project.pbxproj
index 0dfd087..f986c83 100644
--- a/extras/package/macosx/vlc.xcodeproj/project.pbxproj
+++ b/extras/package/macosx/vlc.xcodeproj/project.pbxproj
@@ -419,6 +419,8 @@
6B3F8D2F1CE58E0E002A4998 /* VLCPreviousTemplate.pdf in Resources */ = {isa = PBXBuildFile; fileRef = 6B3F8D2B1CE58E0E002A4998 /* VLCPreviousTemplate.pdf */; };
6B3F8D311CE5CC21002A4998 /* VLCStatusBarIcon.pdf in Resources */ = {isa = PBXBuildFile; fileRef = 6B3F8D301CE5CC21002A4998 /* VLCStatusBarIcon.pdf */; };
6B3F8D331CE5CD57002A4998 /* VLCShuffleTemplate.pdf in Resources */ = {isa = PBXBuildFile; fileRef = 6B3F8D321CE5CD57002A4998 /* VLCShuffleTemplate.pdf */; };
+ 6B6A499E1DFD9B23009128AC /* VLCDefaultValueSlider.m in Sources */ = {isa = PBXBuildFile; fileRef = 6B6A499B1DFD9B23009128AC /* VLCDefaultValueSlider.m */; };
+ 6B6A499F1DFD9B23009128AC /* VLCDefaultValueSliderCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 6B6A499D1DFD9B23009128AC /* VLCDefaultValueSliderCell.m */; };
6B846FE41CF5D88C00112E54 /* VLCHUDButtonCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 6B846FDD1CF5D88C00112E54 /* VLCHUDButtonCell.m */; };
6B846FE51CF5D88C00112E54 /* VLCHUDCheckboxCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 6B846FDF1CF5D88C00112E54 /* VLCHUDCheckboxCell.m */; };
6B846FE61CF5D88C00112E54 /* VLCHUDRadiobuttonCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 6B846FE11CF5D88C00112E54 /* VLCHUDRadiobuttonCell.m */; };
@@ -1125,6 +1127,10 @@
6B3F8D2B1CE58E0E002A4998 /* VLCPreviousTemplate.pdf */ = {isa = PBXFileReference; lastKnownFileType = image.pdf; name = VLCPreviousTemplate.pdf; path = Resources/vlcmenubaricon/VLCPreviousTemplate.pdf; sourceTree = "<group>"; };
6B3F8D301CE5CC21002A4998 /* VLCStatusBarIcon.pdf */ = {isa = PBXFileReference; lastKnownFileType = image.pdf; name = VLCStatusBarIcon.pdf; path = Resources/vlcmenubaricon/VLCStatusBarIcon.pdf; sourceTree = "<group>"; };
6B3F8D321CE5CD57002A4998 /* VLCShuffleTemplate.pdf */ = {isa = PBXFileReference; lastKnownFileType = image.pdf; name = VLCShuffleTemplate.pdf; path = Resources/vlcmenubaricon/VLCShuffleTemplate.pdf; sourceTree = "<group>"; };
+ 6B6A499A1DFD9B23009128AC /* VLCDefaultValueSlider.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLCDefaultValueSlider.h; path = ../../../modules/gui/macosx/VLCDefaultValueSlider.h; sourceTree = "<group>"; };
+ 6B6A499B1DFD9B23009128AC /* VLCDefaultValueSlider.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = VLCDefaultValueSlider.m; path = ../../../modules/gui/macosx/VLCDefaultValueSlider.m; sourceTree = "<group>"; };
+ 6B6A499C1DFD9B23009128AC /* VLCDefaultValueSliderCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLCDefaultValueSliderCell.h; path = ../../../modules/gui/macosx/VLCDefaultValueSliderCell.h; sourceTree = "<group>"; };
+ 6B6A499D1DFD9B23009128AC /* VLCDefaultValueSliderCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = VLCDefaultValueSliderCell.m; path = ../../../modules/gui/macosx/VLCDefaultValueSliderCell.m; sourceTree = "<group>"; };
6B846FDC1CF5D88C00112E54 /* VLCHUDButtonCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLCHUDButtonCell.h; path = ../../../modules/gui/macosx/VLCHUDButtonCell.h; sourceTree = "<group>"; };
6B846FDD1CF5D88C00112E54 /* VLCHUDButtonCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = VLCHUDButtonCell.m; path = ../../../modules/gui/macosx/VLCHUDButtonCell.m; sourceTree = "<group>"; };
6B846FDE1CF5D88C00112E54 /* VLCHUDCheckboxCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = VLCHUDCheckboxCell.h; path = ../../../modules/gui/macosx/VLCHUDCheckboxCell.h; sourceTree = "<group>"; };
@@ -1763,6 +1769,10 @@
6B846FE81CF5D89500112E54 /* HUD UI Classes */,
5CCED71414C0D4A90057F8D1 /* VLCUIWidgets.h */,
5CCED71514C0D4A90057F8D1 /* VLCUIWidgets.m */,
+ 6B6A499A1DFD9B23009128AC /* VLCDefaultValueSlider.h */,
+ 6B6A499B1DFD9B23009128AC /* VLCDefaultValueSlider.m */,
+ 6B6A499C1DFD9B23009128AC /* VLCDefaultValueSliderCell.h */,
+ 6B6A499D1DFD9B23009128AC /* VLCDefaultValueSliderCell.m */,
E0C2583E161B593D00185AAD /* VLCVoutWindowController.h */,
E0C2583F161B593D00185AAD /* VLCVoutWindowController.m */,
E06CF7F416020F6200C698B7 /* Windows.h */,
@@ -3556,6 +3566,7 @@
6B846FE51CF5D88C00112E54 /* VLCHUDCheckboxCell.m in Sources */,
1CCB5F6A1A62A724004C3E90 /* VLCExtensionsDialogProvider.h in Sources */,
7DBB06641CC2314D004C74D2 /* caopengllayer.m in Sources */,
+ 6B6A499E1DFD9B23009128AC /* VLCDefaultValueSlider.m in Sources */,
1CCB5F6B1A62A724004C3E90 /* VLCExtensionsDialogProvider.m in Sources */,
1CCB5F6C1A62A724004C3E90 /* VLCExtensionsManager.h in Sources */,
1CCB5F6D1A62A724004C3E90 /* VLCExtensionsManager.m in Sources */,
@@ -3582,6 +3593,7 @@
1C67C8A81D58C0A40079E1C1 /* VLCAboutWindowController.m in Sources */,
1CCB5F801A62A724004C3E90 /* VLCPlaylistInfo.m in Sources */,
1CCB5F811A62A724004C3E90 /* prefs_widgets.h in Sources */,
+ 6B6A499F1DFD9B23009128AC /* VLCDefaultValueSliderCell.m in Sources */,
1CCB5F821A62A724004C3E90 /* prefs_widgets.m in Sources */,
1CCB5F831A62A724004C3E90 /* prefs.h in Sources */,
1CCB5F841A62A724004C3E90 /* prefs.m in Sources */,
diff --git a/modules/gui/macosx/Makefile.am b/modules/gui/macosx/Makefile.am
index 2a0fcc8..9f5cc4f 100644
--- a/modules/gui/macosx/Makefile.am
+++ b/modules/gui/macosx/Makefile.am
@@ -88,4 +88,6 @@ libmacosx_plugin_la_SOURCES = \
VLCResumeDialogController.h VLCResumeDialogController.m \
VLCTrackSynchronizationWindowController.h VLCTrackSynchronizationWindowController.m \
VLCVideoEffectsWindowController.h VLCVideoEffectsWindowController.m \
- VLCFSPanelController.h VLCFSPanelController.m
+ VLCFSPanelController.h VLCFSPanelController.m \
+ VLCDefaultValueSlider.h VLCDefaultValueSlider.m \
+ VLCDefaultValueSliderCell.h VLCDefaultValueSliderCell.m
diff --git a/modules/gui/macosx/VLCDefaultValueSlider.h b/modules/gui/macosx/VLCDefaultValueSlider.h
new file mode 100644
index 0000000..4a9ab7c
--- /dev/null
+++ b/modules/gui/macosx/VLCDefaultValueSlider.h
@@ -0,0 +1,62 @@
+/*****************************************************************************
+ * VLCDefaultValueSlider.h: Custom NSSlider which allows a defaultValue
+ *****************************************************************************
+ * Copyright (C) 2016 VLC authors and VideoLAN
+ * $Id$
+ *
+ * Authors: Marvin Scholz <epirat07 -at- gmail -dot- com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#import <Cocoa/Cocoa.h>
+
+/**
+ \c VLCDefaultValueSlider is a NSSlider subclass that allows setting
+ a \c defaultValue which gets a tickmark and the knob snaps to that
+ default value. Additionally a VLCDefaultValueSlider can be adjusted
+ with the mouse scroll wheel, if enabled.
+ */
+ at interface VLCDefaultValueSlider : NSSlider
+
+/**
+ Indicates if the slider is scrollable with the mouse or trackpad scrollwheel.
+ */
+ at property (readwrite) BOOL isScrollable;
+
+/**
+ Sets the default value to which the slider will snap and draw a tickmark for.
+
+ \note value must be in the value range of the slider and be smaller than \c DBL_MAX
+
+ \param value The default value
+ */
+- (void)setDefaultValue:(double)value;
+
+/**
+ Unsets the default value
+
+ \note Internally this sets the defaultValue to \c DBL_MAX
+ */
+- (void)unsetDefaultValue;
+
+/**
+ Get the default value
+
+ \note It the returned value is \c DBL_MAX, there is no defaultValue set.
+ */
+- (double)defaultValue;
+
+ at end
diff --git a/modules/gui/macosx/VLCDefaultValueSlider.m b/modules/gui/macosx/VLCDefaultValueSlider.m
new file mode 100644
index 0000000..e10c5e5
--- /dev/null
+++ b/modules/gui/macosx/VLCDefaultValueSlider.m
@@ -0,0 +1,83 @@
+/*****************************************************************************
+ * VLCDefaultValueSlider.m: Custom NSSlider which allows a defaultValue
+ *****************************************************************************
+ * Copyright (C) 2016 VLC authors and VideoLAN
+ * $Id$
+ *
+ * Authors: Marvin Scholz <epirat07 -at- gmail -dot- com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#import "VLCDefaultValueSlider.h"
+#import "VLCDefaultValueSliderCell.h"
+
+ at implementation VLCDefaultValueSlider
+
+- (instancetype)initWithCoder:(NSCoder *)coder
+{
+ if ([coder isKindOfClass: [NSKeyedUnarchiver class]]) {
+ NSKeyedUnarchiver *keyedUnarchiver = (id)coder;
+ NSString *oldClass = NSStringFromClass([self.superclass cellClass]);
+ [keyedUnarchiver setClass:[VLCDefaultValueSliderCell class] forClassName:oldClass];
+ }
+ self = [super initWithCoder:coder];
+ if (self) {
+ _isScrollable = YES;
+ }
+ return self;
+}
+
+- (void)scrollWheel:(NSEvent *)event
+{
+ if (!_isScrollable)
+ return [super scrollWheel:event];
+ double increment;
+ CGFloat deltaY = [event scrollingDeltaY];
+ double range = [self maxValue] - [self minValue];
+
+ // Scroll less for high precision, else it's too fast
+ if (event.hasPreciseScrollingDeltas) {
+ increment = (range * 0.002) * deltaY;
+ } else {
+ if (deltaY == 0.0)
+ return;
+ increment = (range * 0.01 * deltaY);
+ }
+
+ // If scrolling is inversed, increment in other direction
+ if (!event.isDirectionInvertedFromDevice)
+ increment = -increment;
+
+ [self setDoubleValue:self.doubleValue - increment];
+ [self sendAction:self.action to:self.target];
+}
+
+- (void)setDefaultValue:(double)value
+{
+ [(VLCDefaultValueSliderCell *)self.cell setDefaultValue:value];
+}
+
+- (void)unsetDefaultValue
+{
+ [(VLCDefaultValueSliderCell *)self.cell unsetDefaultValue];
+}
+
+- (double)defaultValue
+{
+ return [(VLCDefaultValueSliderCell *)self.cell defaultValue];
+}
+
+ at end
diff --git a/modules/gui/macosx/VLCDefaultValueSliderCell.h b/modules/gui/macosx/VLCDefaultValueSliderCell.h
new file mode 100644
index 0000000..1aae9b0
--- /dev/null
+++ b/modules/gui/macosx/VLCDefaultValueSliderCell.h
@@ -0,0 +1,58 @@
+/*****************************************************************************
+ * VLCDefaultValueSliderCell.h: SliderCell subclass for VLCDefaultValueSlider
+ *****************************************************************************
+ * Copyright (C) 2016 VLC authors and VideoLAN
+ * $Id$
+ *
+ * Authors: Marvin Scholz <epirat07 -at- gmail -dot- com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#import <Cocoa/Cocoa.h>
+
+/**
+ \c VLCDefaultValueSliderCell is the cell use by the
+ \c VLCDefaultValueSlider class.
+ */
+ at interface VLCDefaultValueSliderCell : NSSliderCell
+
+/**
+ Indicates if a tickmark should be drawn for the \c defaultValue
+ */
+ at property (readwrite) BOOL drawTickMarkForDefault;
+
+/**
+ Indicates if the slider knob should snap to the \c defaultValue
+ */
+ at property (readwrite) BOOL snapsToDefault;
+
+- (void)setDefaultValue:(double)value;
+- (void)unsetDefaultValue;
+
+- (double)defaultValue;
+
+/**
+ Draws the tick mark for the \c defaultValue in the
+ given rect.
+
+ \note Override this in a subclass if you need to customize the
+ tickmark that is drawn for the \c defaultValue
+
+ \param rect The rect in which the tickMark should be drawn
+ */
+- (void)drawDefaultTickMarkWithFrame:(NSRect)rect;
+
+ at end
diff --git a/modules/gui/macosx/VLCDefaultValueSliderCell.m b/modules/gui/macosx/VLCDefaultValueSliderCell.m
new file mode 100644
index 0000000..f2fbbda
--- /dev/null
+++ b/modules/gui/macosx/VLCDefaultValueSliderCell.m
@@ -0,0 +1,156 @@
+/*****************************************************************************
+ * VLCDefaultValueSliderCell.m: SliderCell subclass for VLCDefaultValueSlider
+ *****************************************************************************
+ * Copyright (C) 2016 VLC authors and VideoLAN
+ * $Id$
+ *
+ * Authors: Marvin Scholz <epirat07 -at- gmail -dot- com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#import "VLCDefaultValueSliderCell.h"
+
+ at interface VLCDefaultValueSliderCell (){
+ double _defaultDoubleValue;
+ CGFloat _defaultPosition;
+ CGFloat _isRTL;
+}
+ at end
+
+ at implementation VLCDefaultValueSliderCell
+
+#pragma mark -
+#pragma mark Public interface
+
+- (instancetype)initWithCoder:(NSCoder *)coder
+{
+ self = [super initWithCoder:coder];
+ if (self) {
+ _defaultDoubleValue = DBL_MAX;
+ _isRTL = ([self userInterfaceLayoutDirection] == NSUserInterfaceLayoutDirectionRightToLeft);
+ }
+ return self;
+}
+
+- (void)setDefaultValue:(double)value
+{
+ if (_defaultDoubleValue == DBL_MAX) {
+ _drawTickMarkForDefault = YES;
+ _snapsToDefault = YES;
+ }
+ _defaultDoubleValue = value;
+ _defaultPosition = [self pointForValue:_defaultDoubleValue];
+}
+
+- (void)unsetDefaultValue
+{
+ _defaultDoubleValue = DBL_MAX;
+ _drawTickMarkForDefault = NO;
+ _snapsToDefault = NO;
+}
+
+- (double)defaultValue
+{
+ return _defaultDoubleValue;
+}
+
+- (void)drawDefaultTickMarkWithFrame:(NSRect)rect
+{
+ [[NSColor grayColor] setFill];
+ NSRectFill(rect);
+}
+
+#pragma mark -
+#pragma mark Internal helpers
+
+- (CGFloat)pointForValue:(double)value
+{
+ CGFloat sliderRange;
+ NSRect cellFrame = self.controlView.frame;
+ CGFloat defaultRelative = (self.maxValue - self.minValue) / (value - self.minValue);
+ if (self.isVertical)
+ sliderRange = cellFrame.size.height - self.knobThickness;
+ else
+ sliderRange = cellFrame.size.width - self.knobThickness;
+ CGFloat sliderOrigin = self.knobThickness / 2.0;
+ CGFloat point = 1.0 / defaultRelative * sliderRange + sliderOrigin;
+
+ return point;
+}
+
+#pragma mark -
+#pragma mark Overwritten super methods
+
+- (void)drawWithFrame:(NSRect)cellFrame inView:(NSView *)controlView
+{
+ // Do all other drawing
+ [super drawWithFrame:cellFrame inView:controlView];
+
+ // Draw default tickmark
+ if (_drawTickMarkForDefault) {
+ CGFloat tickThickness = 1.0;
+ NSRect tickFrame = cellFrame;
+ if (self.isVertical) {
+ tickFrame.origin.y = (tickFrame.size.height - _defaultPosition);
+ tickFrame.origin.y -= tickThickness / 2;
+ tickFrame.size.height = tickThickness;
+ } else {
+ tickFrame.origin.x = (_isRTL) ? (tickFrame.size.width - _defaultPosition) : _defaultPosition;
+ tickFrame.origin.x -= tickThickness / 2;
+ tickFrame.size.width = tickThickness;
+ }
+
+ [self drawDefaultTickMarkWithFrame:tickFrame];
+ }
+
+ // Redraw knob
+ [super drawKnob];
+
+}
+
+- (BOOL)continueTracking:(NSPoint)lastPoint at:(NSPoint)currentPoint inView:(NSView *)controlView
+{
+ double oldValue = [self doubleValue];
+ BOOL result = [super continueTracking:lastPoint at:currentPoint inView:controlView];
+ double newValue = [self doubleValue];
+
+ // If no change, nothing to do.
+ if (newValue == oldValue)
+ return result;
+
+ // Determine in which direction slider is moving
+ BOOL sliderMovingForward = YES;
+ if (oldValue > newValue) {
+ sliderMovingForward = NO;
+ }
+
+ // Calculate snap-threshhold
+ double range = self.maxValue - self.minValue;
+ double thresh = (range * 0.01) * 5;
+
+ // Snap to default value
+ if (ABS(newValue - _defaultDoubleValue) < thresh && _snapsToDefault) {
+ if (sliderMovingForward && newValue > _defaultDoubleValue) {
+ [self setDoubleValue: _defaultDoubleValue];
+ } else if (!sliderMovingForward && newValue < _defaultDoubleValue) {
+ [self setDoubleValue: _defaultDoubleValue];
+ }
+ }
+
+ return result;
+}
+
+ at end
--
2.9.3 (Apple Git-75)
More information about the vlc-devel
mailing list