Webové aplikácie potrebujú jednoducho použiteľné riešenie pre upload a manipuláciu bohatého obsahu. Tento proces môže spôsobovať problémy niektorým používateľom, ktorí majú minimálne znalosti s úpravou fotografií. Orezávanie je jednou z najpoužívanejších metód pre manipuláciu s fotografiami, a tento tutoriál sa bude vzťahovať na celý vývojový proces jQuery pluginu, na orezávanie obrázku.
Najskôr si pripravíme pracovný priestor projektu pre náš tutoriál. Začnime tým, že vytvoríme hierarchiu adresárov a prázdne súbory s názvami ako na nasledujúcom obrázku:
Ďalej budeme musieť stiahnuť jQuery a presunúť ho do /resources/js/
priečinka. Obrázok použitý v tomto tuoriáli musí byť pomenovaný example.jpg
a umiestnený do /resources/images/
priečinka. Môžete použiť tento obrázok (vďaka gsso-stock), poskytnutý v zdrojových súboroch tohto tutoriálu, alebo jeden z vašich vlastných. A posledný súbor je outline.gif
, ktorý musí byť umiestnený v /resources/js/imageCrop/
priečinku.
Ak chcete vyskúšať náš plugin, budeme ho musieť pripojiť na obrázok. Pred započatím práce vytvoríme jednoduchú stránku obsahujúcu tento obrázok.
Otvorte index.html
súbor vo vašom obľúbenom textovom editore a napíšte nasledujúci kód.
jQuery Image Cropping Plug-In jQuery Image Cropping Plug-In
Nie je na tom nič zvláštne: iba čistý HTML kód. Načítame CSS pre stránku, jQuery, náš plugin súbor (ktorý je momentálne prázdny) a vložíme obrázok do dokumentu.
Teraz upravíme style.css
, tak ako je uvedené nižšie.
* { margin : 0; outline : 0; padding : 0; } body { background-color : #ededed; color : #646464; font-family : 'Verdana', 'Geneva', sans-serif; font-size : 12px; text-shadow : 0 1px 0 #ffffff; } h1 { font-size : 24px; font-weight : normal; margin : 0 0 10px 0; } div#wrapper { margin : 25px 25px 25px 25px; } div.image-decorator { -moz-border-radius : 5px 5px 5px 5px; -moz-box-shadow : 0 0 6px #c8c8c8; -webkit-border-radius : 5px 5px 5px 5px; -webkit-box-shadow : 0 0 6px #c8c8c8; background-color : #ffffff; border : 1px solid #c8c8c8; border-radius : 5px 5px 5px 5px; box-shadow : 0 0 6px #c8c8c8; display : inline-block; height : 360px; padding : 5px 5px 5px 5px; width : 480px; }
Nastavili sme vzhľad našej stránky zmenou farby pozadia a pridali sme základný vzhľad pre nadpis a obrázok.
Začnime tým, že vytvoríme základ jQuery pluginu.
Ďalšie informácie o tom, ako napísať svoj vlastný plugin, získate prostredníctvom tejto správy. Popisuje základy, najlepšie postupy a bežné úskalia, na ktoré si treba dať pozor pri písaní vlastného pluginu.
Otvorte /resources/js/imageCrop/jquery.imagecrop.js
a pridajte nasledujúci kód.
// Vzdy zapuzdrite plugin do '(function($) { // sem pojde plugin }) (jQuery);' (function($) { $.imageCrop = function(object, customOptions) {}; $.fn.imageCrop = function(customOptions) { // Prechádza každým objektom this.each(function() { var currentObject = this, image = new Image(); // A pripoji imageCrop ked je objekt nacitany image.onload = function() { $.imageCrop(currentObject, customOptions); }; // Resetne src, pretoze cachovane obrázky obcas nespustaju load image.src = currentObject.src; }); // Akonahle plugin vrati vnutornu hodnotu, funkcia vzdy vrati 'this' pre zachovanie retazenia return this; }; }) (jQuery);
Práve sme rozšírili jQuery pridaním novej vlastnosti funkcie do jQuery.fn
objektu. Teraz máme hrubý základ pluginu, ktorý prechádza každým objektom a pridá imageCrop
pri načítaní objektu. Všimnite si, že cachované obrázky občas nespúštajú load
, takže to opravíme resetnutím src
atribútu.
Umožnením prispôsobenia nastavení robí plugin pre užívateľov viac flexibilným.
$.imageCrop = function(object, customOptions) { // Rather than requiring a lengthy amount of arguments, pass the // plug-in options in an object literal that can be extended over // the plug-in's defaults var defaultOptions = { allowMove : true, allowResize : true, allowSelect : true, minSelect : [0, 0], outlineOpacity : 0.5, overlayOpacity : 0.5, selectionPosition : [0, 0], selectionWidth : 0, selectionHeight : 0 }; // Nastavi prevolene hodnoty var options = defaultOptions; // A zmeni zvolene nastavenia setOptions(customOptions); };
Definovali sme pole predvolených nastavení, potom sme ich spojili s voľbou vlastností zavolaním setOptions
funkcie. Poďme ďalej a napíšme telo tejto funkcie.
... // Zameni aktualne nastavenia zvolenymi function setOptions(customOptions) { options = $.extend(options, customOptions); };
$.extend()
funkcia zlúči obsah dvoj a viacerých objektov do prvého objektu.
Nasledujúci zoznam popisuje jednotlivé voľby pluginu.
true
).true
).true
).[0,0]
).0.5
).0.5
).[0,0]
).0
).0
).V tomto kroku budeme modifikovať DOM pre prípravu na ďalší krok: rozhranie pluginu.
Najskôr inicializujeme image vrstvu.
... // inicializuje image vrstvu var $image = $(object);
Teraz inicializujeme image holder.
... // inicializuje image holder var $holder = $('') .css({ position : 'relative' }) .width($image.width()) .height($image.height()); // Obalime holder okolo obrazku $image.wrap($holder) .css({ position : 'absolute' });
Ako môžete vidieť, holder vrstvy má rovnakú veľkosť ako obrázok a relatívnu pozíciu. Ďalej zavoláme .wrap()
funkciu pre umiestnenie obrázka do vnútra holdera.
Nad obrázkom bude overlay vrstva.
... // Inicializuje overlay vrstvu a umiestni ju nad obrazok var $overlay = $('') .css({ opacity : options.overlayOpacity, position : 'absolute' }) .width($image.width()) .height($image.height()) .insertAfter($image);
Táto vrstva má rovnakú veľkosť ako obrázok, ale tiež dostane absolútnu pozíciu. Získame hodnotu priehľadnosti z options.overlayOpacity
a necháme jQuery aplikovať ju. Tento element má tiež id, takže môžeme túto vlastnosť meniť pomocou stylesheet pluginu. Nakoniec zavoláme .insertAfter()
metódu pre vloženie overlay vrstvy hneď za obrázok.
Ďalšou vrstvou je trigger vrstva, ktorú umiestníme za overlay vrstvu, rovnako ako sme to urobili s predošlou.
... // Inicializuje trigger vrstvu a umiestni ju nad overlay vrstvu var $trigger = $('') .css({ backgroundColor : '#000000', opacity : 0, position : 'absolute' }) .width($image.width()) .height($image.height()) .insertAfter($overlay);
Na farbe pozadia nezáleží ale musí byť iná ako priehľadná (ktorá je predvolená). Táto vrstva je pre užívateľa neviditeľná ale obsluhuje nejaké udalosti.
Umiestnime outline vrstvu nad trigger vrstvu.
... // Inicializuje outline vrstvu a umiestni ju nad trigger vrstvu var $outline = $('') .css({ opacity : options.outlineOpacity, position : 'absolute' }) .insertAfter($trigger);
A nakoniec posledná vrstva.
... // Inicializuje selection vrstvua umiestni ju nad outline vrstvu var $selection = $('') .css({ background : 'url(' + $image.attr('src') + ') no-repeat', position : 'absolute' }) .insertAfter($outline);
.attr()
metóda vráti hodnotu zvoleného atribútu. Použijeme ju pre získanie src
, a nastavíme ju ako pozadie selection vrstvy.
Možno to už viete, ale element s relatívnym poziciovaním získava kontrolu nad absolútne poziciovaným elementom v jeho vnútri. To je dôvod, prečo holder vrstva má relatívnu pozíciu a všetci jeho potomkovia absolútnu pozíciu.
Vynikajúce vysvetlenie tohto triku je obsiahnuté v tomto článku.
Najskôr inicializujeme nejaké premenné.
... // Inicializuje globalne premenne var selectionExists, selectionOffset = [0, 0], selectionOrigin = [0, 0];
selectionExists
nás bude informovať, či existuje výber. selectionOffset
bude obsahovať odsadenie vzhľadom k obrázku, a selectionOrigin
bude uvádzať pôvodný výber. Veci budú oveľa jasnejšie po niekoľkých krokoch.
Nasledujúce podmienky sú nutné v prípade, že existuje výber pri načítaní pluginu.
... // Skontroluje, ci je velkost vyberu vacsia nez povolene minimum if (options.selectionWidth > options.minSelect[0] && options.selectionHeight > options.minSelect[1]) selectionExists = true; else selectionExists = false;
Ďalej zavoláme updateInterface()
funkciu pre inicializovanie rozhrania.
... // Zavola 'updateInterface' funkciu pre inicializovanie rozhrania updateInterface();
Telo tejto funkcie napíšeme už čoskoro. Teraz sa poďme postarať o našu prvú udalosť.
... if (options.allowSelect) // Zviaze handler udalosť k 'mousedown' udalosti trigger vrstvy $trigger.mousedown(setSelection);
Zavoláme .mousedown()
ak options.allowSelect
je true
. To sa bude viazať na handler udalosť k mousedown
udalosti trigger vrstvy. Takže ak užívateľ klikne na obrázok, vyvolá sa setSelection()
.
... // Ziska aktualne odsadenie elementu function getElementOffset(object) { var offset = $(object).offset(); return [offset.left, offset.top]; }; // Ziska aktualnu poziciu kurzora relativne k pozicii obrazka function getMousePosition(event) { var imageOffset = getElementOffset($image); var x = event.pageX - imageOffset[0], y = event.pageY - imageOffset[1]; x = (x < 0) ? 0 : (x > $image.width()) ? $image.width() : x; y = (y < 0) ? 0 : (y > $image.height()) ? $image.height() : y; return [x, y]; };
Prvá funkcia, getElementOffset()
, vráti left a top súradnice zvoleného objektu relatívne vzhľadom k dokumentu. Túto hodnotu získame tým, že zavoláme .offset()
metódu. Druhá funkcia, getMousePosition()
, vráti aktuálnu pozíciu myši, ale vzhľadom na pozíciu obrázka. Takže budeme pracovať s hodnotami, ktoré sú len medzi 0 a šírkou/výškou obrázku respektíve na x/y osi.
Poďme si napísať funkciu pre aktualizáciu našej vrstvy.
... // Aktualizuje overlay vrstvu function updateOverlayLayer() { $overlay.css({ display : selectionExists ? 'block' : 'none' }); };
Táto funkcia kontroluje hodnotu premennej selectionExists
, a určuje, či by mala byť overlay vrstva zobrazená alebo nie.
... // Aktualizuje trigger vrstvu function updateTriggerLayer() { $trigger.css({ cursor : options.allowSelect ? 'crosshair' : 'default' }); };
Funkcia updateTriggerLayer()
zmení kurzor na crosshair
alebo default
, v závislosti na hodnotu options.allowSelect
.
Ďalej si napíšme updateSelection()
funkciu. Tá bude aktualizovať nielen selection vrstvu, ale aj outline vrstvu.
... // Aktualizuje selection function updateSelection() { // Update the outline layer $outline.css({ cursor : 'default', display : selectionExists ? 'block' : 'none', left : options.selectionPosition[0], top : options.selectionPosition[1] }) .width(options.selectionWidth) .height(options.selectionHeight); // Aktualizuje selection vrstvu $selection.css({ backgroundPosition : ( - options.selectionPosition[0] - 1) + 'px ' + ( - options.selectionPosition[1] - 1) + 'px', cursor : options.allowMove ? 'move' : 'default', display : selectionExists ? 'block' : 'none', left : options.selectionPosition[0] + 1, top : options.selectionPosition[1] + 1 }) .width((options.selectionWidth - 2 > 0) ? (options.selectionWidth - 2) : 0) .height((options.selectionHeight - 2 > 0) ? (options.selectionHeight - 2) : 0); };
Po prvé, táto funkcia nastavuje vlastnosti outline vrstvy: kurzor, zobrazenie, veľkosť a jej pozíciu. Ďalšou je selection vrstva; nová hodnota pozície pozadia spôsobí, že sa obrázky prekrývajú.
Teraz potrebujeme funkciu pre obnovenie kurzora, keď to bude potrebné. Napríklad keď robíme výber, chceme mať crosshair
kurzor bez ohľadu na to nad ktorou vrstvou sa nachádzame.
... // Aktualizuje typ kurzora function updateCursor(cursorType) { $trigger.css({ cursor : cursorType }); $outline.css({ cursor : cursorType }); $selection.css({ cursor : cursorType }); };
Áno, je to tak jednoduché, ako to vyzerá. Stačí zmeniť typ kurzora na jeden zo zvolených!
A teraz, posledná funkcia tohto kroku; potrebujeme ju na updatovanie rozhrania pluginu v rôznych situáciách - v označovaní, zmene veľkosti, po skončení označovania a tiež, keď sa plugin inicializuje.
... // Aktualizuje rozhranie pluginu function updateInterface(sender) { switch (sender) { case 'setSelection' : updateOverlayLayer(); updateSelection(); break; case 'resizeSelection' : updateSelection(); updateCursor('crosshair'); break; default : updateTriggerLayer(); updateOverlayLayer(); updateSelection(); } };
Ako môžete vidieť updateInterface()
funkcia filtruje niektoré prípady a volá potrebné funkcie, ktoré sme práve napísali.
Až doteraz sme sa starali o prispôsobenie možností a rozhrania, ale nie o to ako užívateľ pracuje s pluginom. Poďme si napísať funkciu, ktorá definuje nový výber po kliknutí na obrázok.
... // Nastavi novy vyber function setSelection(event) { // Zabrani predvolenej akcii jej udalost event.preventDefault(); // Zabrani zaznamenaniu udalosti event.stopPropagation(); // Zviaze hander udalosti na 'mousemove' a 'mouseup' udalosti $(document).mousemove(resizeSelection).mouseup(releaseSelection); // Zaznamena, ze existuje vyber selectionExists = true; // Resetne velkost vyberu options.selectionWidth = 0; options.selectionHeight = 0; // Ziska povodný vyber selectionOrigin = getMousePosition(event); // A nastaví jeho pozíciu options.selectionPosition[0] = selectionOrigin[0]; options.selectionPosition[1] = selectionOrigin[1]; // Aktualizuje iba potrebne elementy rozhrania pluginu specifikovanim odosielatela aktualneho volania updateInterface('setSelection'); };
Najskôr funkcia setSelection
zavolá dve metódy: event.preventDefault()
a event.stopPropagation()
. Tým sa zabráni predvolenej akcii udalosti a každému rodičovi handlera od zaznamenania udalosti. Metóda .mousemove()
viaže handler udalosti na mousemove
udalosť. Tá bude volať resizeSelection()
funkciu zakaždým, keď užívateľ presunie kurzor myši. Pre zaznamenanie, že bol vytvorený nový výber, je selectionExists
hodnota nastavená na true
a veľkosť výberu je nastavená na 0. Ďalej získame výber zavolaním našej predošlej napísanej funkcie getMousePosition()
, a vložíme túto hodnotu do options.selectionPosition
. Nakoniec zavoláme updateInterface()
funkciu pre aktualizovanie rozhrania pluginu v závislosti na vykonané zmeny.
V predchádzajúcich krokoch sme si napísali funkciu pre nastavenie nového výberu. Poďme si teraz napísať funkciu pre zmenu veľkosti tohto výberu.
... // Zmeni velkost vyberu function resizeSelection(event) { // Zabráni predvolenej akcii jej udalosť event.preventDefault(); // Zabrani zaznamenaniu udalosti event.stopPropagation(); var mousePosition = getMousePosition(event); // Ziska velkost vyberu options.selectionWidth = mousePosition[0] - selectionOrigin[0]; options.selectionHeight = mousePosition[1] - selectionOrigin[1]; if (options.selectionWidth < 0) { options.selectionWidth = Math.abs(options.selectionWidth); options.selectionPosition[0] = selectionOrigin[0] - options.selectionWidth; } else options.selectionPosition[0] = selectionOrigin[0]; if (options.selectionHeight < 0) { options.selectionHeight = Math.abs(options.selectionHeight); options.selectionPosition[1] = selectionOrigin[1] - options.selectionHeight; } else options.selectionPosition[1] = selectionOrigin[1]; // Aktualizuje iba potrebne elementy rozhrania pluginu specifikovanim odosielatela aktualneho volania updateInterface('resizeSelection'); };
Ak chcete zmeniť veľkosť výberu, je potrebné načítať aktuálnu pozíciu myši. Pretože vrátená hodnota je relatívna k veľkosti obrázka, musíme dbať na záporné hodnoty. Tá nikdy neprekročí hranice obrázka. Ako viete, premenné width
a height
nemôžu mať záporné hodnoty. To zabezpečíme zavolaním Math.abs()
, aby sme získali absolútnu (nezápornú) hodnotu, a potom premiestníme výber.
A teraz posledná funkcia:
... // Skonci oznacovanie vyberu function releaseSelection(event) { // Zabrani predvolenej akcii jej udalost event.preventDefault(); // Zabrani zaznamenaniu udalosti event.stopPropagation(); // Odviaze handler udalosti z 'mousemove' udalosti $(document).unbind('mousemove'); // Odviaze handler udalosti z 'mouseup' udalosti $(document).unbind('mouseup'); // Aktualizuje povodny vyber selectionOrigin[0] = options.selectionPosition[0]; selectionOrigin[1] = options.selectionPosition[1]; // Otestuje minimalnu akceptovatelnu velkost if (options.selectionWidth > options.minSelect[0] && options.selectionHeight > options.minSelect[1]) selectionExists = true; else selectionExists = false; // Aktualizuje iba potrebne elementy rozhrania pluginu specifikovanim odosielatela aktualneho volania updateInterface('releaseSelection'); };
Ak bolo ukončené označovanie, funkcia releaseSelection()
odstráni predtým pripojené handlery udalosti v setSelection()
funkcii zavolaním .unbind
metódy. Ďalej updatuje pôvodný výber a otestuje minimálnu akceptovateľnú veľkosť.
Teraz už sme takmer pripravení. Zatvorte súbor a pripravte sa na ďalší krok.
Otvorte /resources/js/imageCrop/jquery.imagecrop.css
stylesheet, a pridajte nasledujúce riadky.
div#image-crop-overlay { background-color : #ffffff; overflow : hidden; } div#image-crop-outline { background : #ffffff url('outline.gif'); overflow : hidden; }
Na tom nie je nič komplikované; pridali sme nejaký vzhľad overlay a outline vrstvám.
Pre otestovanie nášho pluginu ho potrebujeme pripojiť na obrázok. Poďme na to a upravme index.html
stránku.
script
tag ...
... a napíšte nasledujúci JavaScript kód.
$(document).ready(function() { $('img#example').imageCrop({ overlayOpacity : 0.25 }); });
My sme pripojili náš plugin na element obrázka pomocou example
id a nastavili nejaké vybrané vlastnosti. Použili sme .ready()
metódu na zistenie, kedy je DOM úplne načítaný.
A je to! Uložte súbor a pre vyskúšanie si ho otvorte vo svojom prehliadači.
Teraz máme základ jQuery pluginu pre orezávanie obrázkov, ktorý vám umožní označiť plochu obrázka. V ďalšom tutoriáli pridáme viac možností prispôsobenia, vytvorenie náhľadu, napíšeme si nejaký kód po strane servera na orezanie obrázka ... a omnoho viac. Dúfam, že ste si užili čas, ktorý sme spolu strávili a niečo ste sa aj naučili. Vďaka za prečítanie!
Zatiaľ žiadne komentáre
© 2009 Shaddow hosting od VIPHosting