From e7e834b723c94b2699171844c651035f6fb92cb4 Mon Sep 17 00:00:00 2001 From: Ruud Date: Sun, 20 Nov 2011 22:01:08 +0100 Subject: [PATCH] Renaming dropdown choice tagging --- couchpotato/core/plugins/renamer/__init__.py | 35 ++- couchpotato/static/scripts/page/settings.js | 228 ++++++++++++++ couchpotato/static/style/main.css | 11 +- couchpotato/static/style/page/settings.css | 296 ++++++++++++++----- couchpotato/templates/_desktop.html | 10 +- 5 files changed, 495 insertions(+), 85 deletions(-) diff --git a/couchpotato/core/plugins/renamer/__init__.py b/couchpotato/core/plugins/renamer/__init__.py index cc6b411a..74a12d9d 100644 --- a/couchpotato/core/plugins/renamer/__init__.py +++ b/couchpotato/core/plugins/renamer/__init__.py @@ -3,14 +3,33 @@ from couchpotato.core.plugins.renamer.main import Renamer def start(): return Renamer() +rename_options = { + 'pre': '<', + 'post': '>', + 'choices': { + 'ext': 'Extention (mkv)', + 'namethe': 'Moviename, The', + 'thename': 'The Moviename', + 'year': 'Year (2011)', + 'first': 'First letter (M)', + 'dirname': 'Dirname (Moviename.2011.720p-releasegrp)', + 'quality': 'Quality (720P)', + 'video': 'Video (x264)', + 'audio': 'Audio (DTS)', + 'group': 'Releasegroup name', + 'source': 'Source media (Bluray)', + }, +} + config = [{ 'name': 'renamer', + 'description': 'Move and rename your downloaded movies to your movie directory.', 'groups': [ { 'tab': 'renamer', 'name': 'renamer', - 'label': 'Folders', - 'description': 'Move and rename your downloaded movies to your movie directory.', + 'label': 'Enable renaming', + 'wizard': True, 'options': [ { 'name': 'enabled', @@ -20,24 +39,28 @@ config = [{ { 'name': 'from', 'type': 'directory', - 'description': 'Folder where the movies are downloaded to.', + 'description': 'Folder where CP searches for movies.', }, { 'name': 'to', 'type': 'directory', - 'description': 'Folder where the movies will be moved to.', + 'description': 'Folder where the movies should be moved to.', }, { 'name': 'folder_name', 'label': 'Folder naming', 'description': 'Name of the folder. Keep empty for no folder.', 'default': ' ()', + 'type': 'choice', + 'options': rename_options }, { 'name': 'file_name', 'label': 'File naming', 'description': 'Name of the file', 'default': '.', + 'type': 'choice', + 'options': rename_options }, { 'name': 'cleanup', @@ -86,11 +109,15 @@ config = [{ 'name': 'nfo_name', 'label': 'NFO naming', 'default': '.orig.', + 'type': 'choice', + 'options': rename_options }, { 'name': 'trailer_name', 'label': 'Trailer naming', 'default': '-trailer.', + 'type': 'choice', + 'options': rename_options }, ], }, diff --git a/couchpotato/static/scripts/page/settings.js b/couchpotato/static/scripts/page/settings.js index b1823f45..b8167ee4 100644 --- a/couchpotato/static/scripts/page/settings.js +++ b/couchpotato/static/scripts/page/settings.js @@ -675,3 +675,231 @@ Option.Directory = new Class({ return self.input.get('text'); } }); + +Option.Choice = new Class({ + Extends: Option.String, + + afterInject: function(){ + var self = this; + + self.replaceInput(); + + self.select = new Element('select').adopt( + new Element('option[text=Add option]') + ).inject(self.tag_input, 'after'); + + var o = self.options.options; + Object.each(o.choices, function(label, choice){ + new Element('option', { + 'text': label, + 'value': o.pre + choice + o.post + }).inject(self.select); + }); + + self.select = new Form.Dropdown(self.select, { + 'onChange': self.addSelection.bind(self) + }); + }, + + replaceInput: function(){ + var self = this; + self.initialized = self.initialized ? self.initialized+1 : 1; + + var value = self.getValue(); + var matches = value.match(/<([^>]*)>/g); + + self.tag_input = new Element('ul.inlay', { + 'events': { + 'click': function(e){ + if(e.target == self.tag_input){ + var input = self.tag_input.getElement('li:last-child input'); + input.fireEvent('focus'); + input.focus(); + } + + self.el.addEvent('outerClick', function(){ + self.reset(); + self.el.removeEvents('outerClick'); + }) + } + } + }).inject(self.input, 'after'); + self.el.addClass('tag_input'); + + var mtches = [] + if(matches) + matches.each(function(match, mnr){ + var msplit = value.split(match); + msplit.each(function(matchsplit, snr){ + if(msplit.length-1 == snr) + value = matchsplit; + mtches.append([value == matchsplit ? match : matchsplit]); + + if(matches.length*2 == mtches.length) + mtches.append([value]); + }); + }); + + mtches.each(self.addTag.bind(self)); + + self.addLastTag(); + + // Sortable + self.sortable = new Sortables(self.tag_input, { + 'revert': true, + 'handle': '', + 'opacity': 0.5, + 'onComplete': function(){ + self.setOrder(); + self.reset(); + } + }); + }, + + addLastTag: function(){ + if(this.tag_input.getElement('li.choice:last-child')) + this.addTag(''); + }, + + addTag: function(tag){ + var self = this; + tag = new Option.Choice.Tag(tag, { + 'onChange': self.setOrder.bind(self), + 'onFocus': self.activate.bind(self), + 'onBlur': function(){ + self.addLastTag(); + self.deactivate(); + } + }); + $(tag).inject(self.tag_input); + + if(self.initialized > 1) + tag.setWidth(); + else + (function(){ tag.setWidth(); }).delay(10, self); + + return tag; + }, + + setOrder: function(){ + var self = this; + + var value = ''; + self.tag_input.getElements('li').each(function(el){ + value += el.getElement('span').get('text'); + }); + self.addLastTag(); + + self.input.set('value', value); + self.input.fireEvent('change'); + }, + + addSelection: function(){ + var self = this; + + var tag = self.addTag(self.el.getElement('.selection input').get('value')); + self.sortable.addItems($(tag)); + self.setOrder(); + }, + + reset: function(){ + var self = this; + + self.tag_input.destroy(); + self.sortable.detach(); + + self.replaceInput(); + }, + + activate: function(){ + + }, + + deactivate: function(){ + + } + +}); + +Option.Choice.Tag = new Class({ + + Implements: [Options, Events], + + options: { + 'pre': '<', + 'post': '>' + }, + + initialize: function(tag, options){ + var self = this; + self.setOptions(options); + + self.tag = tag; + self.is_choice = tag.substr(0, 1) == self.options.pre && tag.substr(-1) == self.options.post; + + self.create(); + }, + + create: function(){ + var self = this; + + self.el = new Element('li', { + 'class': self.is_choice ? 'choice' : '', + 'events': { + 'mouseover': !self.is_choice ? self.fireEvent.bind(self, 'focus') : function(){} + } + }).adopt( + self.input = new Element(self.is_choice ? 'span' : 'input', { + 'text': self.tag, + 'value': self.tag, + 'events': { + 'keyup': self.is_choice ? null : function(){ + self.setWidth(); + self.fireEvent('change'); + }, + 'focus': self.fireEvent.bind(self, 'focus'), + 'blur': self.fireEvent.bind(self, 'blur') + } + }), + self.span = !self.is_choice ? new Element('span', { + 'text': self.tag + }) : null, + self.del_button = new Element('a.delete', { + 'events': { + 'click': self.del.bind(self) + } + }) + ); + + self.addEvent('focus', self.setWidth.bind(self)); + + }, + + focus: function(){ + this.input.focus(); + }, + + setWidth: function(){ + var self = this; + + if(self.span && self.input){ + self.span.set('text', self.input.get('value')); + self.input.setStyle('width', self.span.getSize().x+2); + } + }, + + del: function(){ + var self = this; + self.el.destroy(); + self.fireEvent('change'); + }, + + getValue: function(){ + return this.span.get('text'); + }, + + toElement: function(){ + return this.el; + } + +}); diff --git a/couchpotato/static/style/main.css b/couchpotato/static/style/main.css index 754cf642..28fa3faf 100644 --- a/couchpotato/static/style/main.css +++ b/couchpotato/static/style/main.css @@ -259,6 +259,7 @@ body > .spinner, .mask{ .select { cursor: pointer; display: inline-block; + color: #fff; } .select .selection { @@ -303,11 +304,11 @@ body > .spinner, .mask{ font-weight: bold; } .select .list { - display: none; + display: none; background: #282d34; border: 1px solid #1f242b; position: absolute; - margin: 28px 0 0 0; + margin: 25px 0 0 0; box-shadow: 0 1px 2px rgba(0,0,0,0.4); -moz-box-shadow: 0 1px 2px rgba(0,0,0,0.4); -webkit-box-shadow: 0 1px 2px rgba(0,0,0,0.4); @@ -325,11 +326,15 @@ body > .spinner, .mask{ width: 100% !important; } .select .list li { - padding: 2px 33px 2px 20px; + padding: 0 33px 0 20px; + margin: 0 !important; display: block; + border-top: 1px solid rgba(255,255,255,0.1); + white-space: nowrap; } .select .list li.highlighted { background: rgba(255,255,255,0.1); + border-color: transparent; } .select input { display: none; } diff --git a/couchpotato/static/style/page/settings.css b/couchpotato/static/style/page/settings.css index d9916272..37be543b 100644 --- a/couchpotato/static/style/page/settings.css +++ b/couchpotato/static/style/page/settings.css @@ -53,21 +53,21 @@ min-height: 300px; } - .page.settings .advanced { + .page .advanced { display: none; color: #edc07f; } - .page.settings.show_advanced .advanced { display: block; } + .page.show_advanced .advanced { display: block; } .page.settings .tab_content { display: none; } .page.settings .tab_content.active { display: block; } - .page.settings fieldset { + .page fieldset { padding: 10px 0; } - .page.settings fieldset h2 { + .page fieldset h2 { font-weight: normal; font-size: 25px; padding: 0 9px 10px 30px; @@ -78,15 +78,15 @@ -moz-box-shadow: 0 1px 0px rgba(255,255,255, 0.15); -webkit-box-shadow: 0 1px 0px rgba(255,255,255, 0.15); } - .page.settings fieldset h2 .hint { + .page fieldset h2 .hint { font-size: 12px; margin-left: 10px; } - .page.settings fieldset.disabled .ctrlHolder { + .page fieldset.disabled .ctrlHolder { display: none; } - .page.settings fieldset .ctrlHolder:first-child { + .page fieldset .ctrlHolder:first-child { display: block; padding: 0; width: auto; @@ -97,26 +97,28 @@ width: 20px; } - .page.settings .ctrlHolder { + .page .ctrlHolder { line-height: 25px; padding: 10px 10px 10px 30px; font-size: 14px; border: 0; } - .page.settings .ctrlHolder.save_success:not(:first-child) { + .page .ctrlHolder.save_success:not(:first-child) { background: url('../../images/icon.check.png') no-repeat 7px center; } - .page.settings .ctrlHolder:last-child { border: none; } - .page.settings .ctrlHolder:hover { background-color: rgba(255,255,255,0.05); } - .page.settings .ctrlHolder.focused { background-color: rgba(255,255,255,0.2); } - .page.settings .ctrlHolder.focused:first-child, .page.settings .ctrlHolder:first-child{ background-color: transparent; } + .page .ctrlHolder:last-child { border: none; } + .page .ctrlHolder:hover { background-color: rgba(255,255,255,0.05); } + .page .ctrlHolder.focused { background-color: rgba(255,255,255,0.2); } + .page .ctrlHolder.focused:first-child, .page .ctrlHolder:first-child{ background-color: transparent; } - .page.settings .ctrlHolder .formHint { - float: right; + .page .ctrlHolder .formHint { width: 47%; margin: -18px 0; padding: 0; - color: #fff; + color: #fff !important; + display: inline-block; + vertical-align: middle; + padding-left: 2%; } .check { @@ -135,7 +137,7 @@ display: none; } - .page.settings .check + .formHint { + .page .check + .formHint { float: none; width: auto; display: inline-block; @@ -144,16 +146,16 @@ vertical-align: middle; } - .page.settings .ctrlHolder label { + .page .ctrlHolder label { font-weight: bold; width: 20%; margin: 0; padding: 6px 0 0; } - .page.settings .xsmall { width: 20px !important; text-align: center; } + .page .xsmall { width: 20px !important; text-align: center; } - .page.settings input[type=text], .page.settings input[type=password] { + .page input[type=text], .page input[type=password] { padding: 5px 3px; margin: 0; width: 30%; @@ -162,25 +164,25 @@ -webkit-border-radius: 3px; -moz-border-radius: 3px; } - .page.settings .input.xsmall { width: 5% } - .page.settings .input.small { width: 10% } - .page.settings .input.medium { width: 15% } - .page.settings .input.large { width: 25% } - .page.settings .input.xlarge { width: 30% } + .page .input.xsmall { width: 5% } + .page .input.small { width: 10% } + .page .input.medium { width: 15% } + .page .input.large { width: 25% } + .page .input.xlarge { width: 30% } - .page.settings .advanced_toggle { + .page .advanced_toggle { clear: both; display: block; text-align: right; height: 20px; margin: 0; } - .page.settings .advanced_toggle span { padding: 0 5px; } - .page.settings.show_advanced .advanced_toggle { + .page .advanced_toggle span { padding: 0 5px; } + .page.show_advanced .advanced_toggle { color: #edc07f; } - .page.settings .directory { + .page .directory { display: inline-block; padding: 0 4% 0 4px; font-size: 13px; @@ -191,7 +193,7 @@ overflow: hidden; vertical-align: top; } - .page.settings .directory > span { + .page .directory > span { height: 25px; display: inline-block; float: right; @@ -200,11 +202,11 @@ cursor: pointer; } - .page.settings .directory_list { + .page .directory_list { z-index: 2; position: absolute; - width: 360px; - margin: -2px 0 20px 60px; + width: 450px; + margin: 28px 0 20px -4px; background: #5c697b; border-radius: 3px; -webkit-border-radius: 3px; @@ -214,54 +216,55 @@ -webkit-box-shadow: 0 0 50px rgba(0,0,0,0.55); } - .page.settings .directory_list .pointer { - border-right: 10px solid transparent; - border-left: 10px solid transparent; - border-bottom: 10px solid #5c697b; + .page .directory_list .pointer { + border-right: 6px solid transparent; + border-left: 6px solid transparent; + border-bottom: 6px solid #5c697b; display: block; position: absolute; width: 0px; - margin: -9px 0 0 48.5%; + margin: -6px 0 0 38%; } - .page.settings .directory_list ul { + .page .directory_list ul { width: 92%; height: 300px; overflow: auto; margin: 0 4%; + font-size: 16px; } - .page.settings .directory_list li { - padding: 0 10px; + .page .directory_list li { + padding: 4px 10px; cursor: pointer; - margin: 0; + margin: 0 !important; border-top: 1px solid rgba(255,255,255,0.1); background: url('../../images/right.arrow.png') no-repeat 98% center; } - .page.settings .directory_list li:last-child { + .page .directory_list li:last-child { border-bottom: 1px solid rgba(255,255,255,0.1); } - .page.settings .directory_list li:hover { + .page .directory_list li:hover { background-color: #515c68; } - .page.settings .directory_list .actions { + .page .directory_list .actions { clear: both; padding: 4% 4% 2%; min-height: 25px; } - .page.settings .directory_list .actions label { + .page .directory_list .actions label { float: right; width: auto; padding: 0; } - .page.settings .directory_list .actions .inlay { + .page .directory_list .actions .inlay { margin: -2px 0 0 7px; } - .page.settings .directory_list .actions .back { + .page .directory_list .actions .back { font-weight: bold; width: 160px; display: inline-block; @@ -270,57 +273,204 @@ vertical-align: top; } - .page.settings .directory_list .actions:last-child { + .page .directory_list .actions:last-child { float: right; padding: 4%; } - .page.settings .directory_list .actions:last-child > span { + .page .directory_list .actions:last-child > span { padding: 0 5px; text-shadow: none; } - .page.settings .directory_list .actions:last-child > .clear { + .page .directory_list .actions:last-child > .clear { left: -90%; position: relative; background-color: #af3128; } - .page.settings .directory_list .actions:last-child > .cancel { + .page .directory_list .actions:last-child > .cancel { font-weight: bold; color: #ddd; } - .page.settings .directory_list .actions:last-child > .save { + .page .directory_list .actions:last-child > .save { background: #9dc156; } + + .page .tag_input select { + width: 20%; + display: inline-block; + } + + .page .tag_input .selection { + border-radius: 0 10px 10px 0; + -moz-border-radius: 0 10px 10px 0; + -webkit-border-radius: 0 10px 10px 0; + height: 26px; + } + + .page .tag_input > input { + display: none; + } + + .page .tag_input > ul { + list-style: none; + line-height: 20px; + padding: 3px 0; + border-radius: 3px; + -moz-border-radius: 3px; + -webkit-border-radius: 3px; + cursor: text; + width: 31%; + margin: 0 !important; + } + .page .tag_input:hover > ul { + width: 50%; + border-radius: 3px 0 0 3px; + -moz-border-radius: 3px 0 0 3px; + -webkit-border-radius: 3px 0 0 3px; + } + .page .tag_input:hover .formHint { display: none; } + + .page .tag_input > ul > li { + display: inline-block; + min-height: 20px; + min-width: 2px; + font-size: 12px; + padding: 0; + margin: 0 !important; + border-width: 0; + background: 0; + } + .page .tag_input > ul > li:first-child { min-width: 4px; } + .page .tag_input li.choice { + cursor: -moz-grab; + cursor: -webkit-grab; + cursor: grab; + padding: 0; + border-radius: 2px; + -moz-border-radius: 2px; + -webkit-border-radius: 2px; + } + .page .tag_input > ul:hover > li.choice { + background: url('../images/checks.png') no-repeat 94% -53px, -webkit-gradient( + linear, + left bottom, + left top, + color-stop(0, rgba(255,255,255,0.1)), + color-stop(1, rgba(255,255,255,0.3)) + ); + background: url('../images/checks.png') no-repeat 94% -53px, -moz-linear-gradient( + center top, + rgba(255,255,255,0.3) 0%, + rgba(255,255,255,0.1) 100% + ); + } + .page .tag_input > ul > li.choice:hover { + background: url('../images/checks.png') no-repeat 94% -53px, -webkit-gradient( + linear, + left bottom, + left top, + color-stop(0, #406db8), + color-stop(1, #5b9bd1) + ); + background: url('../images/checks.png') no-repeat 94% -53px, -moz-linear-gradient( + center top, + #5b9bd1 0%, + #406db8 100% + ); + } + + .page .tag_input .select { + display: none; + } + .page .tag_input:hover .select { display: inline-block; } + + .page .tag_input li input { + background: 0; + border: 0; + color: #fff; + outline-width: 0; + padding: 0; + min-width: 2px; + } + .page .tag_input li:first-child input { + padding-left: 2px; + min-width: 0; + } + + .page .tag_input li:not(.choice) span { + white-space: pre; + position: absolute; + top: -9999px; + } + + .page .tag_input .delete { + display: none; + height: 10px; + width: 16px; + position: absolute; + margin: -9px 0 0 -16px; + border-radius: 30px 30px 0 0; + -webkit-border-radius: 30px 30px 0 0; + -moz-border-radius: 30px 30px 0 0; + cursor: pointer; + background: url('../images/checks.png') no-repeat 94% -53px, -webkit-gradient( + linear, + left bottom, + left top, + color-stop(0, #5b9bd1), + color-stop(1, #5b9bd1) + ); + background: url('../images/checks.png') no-repeat 94% -53px, -moz-linear-gradient( + center top, + #5b9bd1 0%, + #5b9bd1 100% + ); + } + .page .tag_input .choice:hover .delete { display: inline-block; } + .page .tag_input .choice .delete:hover { + background: url('../images/checks.png') no-repeat 94% -53px, -webkit-gradient( + linear, + left bottom, + left top, + color-stop(0, #cc0000), + color-stop(1, #cc3e00) + ); + background: url('../images/checks.png') no-repeat 94% -53px, -moz-linear-gradient( + center top, + #5b9bd1 0%, + #5b9bd1 100% + ); + } - .page.settings .section_newznab .head { + .page .section_newznab .head { margin: 0 0 0 60px; } - .page.settings .disabled .head { display: none; } - .page.settings .section_newznab .head abbr { + .page .disabled .head { display: none; } + .page .section_newznab .head abbr { display: inline-block; font-weight: bold; border-bottom: 1px dotted #fff; line-height: 140%; cursor: help; } - .page.settings .section_newznab .head abbr.host { + .page .section_newznab .head abbr.host { margin-right: 197px; } - .page.settings .section_newznab .ctrlHolder { + .page .section_newznab .ctrlHolder { padding-top: 2px; padding-bottom: 3px; } - .page.settings .section_newznab .ctrlHolder.hide { display: none; } + .page .section_newznab .ctrlHolder.hide { display: none; } - .page.settings .section_newznab .ctrlHolder > * { + .page .section_newznab .ctrlHolder > * { margin: 0 10px 0 0; } - .page.settings .section_newznab .ctrlHolder .delete { + .page .section_newznab .ctrlHolder .delete { display: inline-block; width: 22px; height: 22px; @@ -328,32 +478,32 @@ background-position: left center; } - .page.settings .section_newznab .ctrlHolder.is_empty .delete, .page.settings .section_newznab .ctrlHolder.is_empty .use { + .page .section_newznab .ctrlHolder.is_empty .delete, .page.settings .section_newznab .ctrlHolder.is_empty .use { visibility: hidden; } - .page.settings .tab_about .usenet { + .page .tab_about .usenet { padding: 20px 30px 0; font-size: 17px; } - .page.settings .tab_about .usenet a { + .page .tab_about .usenet a { padding: 0 5px; } - .page.settings .tab_about .usenet ul { + .page .tab_about .usenet ul { float: left; width: 50%; margin: 10px 0; padding: 0; } - .page.settings .tab_about .usenet li { + .page .tab_about .usenet li { background: url('../../images/icon.check.png') no-repeat left center; padding: 0 0 0 25px; } - .page.settings .tab_about .donate { + .page .tab_about .donate { float: left; width: 42%; text-align: center; @@ -365,24 +515,24 @@ -moz-box-shadow: -1px 0 0 rgba(255,255,255, 0.15); -webkit-box-shadow: -1px 0 0 rgba(255,255,255, 0.15); } - .page.settings .tab_about .donate form { + .page .tab_about .donate form { padding: 10px 0 0; } - .page.settings .tab_about .info { + .page .tab_about .info { padding: 20px 30px; margin: 0; overflow: hidden; } - .page.settings .tab_about .info dt { + .page .tab_about .info dt { clear: both; float: left; width: 17%; font-weight: bold; } - .page.settings .tab_about .info dd { + .page .tab_about .info dd { float: right; width: 80%; padding: 0; @@ -390,12 +540,12 @@ font-style: italic; } - .page.settings .tab_about .group_actions > div { + .page .tab_about .group_actions > div { padding: 30px; text-align: center; } - .page.settings .tab_about .group_actions a { + .page .tab_about .group_actions a { margin: 0 10px; font-size: 20px; } \ No newline at end of file diff --git a/couchpotato/templates/_desktop.html b/couchpotato/templates/_desktop.html index 95fb1cd4..9943b6f3 100644 --- a/couchpotato/templates/_desktop.html +++ b/couchpotato/templates/_desktop.html @@ -28,17 +28,17 @@ - {% for url in fireEvent('clientscript.get_scripts', as_html = True, single = True) %} - {% endfor %} - {% for url in fireEvent('clientscript.get_styles', as_html = True, single = True) %} - {% endfor %} - + {% for url in fireEvent('clientscript.get_scripts', as_html = True, single = True) %} + {% endfor %} + {% for url in fireEvent('clientscript.get_styles', as_html = True, single = True) %} + {% endfor %} +