Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

jQuery CSS plugin that returns computed style of element to pseudo clone that element?

I'm looking for a way using jQuery to return an object of computed styles for the 1st matched element. I could then pass this object to another call of jQuery's css method.

For example, with width, I can do the following to make the 2 divs have the same width:

$('#div2').width($('#div1').width()); 

It would be nice if I could make a text input look like an existing span:

$('#input1').css($('#span1').css()); 

where .css() with no argument returns an object that can be passed to .css(obj).

(I can't find a jQuery plugin for this, but it seems like it should exist. If it doesn't exist, I'll turn mine below into a plugin and post it with all the properties that I use.)

Basically, I want to pseudo clone certain elements but use a different tag. For example, I have an li element that I want to hide and put an input element over it that looks the same. When the user types, it looks like they are editing the element inline.

I'm also open to other approaches for this pseudo cloning problem for editing. Any suggestions?

Here's what I currently have. The only problem is just getting all the possible styles. This could be a ridiculously long list.


jQuery.fn.css2 = jQuery.fn.css; jQuery.fn.css = function() {     if (arguments.length) return jQuery.fn.css2.apply(this, arguments);     var attr = ['font-family','font-size','font-weight','font-style','color',     'text-transform','text-decoration','letter-spacing','word-spacing',     'line-height','text-align','vertical-align','direction','background-color',     'background-image','background-repeat','background-position',     'background-attachment','opacity','width','height','top','right','bottom',     'left','margin-top','margin-right','margin-bottom','margin-left',     'padding-top','padding-right','padding-bottom','padding-left',     'border-top-width','border-right-width','border-bottom-width',     'border-left-width','border-top-color','border-right-color',     'border-bottom-color','border-left-color','border-top-style',     'border-right-style','border-bottom-style','border-left-style','position',     'display','visibility','z-index','overflow-x','overflow-y','white-space',     'clip','float','clear','cursor','list-style-image','list-style-position',     'list-style-type','marker-offset'];     var len = attr.length, obj = {};     for (var i = 0; i < len; i++)          obj[attr[i]] = jQuery.fn.css2.call(this, attr[i]);     return obj; } 

Edit: I've now been using the code above for awhile. It works well and behaves exactly like the original css method with one exception: if 0 args are passed, it returns the computed style object.

As you can see, it immediately calls the original css method if that's the case that applies. Otherwise, it gets the computed styles of all the listed properties (gathered from Firebug's computed style list). Although it's getting a long list of values, it's quite fast. Hope it's useful to others.

like image 604
Keith Bentrup Avatar asked Jun 16 '09 23:06

Keith Bentrup


2 Answers

Two years late, but I have the solution you're looking for. Here's a plugin I wrote (by wrapping another guy's function in plugin format) which does exactly what you want, but gets all possible styles in all browsers, even IE.

jquery.getStyleObject.js:

/*  * getStyleObject Plugin for jQuery JavaScript Library  * From: http://upshots.org/?p=112  *  * Copyright: Unknown, see source link  * Plugin version by Dakota Schneider (http://hackthetruth.org)  */  (function($){     $.fn.getStyleObject = function(){         var dom = this.get(0);         var style;         var returns = {};         if(window.getComputedStyle){             var camelize = function(a,b){                 return b.toUpperCase();             }             style = window.getComputedStyle(dom, null);             for(var i=0;i<style.length;i++){                 var prop = style[i];                 var camel = prop.replace(/\-([a-z])/g, camelize);                 var val = style.getPropertyValue(prop);                 returns[camel] = val;             }             return returns;         }         if(dom.currentStyle){             style = dom.currentStyle;             for(var prop in style){                 returns[prop] = style[prop];             }             return returns;         }         return this.css();     } })(jQuery); 

Basic usage is pretty simple:

var style = $("#original").getStyleObject(); // copy all computed CSS properties $("#original").clone() // clone the object     .parent() // select it's parent     .appendTo() // append the cloned object to the parent, after the original                 // (though this could really be anywhere and ought to be somewhere                 // else to show that the styles aren't just inherited again     .css(style); // apply cloned styles 

Hope that helps.

like image 81
Dakota Avatar answered Oct 17 '22 22:10

Dakota


It's not jQuery but, in Firefox, Opera and Safari you can use window.getComputedStyle(element) to get the computed styles for an element and in IE<=8 you can use element.currentStyle. The returned objects are different in each case, and I'm not sure how well either work with elements and styles created using Javascript, but perhaps they'll be useful.

In Safari you can do the following which is kind of neat:

document.getElementById('b').style.cssText = window.getComputedStyle(document.getElementById('a')).cssText; 
like image 25
Richard M Avatar answered Oct 17 '22 22:10

Richard M