diff --git a/client.js b/client.js index 4cf02c70..d648df8d 100644 --- a/client.js +++ b/client.js @@ -1,829 +1,829 @@ -/* Функция которая возвратит обьект CloudCommander - * @window - обьект window - * @document - обьект document - * @CloudFunc - обьект содержащий общий функционал - * клиентский и серверный - */ - -var CloudCommander=(function(){ -"use strict"; - -/* Клиентский обьект, содержащий функциональную часть*/ -var CloudClient={ - /* Конструктор CloudClient, который - * выполняет весь функционал по - * инициализации - */ - init :function(){}, - - keyBinding :function(){},/* функция нажатий обработки клавишь */ - Editor :function(){},/* function loads and shows editor */ - Viewer :function(){},/* function loads and shows viewer */ - keyBinded :false,/* оброботка нажатий клавишь установлена*/ - _loadDir :function(){}, - /* - * Функция привязываеться ко всем ссылкам и - * загружает содержимое каталогов - */ - /* Обьект для работы с кэшем */ - Cashe :{}, - - /* ПРИВАТНЫЕ ФУНКЦИИ */ - /* функция загружает json-данные о файловой системе */ - _ajaxLoad :function(){}, - /* Функция генерирует JSON из html-таблицы файлов */ - _getJSONfromFileTable :function(){}, - /* функция меняет ссыки на ajax-овые */ - _changeLinks :function(){}, - /* ОБЬЕКТЫ */ - /* обьект, который содержит функции для отображения картинок*/ - _images :{}, - /* КОНСТАНТЫ*/ - /* название css-класа текущего файла*/ - CURRENT_FILE :'current-file', - LIBDIR :'/lib/', - LIBDIRCLIENT :'/lib/client/', - /* height of Cloud Commander - * seting up in init() - */ - HEIGHT :0 -}; - -/* - * Обьект для работы с кэшем - * в него будут включены функции для - * работы с LocalStorage, webdb, - * indexed db etc. - */ -CloudClient.Cache={ - _allowed :true, /* приватный переключатель возможности работы с кэшем */ - /* функция проверяет возможно ли работать с кэшем каким-либо образом */ - isAllowed :function(){}, - /* Тип кэша, который доступен*/ - type :{}, - /* Функция устанавливает кэш, если выбранный вид поддерживаеться браузером*/ - set :function(){}, - /* Функция достаёт кэш, если выбранный вид поддерживаеться браузером*/ - get :function(){}, - /* функция чистит весь кэш для всех каталогов*/ - clear :function(){} -}; - -/* Обьект, который содержит - * функции для отображения - * картинок - */ -CloudClient._images={ - /* Функция создаёт картинку загрузки*/ - loading :function(){ - var e=document.createElement('span'); - e.className='icon loading'; - e.id='loading-image'; - return e; -}, - - /* Функция создаёт картинку ошибки загрузки*/ - error :function(){ - var e=document.createElement('span'); - e.className='icon error'; - e.id='error-image'; - return e; - } -}; - -/* функция проверяет поддерживаеться ли localStorage */ -CloudClient.Cache.isAllowed=(function(){ - if(window.localStorage && - localStorage.setItem && - localStorage.getItem){ - CloudClient.Cache._allowed=true; - }else - { - CloudClient.Cache._allowed=false; - /* загружаем PolyFill для localStorage, - * если он не поддерживаеться браузером - * https://gist.github.com/350433 - */ - /* - CloudClient.jsload('https://raw.github.com/gist/350433/c9d3834ace63e5f5d7c8e1f6e3e2874d477cb9c1/gistfile1.js', - function(){CloudClient.Cache._allowed=true; - }); - */ - } -}); - /* если доступен localStorage и - * в нём есть нужная нам директория - - * записываем данные в него - */ -CloudClient.Cache.set=(function(pName, pData){ - if(CloudClient.Cache._allowed && pName && pData){ - localStorage.setItem(pName,pData); - } -}); -/* Если доступен Cache принимаем из него данные*/ -CloudClient.Cache.get=(function(pName){ - if(CloudClient.Cache._allowed && pName){ - return localStorage.getItem(pName); - } - else return null; -}); -/* Функция очищает кэш*/ -CloudClient.Cache.clear=(function(){ - if(CloudClient.Cache._allowed){ - localStorage.clear(); - } -}); - - -/* функция обработки нажатий клавишь */ -CloudClient.keyBinding=(function(){ - /* loading keyBinding module and start it */ - CloudClient.jsload(CloudClient.LIBDIRCLIENT+'keyBinding.js',function(){ - CloudCommander.keyBinding(); - }); -}); - -/* function loads and shows editor */ -CloudClient.Editor = (function(){ - /* loading CloudMirror plagin */ - CloudClient.jsload(CloudClient.LIBDIRCLIENT + - 'editor.js',{ - onload:(function(){ - CloudCommander.Editor.Keys(); - }) - }); -}); - -/* function loads and shows viewer */ -CloudClient.Viewer = (function(){ - CloudCommander.jsload(CloudClient.LIBDIRCLIENT + - 'viewer.js',{ - onload: (function(){ - CloudCommander.Viewer.Keys(); - }) - }); -}); -/* - * Функция привязываеться ко всем ссылкам и - * загружает содержимое каталогов - */ -CloudClient._loadDir=(function(pLink,pNeedRefresh){ - /* @pElem - элемент, - * для которого нужно - * выполнить загрузку - */ - return function(){ - /* показываем гиф загрузки возле пути папки сверху*/ - LoadingImage.className='icon loading';/* показываем загрузку*/ - ErrorImage.className='icon error hidden';/* прячем ошибку */ - /* если элемент задан - - * работаем с ним - */ - /* если мы попали сюда с таблицы файлов*/ - try{ - this.firstChild.nextSibling.appendChild(LoadingImage); - }catch(error){ - /* если + - * кнопка обновления - */ - try{this.firstChild.parentElement.appendChild(LoadingImage);} - catch(error){console.log(error);} - } - - var lCurrentFile=document.getElementsByClassName(CloudClient.CURRENT_FILE); - /* получаем имя каталога в котором находимся*/ - var lHref; - try{ - lHref=lCurrentFile[0].parentElement.getElementsByClassName('path')[0].textContent; - }catch(error){console.log('error');} - - lHref=CloudFunc.removeLastSlash(lHref); - var lSubstr=lHref.substr(lHref,lHref.lastIndexOf('/')); - lHref=lHref.replace(lSubstr+'/',''); - - /* загружаем содержимое каталога*/ - CloudClient._ajaxLoad(pLink, pNeedRefresh); - - /* получаем все элементы выделенной папки*/ - /* при этом, если мы нажали обновить - * или +R - ссылок мы ненайдём - * и заходить не будем - */ - var lA=this.getElementsByTagName('a'); - /* если нажали на ссылку на верхний каталог*/ - if(lA.length>0 && lA[0].textContent==='..' && - lHref!=='/'){ - /* функция устанавливает курсор на каталог - * с которого мы пришли, если мы поднялись - * в верх по файловой структуре - */ - CloudClient._currentToParent(lHref); - } - - /* что бы не переходить по ссылкам - * а грузить всё ajax'ом, - * возвращаем false на событие - * onclick - */ - return false; - }; - }); - -/* Функция устанавливает текущим файлом, тот - * на который кликнули единожды - */ -CloudClient._setCurrent=(function(){ - /* - * @pFromEnter - если мы сюда попали - * из события нажатия на энтер - - * вызоветься _loadDir - */ - return function(pFromEnter){ - var lCurrentFile=document.getElementsByClassName(CloudClient.CURRENT_FILE); - if(lCurrentFile && lCurrentFile.length > 0){ - /* если мы находимся не на - * пути и не на заголовках - */ - if(this.className!=='path' && - this.className!=='fm_header'){ - - lCurrentFile[0].className=''; - /* устанавливаем курсор на файл, - * на который нажали */ - this.className=CloudClient.CURRENT_FILE; - } - } - /* если мы попали сюда с энтера*/ - if(pFromEnter===true){ - this.ondblclick(this); - }/* если мы попали сюда от клика мышки */ - else{pFromEnter.returnValue=false;} - - /* что бы не переходить по ссылкам - * а грузить всё ajax'ом, - * возвращаем false на событие - * onclick - */ - return false; - }; - }); - -/* функция устанавливает курсор на каталог - * с которого мы пришли, если мы поднялись - * в верх по файловой структуре - * @pDirName - имя каталога с которого мы пришли - */ -CloudClient._currentToParent = (function(pDirName){ - /* опредиляем в какой мы панели: - * правой или левой - */ - var lCurrentFile = document.getElementsByClassName(CloudClient.CURRENT_FILE); - var lPanel = lCurrentFile[0].parentElement; - - /* убираем слэш с имени каталога*/ - pDirName=pDirName.replace('/',''); - - var lRootDir = document.getElementById(pDirName + '(' + lPanel.id + ')'); - - /* if found li element with ID directory name - * set it to current file - */ - lRootDir && - !(lCurrentFile[0].className = '') && - (lRootDir.className = CloudClient.CURRENT_FILE); -}); - -/* глобальные переменные */ -var LoadingImage; -var ErrorImage; - -var CloudFunc, $; -/* Конструктор CloudClient, который - * выполняет весь функционал по - * инициализации - */ -CloudClient.init=(function() -{ - /* меняем title - * если js включен - имена папок отображать необязательно... - * а может и обязательно при переходе, можно будет это сделать - */ - var lTitle=document.getElementsByTagName('title'); - if(lTitle.length>0)lTitle[0].textContent='Cloud Commander'; - - /* загружаем jquery: */ - CloudClient.jsload('//ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js',{ - onload: function(){ - $ = window.jQuery; - }, - - onerror: function(){ - CloudClient.jsload('lib/client/jquery.js'); - - /* - * if could not load jquery from google server - * maybe we offline, load font from local - * directory - */ - CloudClient.cssSet({id:'local-droids-font', - element : document.head, - inner : '@font-face {font-family: "Droid Sans Mono";' + - 'font-style: normal;font-weight: normal;' + - 'src: local("Droid Sans Mono"), local("DroidSansMono"),'+ - ' url("font/DroidSansMono.woff") format("woff");}' - }); - } - }); - - /* загружаем общие функции для клиента и сервера*/ - CloudClient.jsload(CloudClient.LIBDIR+'cloudfunc.js',function(){ - /* берём из обьекта window общий с сервером функционал */ - CloudFunc=window.CloudFunc; - - /* меняем ссылки на ajax'овые*/ - CloudClient._changeLinks(CloudFunc.LEFTPANEL); - CloudClient._changeLinks(CloudFunc.RIGHTPANEL); - - /* устанавливаем переменную доступности кэша*/ - CloudClient.Cache.isAllowed(); - /* Устанавливаем кэш корневого каталога */ - if(!CloudClient.Cache.get('/'))CloudClient.Cache.set('/',CloudClient._getJSONfromFileTable()); - } - ); - - LoadingImage=CloudClient._images.loading(); - /* загружаем иконку загрузки возле кнопки обновления дерева каталогов*/ - try{ - document.getElementsByClassName('path')[0].getElementsByTagName('a')[0].appendChild(LoadingImage); - LoadingImage.className+=' hidden'; /* прячем её */ - }catch(error){console.log(error);} - ErrorImage=CloudClient._images.error(); - - /* устанавливаем размер высоты таблицы файлов - * исходя из размеров разрешения экрана - */ - - /* выделяем строку с первым файлом */ - var lFmHeader=document.getElementsByClassName('fm_header'); - if(lFmHeader && lFmHeader[0].nextSibling) - lFmHeader[0].nextSibling.className=CloudClient.CURRENT_FILE; - - /* показываем элементы, которые будут работать только, если есть js */ - var lFM=document.getElementById('fm'); - if(lFM)lFM.className='localstorage'; - - /* если есть js - показываем правую панель*/ - var lRight=document.getElementById('right'); - if(lRight)lRight.className=lRight.className.replace('hidden',''); - - /* формируем и округляем высоту экрана - * при разрешениии 1024x1280: - * 658 -> 700 - */ - - var lHeight=window.screen.height - (window.screen.height/3).toFixed(); - lHeight=(lHeight/100).toFixed()*100; - - CloudClient.HEIGHT = lHeight; - - CloudClient.cssSet({id:'show_2panels', - element:document.head, - inner:'#left{width:46%;}' + - '.panel{height:' + lHeight +'px' - }); -}); - -/* функция меняет ссыки на ajax-овые */ -CloudClient._changeLinks = function(pPanelID) -{ - /* назначаем кнопку очистить кэш и показываем её*/ - var lClearcache=document.getElementById('clear-cache'); - if(lClearcache)lClearcache.onclick=CloudClient.Cache.clear; - - /* меняем ссылки на ajax-запросы */ - var lPanel=document.getElementById(pPanelID); - var a=lPanel.getElementsByTagName('a'); - - /* Если нажмут на кнопку перезагрузить страниц - её нужно будет обязательно - * перезагрузить - */ - /* номер ссылки очистки кэша*/ - /* номер ссылки иконки обновления страницы */ - var lREFRESHICON=0; - - /* путь в ссылке, который говорит - * что js отключен - */ - var lNoJS_s = CloudFunc.NOJS; - var lFS_s = CloudFunc.FS; - - for(var i=0;i+ + * кнопка обновления + */ + try{this.firstChild.parentElement.appendChild(LoadingImage);} + catch(error){console.log(error);} + } + + var lCurrentFile=document.getElementsByClassName(CloudClient.CURRENT_FILE); + /* получаем имя каталога в котором находимся*/ + var lHref; + try{ + lHref=lCurrentFile[0].parentElement.getElementsByClassName('path')[0].textContent; + }catch(error){console.log('error');} + + lHref=CloudFunc.removeLastSlash(lHref); + var lSubstr=lHref.substr(lHref,lHref.lastIndexOf('/')); + lHref=lHref.replace(lSubstr+'/',''); + + /* загружаем содержимое каталога*/ + CloudClient._ajaxLoad(pLink, pNeedRefresh); + + /* получаем все элементы выделенной папки*/ + /* при этом, если мы нажали обновить + * или +R - ссылок мы ненайдём + * и заходить не будем + */ + var lA=this.getElementsByTagName('a'); + /* если нажали на ссылку на верхний каталог*/ + if(lA.length>0 && lA[0].textContent==='..' && + lHref!=='/'){ + /* функция устанавливает курсор на каталог + * с которого мы пришли, если мы поднялись + * в верх по файловой структуре + */ + CloudClient._currentToParent(lHref); + } + + /* что бы не переходить по ссылкам + * а грузить всё ajax'ом, + * возвращаем false на событие + * onclick + */ + return false; + }; + }); + +/* Функция устанавливает текущим файлом, тот + * на который кликнули единожды + */ +CloudClient._setCurrent=(function(){ + /* + * @pFromEnter - если мы сюда попали + * из события нажатия на энтер - + * вызоветься _loadDir + */ + return function(pFromEnter){ + var lCurrentFile=document.getElementsByClassName(CloudClient.CURRENT_FILE); + if(lCurrentFile && lCurrentFile.length > 0){ + /* если мы находимся не на + * пути и не на заголовках + */ + if(this.className!=='path' && + this.className!=='fm_header'){ + + lCurrentFile[0].className=''; + /* устанавливаем курсор на файл, + * на который нажали */ + this.className=CloudClient.CURRENT_FILE; + } + } + /* если мы попали сюда с энтера*/ + if(pFromEnter===true){ + this.ondblclick(this); + }/* если мы попали сюда от клика мышки */ + else{pFromEnter.returnValue=false;} + + /* что бы не переходить по ссылкам + * а грузить всё ajax'ом, + * возвращаем false на событие + * onclick + */ + return false; + }; + }); + +/* функция устанавливает курсор на каталог + * с которого мы пришли, если мы поднялись + * в верх по файловой структуре + * @pDirName - имя каталога с которого мы пришли + */ +CloudClient._currentToParent = (function(pDirName){ + /* опредиляем в какой мы панели: + * правой или левой + */ + var lCurrentFile = document.getElementsByClassName(CloudClient.CURRENT_FILE); + var lPanel = lCurrentFile[0].parentElement; + + /* убираем слэш с имени каталога*/ + pDirName=pDirName.replace('/',''); + + var lRootDir = document.getElementById(pDirName + '(' + lPanel.id + ')'); + + /* if found li element with ID directory name + * set it to current file + */ + lRootDir && + !(lCurrentFile[0].className = '') && + (lRootDir.className = CloudClient.CURRENT_FILE); +}); + +/* глобальные переменные */ +var LoadingImage; +var ErrorImage; + +var CloudFunc, $; +/* Конструктор CloudClient, который + * выполняет весь функционал по + * инициализации + */ +CloudClient.init=(function() +{ + /* меняем title + * если js включен - имена папок отображать необязательно... + * а может и обязательно при переходе, можно будет это сделать + */ + var lTitle=document.getElementsByTagName('title'); + if(lTitle.length>0)lTitle[0].textContent='Cloud Commander'; + + /* загружаем jquery: */ + CloudClient.jsload('//ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js',{ + onload: function(){ + $ = window.jQuery; + }, + + onerror: function(){ + CloudClient.jsload('lib/client/jquery.js'); + + /* + * if could not load jquery from google server + * maybe we offline, load font from local + * directory + */ + CloudClient.cssSet({id:'local-droids-font', + element : document.head, + inner : '@font-face {font-family: "Droid Sans Mono";' + + 'font-style: normal;font-weight: normal;' + + 'src: local("Droid Sans Mono"), local("DroidSansMono"),'+ + ' url("font/DroidSansMono.woff") format("woff");}' + }); + } + }); + + /* загружаем общие функции для клиента и сервера*/ + CloudClient.jsload(CloudClient.LIBDIR+'cloudfunc.js',function(){ + /* берём из обьекта window общий с сервером функционал */ + CloudFunc=window.CloudFunc; + + /* меняем ссылки на ajax'овые*/ + CloudClient._changeLinks(CloudFunc.LEFTPANEL); + CloudClient._changeLinks(CloudFunc.RIGHTPANEL); + + /* устанавливаем переменную доступности кэша*/ + CloudClient.Cache.isAllowed(); + /* Устанавливаем кэш корневого каталога */ + if(!CloudClient.Cache.get('/'))CloudClient.Cache.set('/',CloudClient._getJSONfromFileTable()); + } + ); + + LoadingImage=CloudClient._images.loading(); + /* загружаем иконку загрузки возле кнопки обновления дерева каталогов*/ + try{ + document.getElementsByClassName('path')[0].getElementsByTagName('a')[0].appendChild(LoadingImage); + LoadingImage.className+=' hidden'; /* прячем её */ + }catch(error){console.log(error);} + ErrorImage=CloudClient._images.error(); + + /* устанавливаем размер высоты таблицы файлов + * исходя из размеров разрешения экрана + */ + + /* выделяем строку с первым файлом */ + var lFmHeader=document.getElementsByClassName('fm_header'); + if(lFmHeader && lFmHeader[0].nextSibling) + lFmHeader[0].nextSibling.className=CloudClient.CURRENT_FILE; + + /* показываем элементы, которые будут работать только, если есть js */ + var lFM=document.getElementById('fm'); + if(lFM)lFM.className='localstorage'; + + /* если есть js - показываем правую панель*/ + var lRight=document.getElementById('right'); + if(lRight)lRight.className=lRight.className.replace('hidden',''); + + /* формируем и округляем высоту экрана + * при разрешениии 1024x1280: + * 658 -> 700 + */ + + var lHeight=window.screen.height - (window.screen.height/3).toFixed(); + lHeight=(lHeight/100).toFixed()*100; + + CloudClient.HEIGHT = lHeight; + + CloudClient.cssSet({id:'show_2panels', + element:document.head, + inner:'#left{width:46%;}' + + '.panel{height:' + lHeight +'px' + }); +}); + +/* функция меняет ссыки на ajax-овые */ +CloudClient._changeLinks = function(pPanelID) +{ + /* назначаем кнопку очистить кэш и показываем её*/ + var lClearcache=document.getElementById('clear-cache'); + if(lClearcache)lClearcache.onclick=CloudClient.Cache.clear; + + /* меняем ссылки на ajax-запросы */ + var lPanel=document.getElementById(pPanelID); + var a=lPanel.getElementsByTagName('a'); + + /* Если нажмут на кнопку перезагрузить страниц - её нужно будет обязательно + * перезагрузить + */ + /* номер ссылки очистки кэша*/ + /* номер ссылки иконки обновления страницы */ + var lREFRESHICON=0; + + /* путь в ссылке, который говорит + * что js отключен + */ + var lNoJS_s = CloudFunc.NOJS; + var lFS_s = CloudFunc.FS; + + for(var i=0;i