Fijate si te sirve para implementar o como idea (
Aquí un ejemplo online que funciona para navegadores que soportan canvas y por tanto nos ahorramos GD -está indicado en el código el lugar donde debería implementarse la solución del lado del servidor para los navegadores que no soportan canvas-): 
 Código PHP:
    <!DOCTYPE HTML>
<htmL>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Documento sin título</title>
<script type="text/javascript">
/*---- funciones auxiliares---*/
//DOMReady
var DR=function(f){
    if(document.addEventListener){
        var func=function(){f();document.removeEventListener('DOMContentLoaded',func,false);}
        document.addEventListener('DOMContentLoaded',func,false);
    }else{
        function r(f){/in/.test(document.readyState)?setTimeout(function(){r(f);},9):f();};
        r(f);
    }
}
function clearSelection() {
    if(window.permSel)return;
    var sel ;
    if(document.selection && document.selection.empty){
        try{document.selection.empty() ;}catch(err){}
    } else if(window.getSelection) {
        sel=window.getSelection();
    if(sel && sel.removeAllRanges)
        sel.removeAllRanges() ;
    }
}
function cancelEvent(e){
    if(e && e.preventDefault)
        e.preventDefault();
    else if(window.event)
        window.event.returnValue=false;
}
/*---- cropeo---*/
var crop=(
function(){
    var cur='';
    var coords={x:0,y:0};
    var coords2={x:0,y:0};
    var origen={x:0,y:0};
    var origen2={x:0,y:0};
    var renderizar=0;
    var recorte=0;
    var f=document.createDocumentFragment();
    var l=document.createElement('div');
    var r=document.createElement('div');
    var t=document.createElement('div');
    var b=document.createElement('div');
    var over=document.createElement('div');
    l.style.borderLeft=r.style.borderLeft='1px dashed white';
    t.style.borderBottom=b.style.borderBottom='1px dashed white';
    over.style.position=l.style.position=r.style.position=t.style.position=b.style.position='absolute';
    over.style.top='-15000px';
    over.style.zIndex=100;
    l.style.width=r.style.width=t.style.width=b.style.width=l.style.height=r.style.height=t.style.height=b.style.height=0;
    f.appendChild(l);
    f.appendChild(r);
    f.appendChild(t);
    f.appendChild(b);
    over.appendChild(f);
    DR(function(){
        document.body.appendChild(over);            
    });
    var mp={
        iniciar:function(o){
            crop.target=o;
            var pos=this.getElementPosition(o);
            var w=o.width || o.offsetWidth || 0;
            var h=o.height || o.offsetHeight || 0;
            over.style.width=w+'px';
            over.style.height=h+'px';
            over.style.top=pos.top+'px';
            over.style.background='url('+o.src+')';
            over.style.left=pos.left+'px';
            this.addEvent('mousemove',this.setCoord,over);
            this.addEvent('mousedown',this.setOrigen,over);
            this.addEvent('mouseup',function(){renderizar=0;over.style.cursor='default';},over);
            over.style.cursor='default';
        },
        render:function(){
            if(renderizar){
                if((coords.y-origen.y)<0){
                    origen2.y=coords.y+3;
                    coords2.y=origen.y;
                    cur='n';
                }else{
                    origen2.y=origen.y;
                    coords2.y=coords.y-3;
                    cur='s';
                }
                if((coords.x-origen.x)<0){
                    origen2.x=coords.x+3;
                    coords2.x=origen.x;
                    cur+='w';
                }else{
                    origen2.x=origen.x;
                    coords2.x=coords.x-3;
                    cur+='e';
                }
                over.style.cursor=cur+'-resize';
                l.style.top=t.style.top=r.style.top=origen2.y+'px';
                l.style.left=t.style.left=b.style.left=origen2.x+'px';
                r.style.left=coords2.x+'px';
                b.style.top=coords2.y+'px';
                l.style.height=r.style.height=Math.abs(coords2.y-origen2.y)+'px';
                t.style.width=b.style.width=Math.abs(coords2.x-origen2.x)+'px';
                t.style.height=b.style.height=l.style.width=r.style.width=0;
                if(parseInt(l.style.height)<5 || parseInt(t.style.width)<5){
                    t.style.visibility=l.style.visibility=r.style.visibility=b.style.visibility='hidden';
                    recorte=0;
                }else{
                    t.style.visibility=l.style.visibility=r.style.visibility=b.style.visibility='visible';
                    recorte=1;
                }
            }
        },
        setOrigen:function(x){
            cancelEvent(x);
            var ev=x || event;
            var o=ev.target || ev.srcElement;
            if(o!=over)return false;
            l.style.width=r.style.width=t.style.width=b.style.width=l.style.height=r.style.height=t.style.height=b.style.height=0;
            l.style.left=r.style.left=b.style.left=t.style.left=coords.x+'px';
            l.style.top=r.style.top=b.style.top=t.style.top=coords.y+'px';
            origen={x:coords.x,y:coords.y};
            renderizar=1;
            recorte=0;
            over.style.cursor='default';
            
        },
        setCoord:function(x){
            cancelEvent(x);
            clearSelection();
            var ev=x || event;
            var o=ev.target || ev.srcElement;
            var posX=ev.layerX || ev.offsetX || 0; 
            var posY=ev.layerY || ev.offsetY || 0; 
            coords={x:posX,y:posY};
            if(o==over)
                mp.render();
            
        },
        addEvent: function(type, fn,o ) {
            if ( o.addEventListener ) {
                o.addEventListener( type, fn, false );
            } else if(o.attachEvent){
                var O=o;
                var f= function(){fn.call(O,window.event);}
                o.attachEvent( 'on'+type, f);
                o[fn.toString()+type]=f;
            }else{
                o['on'+type]=fn;
            }
            var ev={_obj:this,_evType:type,_fn:fn};
            window.EvRegister=window.EvRegister || [];
            window.EvRegister.push(ev);
        },
        getElementPosition:function(o) {
            var offsetTrail = o;
            var offsetLeft = 0;
            var offsetTop = 0;
            while (offsetTrail) {
                offsetLeft += offsetTrail.offsetLeft;
                offsetTop += offsetTrail.offsetTop;
                offsetTrail = offsetTrail.offsetParent;
            }
            return {left:offsetLeft, top:offsetTop};
        }
    };
    return {
        setTarget:function(id){
            if(!document.getElementById(id)){
                throw new Error('El elemento no existe o no posee atributo id');
            }else if(document.getElementById(id).nodeName.toLowerCase()!='img'){
                throw new Error('El elemento no es una imagen');
            }else{
                mp.iniciar(document.getElementById(id));
            }
        },
        getCoords:function(){
            if(recorte)
                return {xo:origen2.x,yo:origen2.y,xd:coords2.x,yd:coords2.y}
            return 0;
        }
        
    }
})();
DR(
   function(){
       crop.setTarget('arw');//seteamos la imagen a cropear indicando su id
    }
);
function cropear(){
    /*---obtenemos las coordenadas del cropeo:---*/
    var recorte=crop.getCoords();
    if(!recorte)return false;
    /*--- si canvas está soportado le ahorramos trabajo al servidor ---*/
    if(document.createElement('canvas').getContext){
        var canvas=document.createElement('canvas');
        canvas.width=recorte.xd-recorte.xo;
        canvas.height=recorte.yd-recorte.yo;
        var ctx=canvas.getContext('2d');
        ctx.drawImage(crop.target, recorte.xo, recorte.yo, canvas.width, canvas.height, 0, 0, canvas.width, canvas.height);
        var src=canvas.toDataURL();
    }else{
        //recortar en servidor    
    }
    /*--- opcional: mostramos la imagen---*/
    var im=document.createElement('img'); 
    im.src=src; 
    document.body.appendChild(im); 
}
</script>
</head>
<body>
<img id="arw" src="arwen.jpg" width="500" height="350">
<form action="" method="get">
<input onClick="cropear()" id="gc" name="" type="button" value="cropear">
</form>
</body>
</html> 
   
  He agregado alguna mejora 
