Commit a75d502a authored by Richard Mansfield's avatar Richard Mansfield
Browse files

Initial commit for non-js my/group/institution/site files sections

parent 1b4698b4
......@@ -35,17 +35,21 @@ require(dirname(dirname(dirname(__FILE__))) . '/init.php');
safe_require('artefact', 'file');
define('TITLE', get_string('sitefiles', 'admin'));
$javascript = ArtefactTypeFileBase::get_my_files_js(param_integer('folder', null));
$javascript .= <<<JS
browser.source += '?institution=mahara';
browser.createfolderscript += '?institution=mahara';
uploader.uploadscript += '?institution=mahara';
JS;
$folder = param_integer('folder', 0);
$edit = param_integer('edit', 0);
$highlight = null;
if ($file = param_integer('file', 0)) {
$highlight = array($file); // todo convert to file1=1&file2=2 etc
}
$form = pieform(files_form(null, 'mahara', $folder, $highlight, $edit));
$js = files_js();
$smarty = smarty(array('tablerenderer', 'artefact/file/js/file.js'));
$smarty->assign('INLINEJAVASCRIPT', $javascript);
$smarty = smarty();
$smarty->assign('descriptionstrargs', array('<a href="' . get_config('wwwroot') . 'admin/site/menu.php">', '</a>'));
$smarty->assign('heading', get_string('sitefiles', 'admin'));
$smarty->display('admin/site/files.tpl');
$smarty->assign('institution', 'mahara');
$smarty->assign('form', $form);
$smarty->assign('INLINEJAVASCRIPT', $js);
$smarty->display('artefact:file:files.tpl');
?>
This diff is collapsed.
......@@ -31,8 +31,6 @@ require(dirname(dirname(dirname(__FILE__))) . '/init.php');
require_once(get_config('libroot') . 'group.php');
safe_require('artefact', 'file');
$javascript = ArtefactTypeFileBase::get_my_files_js(param_integer('folder', null));
define('GROUP', param_integer('group'));
$group = group_current_group();
......@@ -43,24 +41,19 @@ define('TITLE', $group->name . ' - ' . get_string('groupfiles', 'artefact.file')
require_once(get_config('docroot') . 'interaction/lib.php');
$groupdata = json_encode($group);
$grouproles = json_encode(array_values(group_get_role_info($group->id)));
$defaultperms = group_get_default_artefact_permissions($group->id);
// By default, users can edit files they upload themselves
$defaultperms[$role] = (object) array('view' => true, 'edit' => true, 'republish' => true);
$grouprolepermissions = json_encode($defaultperms);
$javascript .= <<<GROUPJS
var group = {$groupdata};
group.roles = {$grouproles};
group.rolepermissions = {$grouprolepermissions};
browser.setgroup({$group->id});
uploader.setgroup({$group->id});
GROUPJS;
$folder = param_integer('folder', 0);
$edit = param_integer('edit', 0);
$highlight = null;
if ($file = param_integer('file', 0)) {
$highlight = array($file); // todo convert to file1=1&file2=2 etc
}
$form = pieform(files_form($group->id, null, $folder, $highlight, $edit));
$js = files_js();
$smarty = smarty(array('tablerenderer', 'artefact/file/js/file.js'));
$smarty = smarty();
$smarty->assign('heading', $group->name);
$smarty->assign('INLINEJAVASCRIPT', $javascript);
$smarty->display('artefact:file:index.tpl');
$smarty->assign('form', $form);
$smarty->assign('INLINEJAVASCRIPT', $js);
$smarty->display('artefact:file:files.tpl');
?>
......@@ -34,15 +34,17 @@ require(dirname(dirname(dirname(__FILE__))) . '/init.php');
define('TITLE', get_string('myfiles', 'artefact.file'));
safe_require('artefact', 'file');
$folder = param_integer('folder', 0);
$edit = param_integer('edit', 0);
$highlight = null;
if ($file = param_integer('file', 0)) {
$highlight = array($file); // todo convert to file1=1&file2=2 etc
}
$javascript = ArtefactTypeFileBase::get_my_files_js(param_integer('folder', null), $highlight);
$form = pieform(files_form(null, null, $folder, $highlight, $edit));
$js = files_js();
$smarty = smarty(
array('tablerenderer', 'artefact/file/js/file.js'),
array(),
array(),
array(),
array(
......@@ -55,8 +57,10 @@ $smarty = smarty(
),
)
);
$smarty->assign('heading', get_string('myfiles', 'artefact.file'));
$smarty->assign('INLINEJAVASCRIPT', $javascript);
$smarty->display('artefact:file:index.tpl');
$smarty->assign('form', $form);
$smarty->assign('INLINEJAVASCRIPT', $js);
$smarty->display('artefact:file:files.tpl');
?>
......@@ -33,7 +33,7 @@ define('SECTION_PAGE', 'institutionfiles');
require(dirname(dirname(dirname(__FILE__))) . '/init.php');
safe_require('artefact', 'file');
require_once('institution.php');
require_once(get_config('libroot') . 'institution.php');
$institution = param_alphanum('institution', false);
......@@ -43,7 +43,18 @@ $s = institution_selector_for_page($institution,
get_config('wwwroot') . 'artefact/file/institutionfiles.php');
$institution = $s['institution'];
$smarty = smarty(array('tablerenderer', 'artefact/file/js/file.js'));
$folder = param_integer('folder', 0);
$edit = param_integer('edit', 0);
$highlight = null;
if ($file = param_integer('file', 0)) {
$highlight = array($file); // todo convert to file1=1&file2=2 etc
}
$form = pieform(files_form(null, $institution, $folder, $highlight, $edit));
$js = files_js();
$smarty = smarty();
if ($institution === false) {
$smarty->display('admin/users/noinstitutions.tpl');
......@@ -54,19 +65,11 @@ if (!$USER->can_edit_institution($institution)) {
throw new AccessDeniedException();
}
$javascript = ArtefactTypeFileBase::get_my_files_js(param_integer('folder', null));
$institutionstr = json_encode($institution);
$javascript .= <<<JS
browser.source += '?institution={$institution}';
browser.createfolderscript += '?institution={$institution}';
uploader.uploadscript += '?institution={$institution}';
JS;
$smarty->assign('institution', $institution);
$smarty->assign('institutionselector', $s['institutionselector']);
$smarty->assign('INLINEJAVASCRIPT', $s['institutionselectorjs'] . $javascript);
$smarty->assign('form', $form);
$smarty->assign('INLINEJAVASCRIPT', $js);
$smarty->assign('heading', TITLE);
$smarty->display('artefact:file:index.tpl');
$smarty->display('artefact:file:files.tpl');
?>
function FileBrowser(idprefix, folderid, config) {
var self = this;
this.id = idprefix;
this.folderid = folderid;
this.config = config;
this.nextupload = 0;
this.init = function () {
self.form = $(self.formname);
self.foldername = self.form.foldername.value;
if (self.config.upload) {
self.upload_init();
}
self.browse_init();
if (self.config.upload) {
self.edit_init();
}
}
this.upload_init = function () {
if ($(self.id + '_notice')) {
addElementClass(self.id + '_elements', 'hidden');
addElementClass(self.id + '_uploadcancel', 'hidden');
}
self.upload_connectbuttons();
}
this.upload_connectbuttons = function () {
if ($(self.id + '_notice')) {
connect(self.id + '_notice', 'onchange', function (e) {
// error class is too general?
forEach(getElementsByTagAndClassName('div', 'error', self.id + '_upload_messages'), removeElement);
if (this.checked) {
removeElementClass(self.id + '_elements', 'hidden');
} else {
addElementClass(self.id + '_elements', 'hidden');
}
});
connect(self.id + '_uploadcancel', 'onclick', function () {
removeElementClass(self.id + '_openbutton', 'hidden');
addElementClass(self.id + '_agreement', 'hidden');
$(self.id + '_notice').checked = false;
addElementClass(self.id + '_elements', 'hidden');
addElementClass(this, 'hidden');
});
}
connect(self.id + '_userfile', 'onchange', self.upload_submit);
}
this.upload_validate = function () {
if ($(self.id + '_notice') && !$(self.id + '_notice').checked) {
appendChildNodes(self.id+'_upload_messages', DIV({'class':'error'}, get_string('youmustagreetothecopyrightnotice')));
return false;
}
return !isEmpty($(self.id + '_userfile').value);
}
this.upload_presubmit = function (e) {
// Display upload status
self.nextupload++;
var localname = basename($(self.id + '_userfile').value);
var message = makeMessage(DIV(null,
IMG({'src':get_themeurl('images/loading.gif')}), ' ',
get_string('uploadingfiletofolder',localname,self.foldername)
), 'info');
setNodeAttribute(message, 'id', 'uploadstatusline' + self.nextupload);
appendChildNodes(self.id + '_upload_messages', message);
$(self.id+'_uploadnumber').value = self.nextupload;
return true;
}
this.upload_submit = function (e) {
e.stop();
if (!self.upload_validate()) {
return false;
}
self.upload_presubmit();
signal(self.form, 'onsubmit');
self.form.submit();
$(self.id + '_userfile').value = '';
return false;
}
this.fileexists = function (filename, id) {
for (var i in self.filedata) {
if (self.filedata[i].title == filename && (!id || i != id)) {
return true;
}
}
return false;
}
this.createfolder_submit = function (e) {
var message;
var name = $(self.id + '_createfolder_name');
if (!name) {
message = get_string('foldernamerequired');
}
else {
name = name.value;
if (name == '') {
message = get_string('foldernamerequired');
}
else if (self.fileexists(name)) {
message = get_string('filewithnameexists', name);
}
}
if (message) {
e.stop();
replaceChildNodes(self.id + '_createfolder_messages', makeMessage(message, 'error'));
return false;
}
}
this.edit_submit = function (e) {
var message;
var name = $(self.id + '_edit_title');
if (!name) {
message = get_string('namefieldisrequired');
}
else {
name = name.value;
if (name == '') {
message = get_string('namefieldisrequired');
}
else if (self.fileexists(name, this.value)) {
message = get_string('filewithnameexists', name);
}
}
if (message) {
e.stop();
replaceChildNodes(self.id + '_edit_messages', makeMessage(message, 'error'));
return false;
}
}
this.browse_submit = function (e) {
e.stop();
signal(self.form, 'onsubmit');
self.form.submit();
return false;
}
this.upload_success = function (data) {
if (data.problem) {
var image = 'images/icon_problem.gif';
}
else if (!data.error) {
var image = 'images/success.gif';
}
else {
var image = 'images/failure.gif';
}
quotaUpdate(data.quotaused, data.quota);
var newmessage = makeMessage(DIV(null,IMG({'src':get_themeurl(image)}), ' ', data.message));
replaceChildNodes($('uploadstatusline'+data.uploadnumber), newmessage);
}
this.edit_form = function (e) {
e.stop();
var id = this.value;
addElementClass(self.id + '_edit_row', 'hidden');
$(self.id + '_edit_heading').innerHTML = self.filedata[id].artefacttype == 'folder' ? get_string('editfolder') : get_string('editfile');
$(self.id + '_edit_title').value = self.filedata[id].title;
$(self.id + '_edit_description').value = self.filedata[id].description;
$(self.id + '_edit_tags').value = self.filedata[id].tags.join(', ');
replaceChildNodes($(self.id + '_edit_messages'));
forEach(getElementsByTagAndClassName('input', 'permission', self.id + '_edit_row'), function (elem) {
var perm = getNodeAttribute(elem, 'name').split(':');
if (self.filedata[id].permissions[perm[1]][perm[2]] == 1) {
elem.checked = true;
}
});
$(self.id + '_edit_artefact').value = id;
var edit_row = removeElement(self.id + '_edit_row');
var this_row = getFirstParentByTagAndClassName(this, 'tr');
insertSiblingNodesAfter(this_row, edit_row);
removeElementClass(edit_row, 'hidden');
return false;
}
this.edit_init = function () { augment_tags_control(self.id + '_edit_tags'); }
this.browse_init = function () {
if (self.config.edit) {
forEach(getElementsByTagAndClassName('button', null, 'filelist'), function (elem) {
var name = getNodeAttribute(elem, 'name');
if (name == 'edit') {
connect(elem, 'onclick', self.edit_form);
}
});
connect(self.id + '_edit_cancel', 'onclick', function (e) {
e.stop();
addElementClass(self.id + '_edit_row', 'hidden');
return false;
});
connect(self.id + '_edit_artefact', 'onclick', self.edit_submit);
forEach(getElementsByTagAndClassName('div', 'icon-drag', 'filelist'), function (elem) {
self.make_icon_draggable(elem);
});
}
forEach(getElementsByTagAndClassName('a', 'changefolder', null), function (elem) {
connect(elem, 'onclick', function (e) {
var params = parseQueryString(getNodeAttribute(this, 'href'));
$(self.id + '_folder').value = params.folder;
self.browse_submit(e);
});
});
if ($(self.id + '_createfolder')) {
connect($(self.id + '_createfolder'), 'onclick', self.createfolder_submit);
}
}
this.make_row_droppable = function(row) {
new Droppable(row, {
accept: ['icon-drag'],
hoverclass: 'folderhover',
ondrop: function (dragged, dropped) {
self.form.move.value = dragged.id.replace(/drag:/, '');
self.form.moveto.value = dropped.id.replace(/file:/, '');
signal(self.form, 'onsubmit');
self.form.submit();
self.form.move.value = '';
self.form.moveto.value = '';
}
});
};
this.make_icon_draggable = function(elem) {
new Draggable(elem, {
starteffect: function(elem) {
// self.drag.clone is a copy of the icon which gets left behind.
map(self.make_row_droppable, getElementsByTagAndClassName('tr', 'folder', 'filelist'));
var row = getFirstParentByTagAndClassName(elem, 'tr', 'directory-item');
var rowid = getNodeAttribute(row, 'id');
var artefactid = rowid.substr(rowid.indexOf(':')+1);
self.drag.clone = elem.cloneNode(true);
setNodeAttribute(elem, 'id', 'drag:' + artefactid);
insertSiblingNodesAfter(elem, self.drag.clone);
setStyle(getFirstElementByTagAndClassName('img', null, elem), {'vertical-align':'middle'});
// Could read filename from self.filedata, but the one on the page is already shortened for display
appendChildNodes(elem, A({'href':''}, scrapeText(getFirstElementByTagAndClassName('td', 'filename', row))));
MochiKit.Position.absolutize(elem);
setStyle(elem, {
'border': '2px solid #000', // doesn't show up in IE6
'padding': '4px',
'line-height': '2em',
});
setOpacity(elem, 0.5);
},
revert: function(element) {
// Throw away the element being dragged
removeElement(element);
element = null;
self.make_icon_draggable(self.drag.clone);
}
});
// Draggable sets position = 'relative', but we set it back
// here because with position = 'relative' in IE6 the rows
// stay put instead of moving down when the create/upload
// forms are opened on the page.
elem.style.position = 'static';
};
this.drag = {};
this.success = function (form, data) {
var stop = false; // Whether to call the form's success callback afterwards
if (self.config.upload && data.action == 'upload') {
self.upload_success(data);
stop = true;
}
if (data.newlist && (data.folder == self.folderid || data.action == 'changefolder')) {
self.filedata = data.newlist.data;
if (self.config.edit) {
replaceChildNodes(self.id + '_edit_placeholder', removeElement(self.id + '_edit_row'));
}
$(self.id+'_filelist_container').innerHTML = data.newlist.html;
if (data.action == 'changefolder' && data.newpath) {
$(self.id+'_folder').value = self.folderid = data.folder;
$(self.id+'_foldername').value = self.foldername = data.newpath.foldername;
$(self.id+'_foldernav').innerHTML = data.newpath.html;
stop = true;
}
else if (data.action == 'move') {
}
stop = true;
self.browse_init();
}
if (data.action == 'delete') {
quotaUpdate(data.quotaused, data.quota);
}
return stop;
}
}
......@@ -32,6 +32,7 @@ $string['sitefilesloaded'] = 'Site files loaded';
$string['bytes'] = 'bytes';
$string['cannoteditfolder'] = 'You do not have permission to add content to this folder';
$string['changessaved'] = 'Changes saved';
$string['clickanddragtomovefile'] = 'Click and drag to move %s';
$string['contents'] = 'Contents';
$string['copyrightnotice'] = 'Copyright notice';
$string['create'] = 'Create';
......@@ -45,6 +46,7 @@ $string['deletefolder?'] = 'Are you sure you want to delete this folder?';
$string['Description'] = 'Description';
$string['destination'] = 'Destination';
$string['Download'] = 'Download';
$string['downloadfile'] = 'Download %s';
$string['downloadoriginalversion'] = 'Download the original version';
$string['editfile'] = 'Edit file';
$string['editfolder'] = 'Edit folder';
......@@ -55,16 +57,18 @@ $string['filealreadyindestination'] = 'The file you moved is already in that fol
$string['files'] = 'files';
$string['Files'] = 'Files';
$string['fileexists'] = 'File exists';
$string['fileexistsonserver'] = 'A file with the name %s already exists.';
$string['fileexistsoverwritecancel'] = 'A file with that name already exists. You can try a different name, or overwrite the existing file.';
$string['filelistloaded'] = 'File list loaded';
$string['filemoved'] = 'File moved successfully';
$string['filenamefieldisrequired'] = 'The file field is required';
$string['fileinstructions'] = 'Upload your images, documents, or other files for inclusion in views. To move a file or folder, drag and drop it onto a folder.';
$string['filethingdeleted'] = '%s deleted';
$string['filewithnameexists'] = 'A file or folder with the name "%s" already exists.';
$string['folder'] = 'Folder';
$string['Folders'] = 'Folders';
$string['foldercreated'] = 'Folder created';
$string['foldernamerequired'] = 'Please provide a name for the new folder.';
$string['gotofolder'] = 'Go to %s';
$string['groupfiles'] = 'Group Files';
$string['home'] = 'Home';
$string['htmlremovedmessage'] = 'You are viewing <strong>%s</strong> by <a href="%s">%s</a>. The file displayed below has been filtered to remove malicious content, and is only a rough representation of the original.';
......@@ -101,6 +105,8 @@ $string['uploadoffilefailed'] = 'Upload of %s failed';
$string['uploadoffiletofoldercomplete'] = 'Upload of %s to %s complete';
$string['uploadoffiletofolderfailed'] = 'Upload of %s to %s failed';
$string['youmustagreetothecopyrightnotice'] = 'You must agree to the copyright notice';
$string['fileuploadedtofolderas'] = '%s uploaded to %s as "%s"';
$string['fileuploadedas'] = '%s uploaded as "%s"';
// File types
......
......@@ -387,13 +387,12 @@ abstract class ArtefactTypeFileBase extends ArtefactType {
// Sort folders before files; then use nat sort order.
public static function my_files_cmp($a, $b) {
return strnatcasecmp((int)($a->artefacttype != 'folder') . $a->title,
(int)($b->artefacttype != 'folder') . $b->title);
return strnatcasecmp((-2 * isset($a->isparent) + ($a->artefacttype != 'folder')) . $a->title,
(-2 * isset($b->isparent) + ($b->artefacttype != 'folder')) . $b->title);
}
public static function get_my_files_data($parentfolderid, $userid, $institution=null, $group=null) {
public static function get_my_files_data($parentfolderid, $userid, $group=null, $institution=null, $idkeys=true) {
$select = '
SELECT
a.id, a.artefacttype, a.mtime, f.size, a.title, a.description,
......@@ -458,6 +457,9 @@ abstract class ArtefactTypeFileBase extends ArtefactType {
foreach ($filedata as $item) {
$item->mtime = format_date(strtotime($item->mtime), 'strfdaymonthyearshort');
$item->tags = array();
if ($item->size) { // Doing this here now for non-js users
$item->size = ArtefactTypeFile::short_size($item->size, true);
}
}
$where = 'artefact IN (' . join(',', array_keys($filedata)) . ')';
$tags = get_records_select_array('artefact_tag', $where);
......@@ -478,22 +480,27 @@ abstract class ArtefactTypeFileBase extends ArtefactType {
}
}
}
$filedata = array_values($filedata);
}
// Add parent folder to the list
if (!empty($parentfolderid)) {
$grandparentid = get_field('artefact', 'parent', 'id', $parentfolderid);
$filedata[] = (object) array(
'title' => '..',
$grandparentid = (int) get_field('artefact', 'parent', 'id', $parentfolderid);
$filedata[$grandparentid] = (object) array(
'title' => get_string('parentfolder', 'artefact.file'),
'artefacttype' => 'folder',
'description' => get_string('parentfolder', 'artefact.file'),
'isparent' => true,
'id' => (int) $grandparentid
'id' => $grandparentid
);
}
usort($filedata, array("ArtefactTypeFileBase", "my_files_cmp"));
uasort($filedata, array("ArtefactTypeFileBase", "my_files_cmp"));
if (!$idkeys) {
// Temporary: allow blog attachment stuff to continue to
// work with the old file.js & tablerenderer.js
return array_values($filedata);
}
return $filedata;
}
......@@ -677,6 +684,32 @@ JAVASCRIPT;
return $folderid;
}
/**
* Return a unique artefact title for a given owner & parent by appending
* digits to a desired title
*