From ec453c59ae3f6828469d1bc9a15c0c813c8d5b55 Mon Sep 17 00:00:00 2001 From: Alex Hayes Date: Mon, 2 May 2011 16:32:05 +1000 Subject: [PATCH 01/55] Added support for TreeDropdownField to DataObjectManager. --- code/DataObjectManager.php | 3 ++- code/simple_html_editor_field/SimpleHTMLEditorField.php | 1 + 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/code/DataObjectManager.php b/code/DataObjectManager.php index e5fb79c..fc0882a 100644 --- a/code/DataObjectManager.php +++ b/code/DataObjectManager.php @@ -785,11 +785,12 @@ function __construct($controller, $name, $fields, $validator, $readonly, $dataOb $this->dataObject = $dataObject; Requirements::clear(); Requirements::clear_combined_files(); + // added prototype.js to provide support for TreeDropdownField + Requirements::javascript(THIRDPARTY_DIR.'/prototype/prototype.js'); Requirements::javascript(THIRDPARTY_DIR.'/jquery/jquery.js'); Requirements::javascript(THIRDPARTY_DIR.'/jquery-livequery/jquery.livequery.js'); Requirements::block(THIRDPARTY_DIR.'/behaviour.js'); Requirements::block(SAPPHIRE_DIR.'/javascript/Validator.js'); - Requirements::block(THIRDPARTY_DIR.'/prototype.js'); Requirements::clear(THIRDPARTY_DIR.'/behavior.js'); Requirements::block(THIRDPARTY_DIR.'/behavior.js'); Requirements::block(SAPPHIRE_DIR.'/javascript/ComplexTableField.js'); diff --git a/code/simple_html_editor_field/SimpleHTMLEditorField.php b/code/simple_html_editor_field/SimpleHTMLEditorField.php index 6d83962..d9323e0 100644 --- a/code/simple_html_editor_field/SimpleHTMLEditorField.php +++ b/code/simple_html_editor_field/SimpleHTMLEditorField.php @@ -72,6 +72,7 @@ private function getConfig() public function FieldHolder() { + Requirements::javascript(THIRDPARTY_DIR."/jquery/jquery.js"); Requirements::javascript('dataobject_manager/javascript/jquery.wysiwyg.js'); Requirements::css('dataobject_manager/css/jquery.wysiwyg.css'); Requirements::customScript(" From 23724ed1c125f2d482c0f05d5369754cfae11429 Mon Sep 17 00:00:00 2001 From: Simon Wade Date: Tue, 7 Jun 2011 08:49:07 +1000 Subject: [PATCH 02/55] Added new changes from patches/dataobject_manager-improvements.patch --- code/HasManyDataObjectManager.php | 45 ++++++++++++++++-------------- code/ManyManyDataObjectManager.php | 27 ++++++++++++++---- 2 files changed, 45 insertions(+), 27 deletions(-) diff --git a/code/HasManyDataObjectManager.php b/code/HasManyDataObjectManager.php index c91962d..a228f41 100644 --- a/code/HasManyDataObjectManager.php +++ b/code/HasManyDataObjectManager.php @@ -93,26 +93,13 @@ function sourceItems() { $dataQuery = $this->getQuery($limitClause); $records = $dataQuery->execute(); $items = new DataObjectSet(); + $class = $this->sourceClass; foreach($records as $record) { - if(! is_object($record)) - $class = $this->sourceClass; - $record = new $class($record); - $items->push($record); + $items->push(new $class($record)); } - $dataQuery = $this->getQuery(); - $records = $dataQuery->execute(); - $unpagedItems = new DataObjectSet(); - foreach($records as $record) { - if(! is_object($record)) { - $class = $this->sourceClass; - $record = new $class($record); - } - $unpagedItems->push($record); - } - $this->unpagedSourceItems = $unpagedItems; - - $this->totalCount = ($this->unpagedSourceItems) ? $this->unpagedSourceItems->TotalItems() : null; + // changed to avoid using $this->unpagedSourceItems because it fails on large datasets + $this->totalCount = $this->getQuery()->unlimitedRowCount(); return $items; } @@ -145,10 +132,8 @@ function saveInto(DataObject $record) { function ExtraData() { $items = array(); - foreach($this->unpagedSourceItems as $item) { - if($item->{$this->joinField} == $this->controller->ID) - $items[] = $item->ID; - } + // changed to avoid having to use $this->unpagedSourceItems because it fails on large datasets + $items = $this->getSelectedIDs(); $list = implode(',', $items); $value = ","; $value .= !empty($list) ? $list."," : ""; @@ -158,6 +143,24 @@ function ExtraData() { HTML; } + /** + * Returns the list of IDs that should be checked in the list. + * @see HasManyDataObjectManager::getSelectedIDs() + * @return array + */ + function getSelectedIDs() { + $ids = array(); + $dataQuery = $this->getQuery(); + $dataQuery->having("{$this->joinField} = '{$this->controller->ID}'"); + $records = $dataQuery->execute(); + $class = $this->sourceClass; + foreach($records as $record) { + $item = new $class($record); + $ids[] = $item->ID; + } + return $ids; + } + } diff --git a/code/ManyManyDataObjectManager.php b/code/ManyManyDataObjectManager.php index e28e9dc..d9f2246 100644 --- a/code/ManyManyDataObjectManager.php +++ b/code/ManyManyDataObjectManager.php @@ -185,10 +185,8 @@ function getParentIdName($parentClass, $childClass) { function ExtraData() { $items = array(); - foreach($this->unpagedSourceItems as $item) { - if($item->{$this->joinField}) - $items[] = $item->ID; - } + // changed to avoid having to use $this->unpagedSourceItems because it fails on large datasets + $items = $this->getSelectedIDs(); $list = implode(',', $items); $value = ","; $value .= !empty($list) ? $list."," : ""; @@ -199,8 +197,25 @@ function ExtraData() { HTML; } - - + + /** + * Returns the list of IDs that should be checked in the list. + * @see HasManyDataObjectManager::getSelectedIDs() + * @return array + */ + function getSelectedIDs() { + $ids = array(); + $dataQuery = $this->getQuery(); + $dataQuery->having("Checked = '1'"); + $records = $dataQuery->execute(); + $class = $this->sourceClass; + foreach($records as $record) { + $item = new $class($record); + $ids[] = $item->ID; + } + return $ids; + } + public function Sortable() { return ( From 4b19c44e8ffe87ac7f0347f67cd9a5efcb9f626f Mon Sep 17 00:00:00 2001 From: Daniel Hensby Date: Sat, 18 Jun 2011 13:25:16 -0700 Subject: [PATCH 03/55] Fixed the but where clicking the row doesn't actually result in saved change. --- javascript/dataobject_manager.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/javascript/dataobject_manager.js b/javascript/dataobject_manager.js index 3be785b..15c5e7a 100644 --- a/javascript/dataobject_manager.js +++ b/javascript/dataobject_manager.js @@ -166,10 +166,10 @@ $.fn.DataObjectManager.init = function(obj) { $container.find('ul:not(.ui-sortable) li.data').unbind('click').click(function(e) { var $this = $(this); if ($this.parent().hasClass('toggleSelect')) { - var $input = $this.find('input'); - if ($input.length) { - $input.click(); - } + var $input = $this.find('input'), + checker = !$input.attr('checked'); + //don't ask me wtf is going on here! + $input.attr('checked',checker).click().attr('checked',checker); } else { $this.find('a.popup-button:first').click(); From 6d271a0daead00c7cb10a95387359251ae283c99 Mon Sep 17 00:00:00 2001 From: Aaron Carlino Date: Wed, 20 Jul 2011 11:31:37 -0400 Subject: [PATCH 04/55] MINOR: allows overriding of duplicating files when imported to FDOM --- code/FileDataObjectManager.php | 6 +++--- dataobject_manager | 1 + 2 files changed, 4 insertions(+), 3 deletions(-) create mode 120000 dataobject_manager diff --git a/code/FileDataObjectManager.php b/code/FileDataObjectManager.php index 823ea6c..dda1805 100644 --- a/code/FileDataObjectManager.php +++ b/code/FileDataObjectManager.php @@ -43,6 +43,8 @@ class FileDataObjectManager extends DataObjectManager public $uploadifyField = "MultipleFileUploadField"; + public $copyOnImport = true; + public function __construct($controller, $name = null, $sourceClass = null, $fileFieldName = null, $fieldList = null, $detailFormFields = null, $sourceFilter = "", $sourceSort = "", $sourceJoin = "") { if(!class_exists("SWFUploadField") && !class_exists("UploadifyField")) @@ -425,7 +427,7 @@ public function saveUploadifyForm($data, $form) if($file = DataObject::get_by_id("File", (int) $id)) { $upload_folder = $form->Fields()->fieldByName('UploadedFiles')->uploadFolder; $folder_id = Folder::findOrMake($upload_folder)->ID; - if($file->ParentID != $folder_id) { + if($this->copyOnImport && ($file->ParentID != $folder_id)) { $new_file_path = $this->uploadFolder.'/'.$file->Name; copy($file->getFullPath(), BASE_PATH.'/'.ASSETS_DIR.'/'.$new_file_path); $clone = new $file_class(); @@ -851,5 +853,3 @@ function __construct($controller, $name, $fields, $validator, $readonly, $dataOb } } - -?> diff --git a/dataobject_manager b/dataobject_manager new file mode 120000 index 0000000..40c0832 --- /dev/null +++ b/dataobject_manager @@ -0,0 +1 @@ +dataobject_manager \ No newline at end of file From 5aed67c6f6139260a7ba17ac487f0608479925ef Mon Sep 17 00:00:00 2001 From: Aaron Carlino Date: Thu, 21 Jul 2011 12:14:44 -0400 Subject: [PATCH 05/55] MINOR: Removed CroppedImage() function from thumbnail. Send to video as-is --- code/flv/FLV.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/flv/FLV.php b/code/flv/FLV.php index 7aca3fa..286e851 100644 --- a/code/flv/FLV.php +++ b/code/flv/FLV.php @@ -244,7 +244,7 @@ public function Player($width = null, $height = null) { if($width === null) $width = self::$video_width; if($height === null) $height = self::$video_height; - $image = ($thumb = $this->VideoThumbnail()) ? $thumb->CroppedImage($width,$height)->URL : ""; + $image = ($thumb = $this->VideoThumbnail()) ? $thumb->URL : ""; self::$player_count++; Requirements::javascript('dataobject_manager/code/flv/swfobject.js'); Requirements::customScript(sprintf( From 0047ea66ddf78d86dc8dbd784d36a1bbb1d559d5 Mon Sep 17 00:00:00 2001 From: mattclegg Date: Sun, 24 Jul 2011 02:21:28 -0700 Subject: [PATCH 06/55] $this->uploadFolder seems to return the same path as in $file->getFullPath() when using ImageDataObjectManager for existing files. Changing $new_file_path to $upload_folder means the path can be overridden in the requested form -and ImageDataObjectManager works as expected from existing files (by copying them and creating a new object) --- code/FileDataObjectManager.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/FileDataObjectManager.php b/code/FileDataObjectManager.php index dda1805..de1c08f 100644 --- a/code/FileDataObjectManager.php +++ b/code/FileDataObjectManager.php @@ -428,7 +428,7 @@ public function saveUploadifyForm($data, $form) $upload_folder = $form->Fields()->fieldByName('UploadedFiles')->uploadFolder; $folder_id = Folder::findOrMake($upload_folder)->ID; if($this->copyOnImport && ($file->ParentID != $folder_id)) { - $new_file_path = $this->uploadFolder.'/'.$file->Name; + $new_file_path = $upload_folder.'/'.$file->Name; copy($file->getFullPath(), BASE_PATH.'/'.ASSETS_DIR.'/'.$new_file_path); $clone = new $file_class(); $clone->Filename = $new_file_path; From ae98d3ac4fb19d88108b53c90003aec4b7381250 Mon Sep 17 00:00:00 2001 From: Aaron Carlino Date: Wed, 27 Jul 2011 10:28:25 -0400 Subject: [PATCH 07/55] BUGFIX: HasManyDOM, ManyManyManyDOM include foreign fields in select query, but that should be ignored if the field refers to a has_one relation --- code/HasManyDataObjectManager.php | 2 +- code/ManyManyDataObjectManager.php | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/code/HasManyDataObjectManager.php b/code/HasManyDataObjectManager.php index c91962d..9b21320 100644 --- a/code/HasManyDataObjectManager.php +++ b/code/HasManyDataObjectManager.php @@ -73,7 +73,7 @@ function getQuery($limitClause = null) { $SNG = singleton($this->sourceClass); foreach($this->FieldList() as $k => $title) { - if(! $SNG->hasField($k) && ! $SNG->hasMethod('get' . $k)) + if(! $SNG->hasField($k) && ! $SNG->hasMethod('get' . $k) && ! $SNG->has_one($k)) $query->select[] = $k; } } diff --git a/code/ManyManyDataObjectManager.php b/code/ManyManyDataObjectManager.php index aa7c7d2..44d6951 100644 --- a/code/ManyManyDataObjectManager.php +++ b/code/ManyManyDataObjectManager.php @@ -150,7 +150,7 @@ function getQuery($limitClause = null) { $SNG = singleton($this->sourceClass); foreach($this->FieldList() as $k => $title) { - if(! $SNG->hasField($k) && ! $SNG->hasMethod('get' . $k)) { + if(! $SNG->hasField($k) && ! $SNG->hasMethod('get' . $k) && ! $SNG->has_one($k)) { // everything we add to select must be added to groupby too... $query->select[] = $k; $query->groupby[] = $k; From 1d457313d6939b1283fb60154fa23662589f3f7d Mon Sep 17 00:00:00 2001 From: Aaron Carlino Date: Tue, 9 Aug 2011 09:43:26 -0400 Subject: [PATCH 08/55] ENHANCEMENT: Drag and drop files to folders in AssetAmin --- css/dataobject_manager.css | 9 +- javascript/dataobject_manager.js | 151 +++++++++++++++-------------- templates/FileDataObjectManager.ss | 17 +++- 3 files changed, 95 insertions(+), 82 deletions(-) diff --git a/css/dataobject_manager.css b/css/dataobject_manager.css index 8ffa634..4e1ae57 100644 --- a/css/dataobject_manager.css +++ b/css/dataobject_manager.css @@ -9,7 +9,7 @@ .list .dataobject-list li div.pad {font-size:12px;padding:0 3px;float:none;} .list .dataobject-list li div {float:left;} -.list .dataobject-list div.actions.col {width:9%;float:right;text-align:right;border:0;position:relative;} +.list .dataobject-list div.actions.col {width:8%;float:right;text-align:right;border:0;position:relative;} .list .dataobject-list div.actions.col a {visibility:hidden;display:inline;margin:0 5px;} .list .dataobject-list div.actions.col input {border:0;padding:0;margin:0;background:none;} .list .dataobject-list li.head {font-weight:bold;font-size:12px;background:url(../images/heading_bg.gif) repeat-x top left;} @@ -20,6 +20,8 @@ .list .dataobject-list li.head a:hover {background:none;} .list .dataobject-list li {width:98.9%;overflow:hidden;border-bottom:1px solid #e4e4e4;padding:4px 5px;text-align:left;font-size:12px;} .list .dataobject-list li .fields-wrap {width:90%;float:left;} +.list .dataobject-list li .drag-pointer {float:left; width:1%;} +.list .dataobject-list li.data {line-height:25px;} .list .dataobject-list li .fields-wrap .col li {width:auto;border:0;padding:0;} .ui-sortable li {cursor:move;} @@ -36,6 +38,7 @@ .grid .dataobject-list li:hover {background:#feffe0;} .grid .dataobject-list li:hover .delete a {display:inline;visibility:visible;} .grid .dataobject-list li div.pad {padding:8px 10px;} +.grid .dataobject-list li .drag-pointer {float:left;} #tooltip {max-width:300px;position: absolute;z-index: 3000;border: 1px solid #111;background-color: #eee;padding: 5px;opacity: 0.85;} @@ -54,9 +57,9 @@ .dataobjectmanager-actions {width:55%;float:left;height:35px;} .dataobjectmanager-actions.filter {padding-top:2em;height:auto;} .dataobjectmanager-actions a {background: transparent url('../images/bg_button_a.gif') no-repeat scroll top right;display: block;float: left;height: 24px;margin-right: 6px;padding-right: 13px;text-decoration: none;color: #333;font-size:13px;font-weight:bold;cursor:pointer;} -.dataobjectmanager-actions a span {background: transparent url('../images/bg_button_span.gif') no-repeat;display: block;line-height: 22px;padding: 2px 0 5px 10px;font-size:12px;height:17px;} +.dataobjectmanager-actions a span {background: transparent url('../images/bg_button_span.gif') no-repeat;display: block;line-height: 22px;padding: 2px 0 5px 10px;font-size:12px;height:17px;} .dataobjectmanager-actions a:active {background: transparent url('../images/bg_button_a.gif') no-repeat scroll right -24px;;display: block;float: left;height: 24px;margin-right: 6px;padding-right: 13px;text-decoration: none;color: #333;font-size:13px;font-weight:bold;} -.dataobjectmanager-actions a:active span {background: transparent url('../images/bg_button_span.gif') no-repeat left -24px;display: block;line-height: 22px;padding: 2px 0 5px 10px;font-size:12px;height:17px;} +.dataobjectmanager-actions a:active span {background: transparent url('../images/bg_button_span.gif') no-repeat left -24px;display: block;line-height: 22px;padding: 2px 0 5px 10px;font-size:12px;height:17px;} .AssetAdmin .dataobjectmanager-actions {margin-top:20px;height:25px;} .dataobjectmanager-actions a img {vertical-align:-3px;margin-right:3px;} .dataobjectmanager-search {width:160px;position:absolute;right:6px;top:7px;} diff --git a/javascript/dataobject_manager.js b/javascript/dataobject_manager.js index e2f4b76..3aee8cd 100644 --- a/javascript/dataobject_manager.js +++ b/javascript/dataobject_manager.js @@ -13,19 +13,19 @@ $.fn.DataObjectManager.init = function(obj) { var container_id = '#'+$container.attr('id'); var nested = $('.DataObjectManager').hasClass('isNested'); if(!i18n_js) - i18n_js = $.fn.DataObjectManager.loadi18n(); - - var facebox_close = function() { + i18n_js = $.fn.DataObjectManager.loadi18n(); + + var facebox_close = function() { $('#facebox').fadeOut(function() { $('#facebox .content').removeClass().addClass('content'); $('#facebox_overlay').remove(); $('#facebox .loading').remove(); - refresh($container, $container.attr('href')); + refresh($container, $container.attr('href')); }) }; - + // Popup links - + // For Nested DOMs if(nested) { $('body').append( @@ -59,7 +59,7 @@ $.fn.DataObjectManager.init = function(obj) { e.stopPropagation(); return false; }); - $container.addClass("loaded"); + $container.addClass("loaded"); } // For normal DOMs else { @@ -96,7 +96,7 @@ $.fn.DataObjectManager.init = function(obj) { }); $div.fadeIn("slow"); $div.find('.yes').click(function(e) { - $.post($target.attr('href'),params,function() {$($target).parents('li:first').fadeOut();$(".ajax-loader").fadeOut("fast");}); + $.post($target.attr('href'),params,function() {$($target).parents('li:first').fadeOut();$(".ajax-loader").fadeOut("fast");}); e.stopPropagation(); return false; }); @@ -114,9 +114,9 @@ $.fn.DataObjectManager.init = function(obj) { } return false; }); - + // Refresh - + $container.find('a.refresh-button').unbind('click').click(function(e) { $t = $(this); $.post($t.attr('href'),{},function() { @@ -124,19 +124,19 @@ $.fn.DataObjectManager.init = function(obj) { }); return false; }); - + $container.find('a.window-link').unbind('click').click(function(e) { $(this).attr('target','_blank'); e.stopPropagation(); }); - + // Pagination $container.find('.Pagination a').unbind('click').click(function() { refresh($container, $(this).attr('href')); return false; }); - + // View if($container.hasClass('FileDataObjectManager') && !$container.hasClass('ImageDataObjectManager')) { $container.find('a.viewbutton').unbind('click').click(function() { @@ -144,8 +144,8 @@ $.fn.DataObjectManager.init = function(obj) { return false; }); } - - + + // Sortable $container.find('.sort-control input').unbind('click').click(function(e) { @@ -166,7 +166,7 @@ $.fn.DataObjectManager.init = function(obj) { tolerance : 'intersect', handle : ($('.list-holder').hasClass('grid') ? '.handle' : null) }); - + // Click function for the LI $container.find('ul:not(.ui-sortable) li.data').unbind('click').click(function(e) { var $this = $(this); @@ -181,8 +181,8 @@ $.fn.DataObjectManager.init = function(obj) { } e.stopPropagation(); }).css({'cursor' : 'pointer'}); - - + + // Column sort if(!$container.hasClass('ImageDataObjectManager')) { $container.find('li.head a').unbind('click').click(function() { @@ -190,7 +190,7 @@ $.fn.DataObjectManager.init = function(obj) { return false; }); } - + // Filter $container.find('.dataobjectmanager-filter select').unbind('change').change(function(e) { refresh($container, $(this).attr('value')); @@ -201,14 +201,14 @@ $.fn.DataObjectManager.init = function(obj) { refresh($container, $(this).attr('value')); }); - + // Refresh filter $container.find('.dataobjectmanager-filter .refresh').unbind('click').click(function(e) { refresh($container, $container.attr('href')); e.stopPropagation(); return false; }) - + // Search var request = false; $container.find('.srch_fld').focus(function() { @@ -216,34 +216,32 @@ $.fn.DataObjectManager.init = function(obj) { }).unbind('blur').blur(function() { if($(this).attr('value') == '') $(this).attr('value','Search').css({'color' : '#666'}); }).unbind('keyup').keyup(function(e) { - if(e.keyCode == 13) {e.preventDefault();e.stopPropagation();return false;} - - if ((e.keyCode == 9) || // tab - (e.keyCode == 16) || (e.keyCode == 17) || // shift, ctl + if ((e.keyCode == 9) || (e.keyCode == 13) || // tab, enter + (e.keyCode == 16) || (e.keyCode == 17) || // shift, ctl (e.keyCode >= 18 && e.keyCode <= 20) || // alt, pause/break, caps lock - (e.keyCode == 27) || // esc - (e.keyCode >= 33 && e.keyCode <= 35) || // page up, page down, end - (e.keyCode >= 36 && e.keyCode <= 38) || // home, left, up - (e.keyCode == 40) || // down + (e.keyCode == 27) || // esc + (e.keyCode >= 33 && e.keyCode <= 35) || // page up, page down, end + (e.keyCode >= 36 && e.keyCode <= 38) || // home, left, up + (e.keyCode == 40) || // down (e.keyCode >= 36 && e.keyCode <= 40) || // home, left, up, right, down - (e.keyCode >= 44 && e.keyCode <= 45) || // print screen, insert - (e.keyCode == 229) // Korean XP fires 2 keyup events, the key and 229 - ) return; - + (e.keyCode >= 44 && e.keyCode <= 45) || // print screen, insert + (e.keyCode == 229) // Korean XP fires 2 keyup events, the key and 229 + ) return; + if(request) window.clearTimeout(request); $input = $(this); request = window.setTimeout(function() { url = $(container_id).attr('href').replace(/\[search\]=(.)*?&/, '[search]='+$input.attr('value')+'&'); - refresh($container, url, '.srch_fld'); - + refresh($container, url, '.srch_fld'); + },1000) e.stopPropagation(); }); - + $container.find('.srch_clear').unbind('click').click(function() { $container.find('.srch_fld').attr('value','').keyup(); }); - + $container.find('a.tooltip').tooltip({ delay: 500, @@ -253,8 +251,8 @@ $.fn.DataObjectManager.init = function(obj) { return $(this).parents('li').find('span.tooltip-info').html(); } }); - - + + // Add the slider to the ImageDataObjectManager if($container.hasClass('ImageDataObjectManager')) { var MIN_IMG_SIZE = 25 @@ -262,7 +260,7 @@ $.fn.DataObjectManager.init = function(obj) { var START_IMG_SIZE = 100; var new_image_size; $('.size-control').slider({ - + // Stupid thing doesn't work. Have to force it with CSS startValue : (START_IMG_SIZE - MIN_IMG_SIZE) / ((MAX_IMG_SIZE - MIN_IMG_SIZE) / 100), slide : function(e, ui) { @@ -270,19 +268,19 @@ $.fn.DataObjectManager.init = function(obj) { $('.grid li img.image').css({'width': new_image_size+'px'}); $('.grid li').css({'width': new_image_size+'px', 'height' : new_image_size +'px'}); }, - + stop : function(e, ui) { - new_image_size = MIN_IMG_SIZE + (ui.value * ((MAX_IMG_SIZE - MIN_IMG_SIZE)/100)); + new_image_size = MIN_IMG_SIZE + (ui.value * ((MAX_IMG_SIZE - MIN_IMG_SIZE)/100)); url = $(container_id).attr('href').replace(/\[imagesize\]=(.)*/, '[imagesize]='+Math.floor(new_image_size)); refresh($container, url); } }); - - $('.ui-slider-handle').css({'left' : $('#size-control-wrap').attr('class').replace('position','')+'px'}); - - } + + $('.ui-slider-handle').css({'left' : $('#size-control-wrap').attr('class').replace('position','')+'px'}); + + } // RelationDataObjectManager - + if($container.hasClass('RelationDataObjectManager')) { var $checkedList = $(container_id+'_CheckedList'); $container.find('.actions input, .file-label input').unbind('click').click(function(e){ @@ -298,39 +296,39 @@ $.fn.DataObjectManager.init = function(obj) { } e.stopPropagation(); }); - + $container.find('.actions input, .file-label input').each(function(i,e) { if($checkedList.val().indexOf(","+$(e).val()+",") != -1) $(e).attr('checked',true).parents('li').addClass('selected'); else $(e).attr('checked',false).parents('li').removeClass('selected'); - - }); - + + }); + $container.find('a[rel=clear]').unbind('click').click(function(e) { $container.find('.actions input, .file-label input').each(function(i,e) { $(e).attr('checked', false).parents('li').removeClass('selected'); $checkedList.attr('value',''); }); }); - + $container.find('.only-related-control input').unbind('click').click(function(e) { refresh($container, $(this).attr('value')); $(this).attr('disabled', true); e.stopPropagation(); }); - + } - + // Columns. God forbid there are more than 10. cols = $('.list #dataobject-list li.head .fields-wrap .col').length; if(cols > 10) { $('.list #dataobject-list li .fields-wrap .col').css({'width' : ((Math.floor(100/cols)) - 0.1) + '%' }); } - - - $(".ajax-loader").fadeOut("fast"); - + + + $(".ajax-loader").fadeOut("fast"); + }; $.fn.DataObjectManager.getPageHeight = function() { @@ -341,7 +339,7 @@ $.fn.DataObjectManager.getPageHeight = function() { windowHeight = document.documentElement.clientHeight; } else if (document.body) { // other Explorers windowHeight = document.body.clientHeight; - } + } return windowHeight; }; @@ -355,9 +353,9 @@ $.fn.DataObjectManager.getPageScroll = function() { xScroll = document.documentElement.scrollLeft; } else if (document.body) {// all other Explorers yScroll = document.body.scrollTop; - xScroll = document.body.scrollLeft; + xScroll = document.body.scrollLeft; } - return new Array(xScroll,yScroll) + return new Array(xScroll,yScroll) }; $.fn.DataObjectManager.loadi18n = function() { @@ -377,17 +375,17 @@ $.fn.DataObjectManager.loadi18n = function() { -$('.DataObjectManager').ajaxSend(function(e,r,s){ +$('.DataObjectManager').ajaxSend(function(e,r,s){ // stupid hack for the cache killer script. if(s.url.indexOf('EditorToolbar') == -1) - $(".ajax-loader").show(); -}); - -$('.DataObjectManager').ajaxStop(function(e,r,s){ - $(".ajax-loader").fadeOut("fast"); -}); + $(".ajax-loader").show(); +}); + +$('.DataObjectManager').ajaxStop(function(e,r,s){ + $(".ajax-loader").fadeOut("fast"); +}); $('.DataObjectManager').livequery(function(){ - $(this).DataObjectManager(); + $(this).DataObjectManager(); }); @@ -398,7 +396,7 @@ function refresh($div, link, focus) { // Kind of a hack. Pass the list of ids to the next refresh var listValue = ($div.hasClass('RelationDataObjectManager')) ? jQuery('#'+$div.attr('id')+'_CheckedList').val() : false; - + jQuery.ajax({ type: "GET", url: link, @@ -407,17 +405,20 @@ function refresh($div, link, focus) $div.parent().html(html); else $div.replaceWith(html); - + if(listValue) { jQuery('#'+$div.attr('id')+'_CheckedList').attr('value',listValue); } - var $container = jQuery('#'+$div.attr('id')); - $container.DataObjectManager(); - if (typeof focus == 'string') { + var $container = jQuery('#'+$div.attr('id')); + $container.DataObjectManager(); + if (typeof focus == 'string') { $target = $container.find(focus); $target.focus().val($target.val()); - } + } //jQuery('#'+$div.attr('id')).DataObjectManager(); + //Init drag function + TableListField.applyTo('div.TableListField'); + DragFileItem.applyTo('#Form_EditForm_Files tr td.dragfile'); } }); } diff --git a/templates/FileDataObjectManager.ss b/templates/FileDataObjectManager.ss index 2e00721..090ade1 100644 --- a/templates/FileDataObjectManager.ss +++ b/templates/FileDataObjectManager.ss @@ -1,4 +1,4 @@ -
+
<% if Can(add) %> @@ -72,6 +72,15 @@ <% if Items %> <% control Items %>
  • + + + + + +
    + +
    + <% if Top.ListView %>
    @@ -101,9 +110,9 @@ <% else %>
  • <% sprintf(_t('DataObjectManager.NOITEMSFOUND','No %s found'),$PluralTitle) %>
  • <% end_if %> - + -
    +
    @@ -116,7 +125,7 @@
    <% if ShowAll %><% else %>$PerPageDropdown<% end_if %>
    - +
    From dc7bb4e623e12219ab0a5e823c7dcfdcb673b797 Mon Sep 17 00:00:00 2001 From: Aaron Carlino Date: Tue, 9 Aug 2011 13:23:53 -0400 Subject: [PATCH 09/55] BUGFIX: remove symlink --- dataobject_manager | 1 - 1 file changed, 1 deletion(-) delete mode 120000 dataobject_manager diff --git a/dataobject_manager b/dataobject_manager deleted file mode 120000 index 40c0832..0000000 --- a/dataobject_manager +++ /dev/null @@ -1 +0,0 @@ -dataobject_manager \ No newline at end of file From 815c494f253925216e27e9948ee3621fe396e699 Mon Sep 17 00:00:00 2001 From: drzax Date: Sat, 27 Aug 2011 11:35:34 +1000 Subject: [PATCH 10/55] An additional check to see if the given class is sortable. This whole function can probably be re-written and/or removed/depreciated in favour of checking directly with the Object::has_extension() function. --- code/SortableDataObject.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/SortableDataObject.php b/code/SortableDataObject.php index 1a6d506..3e3cab1 100644 --- a/code/SortableDataObject.php +++ b/code/SortableDataObject.php @@ -65,7 +65,7 @@ public static function is_sortable_class($classname) if(is_subclass_of($classname, $class)) return true; } - return false; + return Object::has_extension($classname, 'SortableDataObject'); } From f2836e49d4d0ede4175463d0477278ff2ff0bcf9 Mon Sep 17 00:00:00 2001 From: drzax Date: Sat, 27 Aug 2011 11:25:37 +1000 Subject: [PATCH 11/55] Test if the DataObject being managed is sortable in a different (probably more accurate) way. Minimally tested. Needs a look over by someone who knows the code better than I do. Fixes #19 --- code/DataObjectManager.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/DataObjectManager.php b/code/DataObjectManager.php index 3daa601..a5a6584 100644 --- a/code/DataObjectManager.php +++ b/code/DataObjectManager.php @@ -489,7 +489,7 @@ public function Paginated() public function Sortable() { - return SortableDataObject::is_sortable_class($this->sourceClass()); + return DataObject::has_extension($this->sourceClass(), 'SortableDataObject'); } public function setFilter($field, $label, $map, $default = null) From b28d86fc05867d7f92776c40a7173c342f68f615 Mon Sep 17 00:00:00 2001 From: s-m Date: Fri, 26 Aug 2011 20:13:09 +0200 Subject: [PATCH 12/55] Update for dataobject_manager.js: Shows newly created items as checked, code copied from silverstripe forum... --- javascript/dataobject_manager.js | 45 ++++++++++++++++++++++++-------- 1 file changed, 34 insertions(+), 11 deletions(-) diff --git a/javascript/dataobject_manager.js b/javascript/dataobject_manager.js index 5521a64..0e0d8a5 100644 --- a/javascript/dataobject_manager.js +++ b/javascript/dataobject_manager.js @@ -391,24 +391,47 @@ $('.DataObjectManager').livequery(function(){ })(jQuery); - function refresh($div, link, focus) { // Kind of a hack. Pass the list of ids to the next refresh var listValue = ($div.hasClass('RelationDataObjectManager')) ? jQuery('#'+$div.attr('id')+'_CheckedList').val() : false; - jQuery.ajax({ - type: "GET", - url: link, - success: function(html){ - if(!$div.next().length && !$div.prev().length) - $div.parent().html(html); - else - $div.replaceWith(html); + // Make a list of all ids so we can detect newly created ones + var all = ','; + $div.find('li.data input:checkbox').each(function(i, el) { + all += el.value + ','; + }); + jQuery.ajax({ + type : "GET", + url : link, + success : function(html) { + if (!$div.next().length && !$div.prev().length) + $div.parent().html(html); + else + $div.replaceWith(html); + if(listValue) { jQuery('#'+$div.attr('id')+'_CheckedList').attr('value',listValue); - } + // Add newly created items in if checked + jQuery(html).find('li.data input:checkbox') + .each( + function(i, el) { + el = jQuery(el); + if (el.attr('checked') + && jQuery.inArray(el.val(), all + .split(',')) == -1) { + jQuery( + '#' + $div.attr('id') + + '_CheckedList').val( + jQuery( + '#' + $div.attr('id') + + '_CheckedList') + .val() + + el.val() + ','); + } + }); + var $container = jQuery('#'+$div.attr('id')); $container.DataObjectManager(); if (typeof focus == 'string') { @@ -420,5 +443,5 @@ function refresh($div, link, focus) TableListField.applyTo('div.TableListField'); DragFileItem.applyTo('#Form_EditForm_Files tr td.dragfile'); } - }); + }); } From caca69d321d44e50efc72a56c83a79032f6b1e53 Mon Sep 17 00:00:00 2001 From: s-m Date: Fri, 26 Aug 2011 20:19:50 +0200 Subject: [PATCH 13/55] Missing }... --- javascript/dataobject_manager.js | 1 + 1 file changed, 1 insertion(+) diff --git a/javascript/dataobject_manager.js b/javascript/dataobject_manager.js index 0e0d8a5..4f622dd 100644 --- a/javascript/dataobject_manager.js +++ b/javascript/dataobject_manager.js @@ -413,6 +413,7 @@ function refresh($div, link, focus) if(listValue) { jQuery('#'+$div.attr('id')+'_CheckedList').attr('value',listValue); + } // Add newly created items in if checked jQuery(html).find('li.data input:checkbox') .each( From 102a11848abac59ffb0c93e28c51c54d701336ec Mon Sep 17 00:00:00 2001 From: s-m Date: Fri, 26 Aug 2011 20:22:00 +0200 Subject: [PATCH 14/55] Made string translatable... --- templates/DataObjectManager_holder.ss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/templates/DataObjectManager_holder.ss b/templates/DataObjectManager_holder.ss index 1eb0301..5a1fd02 100644 --- a/templates/DataObjectManager_holder.ss +++ b/templates/DataObjectManager_holder.ss @@ -1,4 +1,4 @@

    $PluralTitle

    -

    You may add $PluralTitle once you have saved for the first time.

    +

    <% sprintf(_t('ADDAFTERSAVE','You may add %s once you have saved for the first time.'),$PluralTitle) %>

    \ No newline at end of file From afce9669462a3b9956414018af13615da10282e9 Mon Sep 17 00:00:00 2001 From: Aaron Carlino Date: Tue, 6 Sep 2011 16:32:58 -0400 Subject: [PATCH 15/55] new swfobject version --- javascript/swfobject.js | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/javascript/swfobject.js b/javascript/swfobject.js index c383123..8eafe9d 100644 --- a/javascript/swfobject.js +++ b/javascript/swfobject.js @@ -1,5 +1,4 @@ -/* SWFObject v2.0 - Copyright (c) 2007 Geoff Stearns, Michael Williams, and Bobby van der Sluis - This software is released under the MIT License +/* SWFObject v2.2 + is released under the MIT License */ -var swfobject=function(){var Z="undefined",P="object",B="Shockwave Flash",h="ShockwaveFlash.ShockwaveFlash",W="application/x-shockwave-flash",K="SWFObjectExprInst",G=window,g=document,N=navigator,f=[],H=[],Q=null,L=null,T=null,S=false,C=false;var a=function(){var l=typeof g.getElementById!=Z&&typeof g.getElementsByTagName!=Z&&typeof g.createElement!=Z&&typeof g.appendChild!=Z&&typeof g.replaceChild!=Z&&typeof g.removeChild!=Z&&typeof g.cloneNode!=Z,t=[0,0,0],n=null;if(typeof N.plugins!=Z&&typeof N.plugins[B]==P){n=N.plugins[B].description;if(n){n=n.replace(/^.*\s+(\S+\s+\S+$)/,"$1");t[0]=parseInt(n.replace(/^(.*)\..*$/,"$1"),10);t[1]=parseInt(n.replace(/^.*\.(.*)\s.*$/,"$1"),10);t[2]=/r/.test(n)?parseInt(n.replace(/^.*r(.*)$/,"$1"),10):0}}else{if(typeof G.ActiveXObject!=Z){var o=null,s=false;try{o=new ActiveXObject(h+".7")}catch(k){try{o=new ActiveXObject(h+".6");t=[6,0,21];o.AllowScriptAccess="always"}catch(k){if(t[0]==6){s=true}}if(!s){try{o=new ActiveXObject(h)}catch(k){}}}if(!s&&o){try{n=o.GetVariable("$version");if(n){n=n.split(" ")[1].split(",");t=[parseInt(n[0],10),parseInt(n[1],10),parseInt(n[2],10)]}}catch(k){}}}}var v=N.userAgent.toLowerCase(),j=N.platform.toLowerCase(),r=/webkit/.test(v)?parseFloat(v.replace(/^.*webkit\/(\d+(\.\d+)?).*$/,"$1")):false,i=false,q=j?/win/.test(j):/win/.test(v),m=j?/mac/.test(j):/mac/.test(v);/*@cc_on i=true;@if(@_win32)q=true;@elif(@_mac)m=true;@end@*/return{w3cdom:l,pv:t,webkit:r,ie:i,win:q,mac:m}}();var e=function(){if(!a.w3cdom){return }J(I);if(a.ie&&a.win){try{g.write("