How can I properly write the following if statement with getLabel() - google-apps-script

I'm getting the following error and would like to know how to rewrite this code properly.
ReferenceError: Function function getLabel() {/* */} can not be used as the left-hand side of assignment or as an operand of ++ or -- operator. (line 61, file "DLContactsToSheet")
var Phones = "";
for ( var g=0;g<contacts[i].getPhones().length;g++)
{
if (contacts[i].getPhones()[g].getLabel() = "MOBILE_PHONE") {
Phones += "C: "
} else if (contacts[i].getPhones()[g].getLabel() = "WORK_PHONE") {
Phones += "W: "
} else if (contacts[i].getPhones()[g].getLabel() = "HOME_PHONE") {
Phones += "H: "
} else {
Phones += "O: "
}
Phones += contacts[i].getPhones()[g].getPhoneNumber();
Phones += "\n";
}
try{ContactArray.push(Phones);}
catch(e){ContactArray.push("N/A")}

It would appear that the reference error is caused by an '=' rather than an '==' in your conditions.
Rewriting the conditions as if (phone.getLabel() == 'MOBILE_PHONE') { /* ... */ } etc should do the trick.

You need to hard code them, in order to fetch them.
Code
function fieldType() {
var contacts = ContactsApp.getContacts(), phones = [];
for(var i = 0, iLen = contacts.length; i < iLen; i++) {
var con = contacts[i], f = ContactsApp.Field;
var c = con.getPhones(f.MOBILE_PHONE), w = con.getPhones(f.HOME_PHONE), h = con.getPhones(f.WORK_PHONE);
phones = getNumber(phones, c, "C: ");
phones = getNumber(phones, w, "W: ");
phones = getNumber(phones, h, "H: ");
}
}
function getNumber(phones, type, prefix) {
var typeNumbers = [];
var pNumber = type.length > 0 ? type.map( function (d) { return prefix + d.getPhoneNumber() + "\n"; }) : null;
if(pNumber) {
typeNumbers.push(pNumber);
}
return phones.concat(typeNumbers);
}
Note
See method description for more info: getPhoneNumber()

You should probably store the value for each iteration in a variable before any conditional statements. A case-switch statement is probably also better suited for this.
for ( var g=0;g<contacts[i].getPhones().length;g++)
{
var phone_type = contacts[i].getPhones()[g].getLabel()
switch(phone_type) {
case "MOBILE_PHONE":
Phones += "C: "
break;
case "WORK_PHONE":
Phones += "W: "
break;
case "HOME_PHONE":
Phones += "H: "
break;
default:
Phones += "O: "
}
Phones += contacts[i].getPhones()[g].getPhoneNumber();
Phones += "\n";
}

Related

Creating A Worksheet Generator

I hope you are having a great day!
I have an ecommerce website with pdfs and ebooks for sale. We are based on "education" and we have seen a few websites that have worksheet generators. We tried using httrack to see how they made the script but nothing worked. We would love some help in how does it work and are there any tutorials for that type of task. Thanks and have a great day!
Edit: We forgot to say, we want something similar to education.com
I think this code useful for you....
code.
<html>
<head>
<title>Math WorkSheet</title>
<script type="text/javascript">
// For: http://codingforums.com/showthread.php?t=184125
var NProblems = 25;
var xvals = [];
var yvals = [];
for (var i = 0; i < NProblems; i++) {
// xvals.push(i); yvals.push(i+1); // limit to problem values to (0,1) ... 25
xvals.push(i % 10);
yvals.push((i % 10) + 1); // limit to single digit problems
}
function MakeTable(act) {
var tmp = '';
var str = '<table border="1" width="80%"><tr>';
i = 0;
while (i < NProblems) {
x = xvals[i];
y = yvals[i];
str += '<td align="right">' + x;
if (act == 'add') {
str += '<br>+ ' + y;
tmp = x + y;
}
if (act == 'sub') {
str += '<br>- ' + y;
tmp = x - y;
}
if (act == 'mul') {
str += '<br>* ' + y;
tmp = x * y;
}
if (act == 'div') {
str += '<br>/ ' + y;
tmp = (x / y).toFixed(2);
}
str += '<br>_____';
if (document.getElementById('answers').checked) {
str += '<br>' + tmp;
} else {
str += '<br> '
}
str += '<br> </td>';
i++;
if ((i % 5) == 0) {
str += '</tr><tr>';
}
}
str += '</tr></table>';
return str;
}
function GenerateWS() {
var x = 0;
var y = 0;
var str = '';
var str = '';
var sel = document.getElementById('MathAction').value;
switch (sel) {
case 'add':
str += MakeTable(sel);
break;
case 'sub':
str += MakeTable(sel);
break;
case 'mul':
str += MakeTable(sel);
break;
case 'div':
str += MakeTable(sel);
break;
default:
alert('No choice selected');
break;
}
document.getElementById('TBL').innerHTML = str;
}
function randOrd() {
return (Math.round(Math.random()) - 0.5);
}
function NewSet() {
xvals.sort(randOrd);
yvals.sort(randOrd);
}
</script>
</head>
<body>
<select id="MathAction">
<option value="add">Addition</option>
<option value="sub">Subtraction</option>
<option value="mul">Multiplication</option>
<option value="div">Division</option>
</select>
<button onclick="NewSet()">New worksheet</button>
<input type="checkbox" id="answers">Show Answers
<button onclick="GenerateWS()">Generate Worksheet</button>
<div id="TBL"></div>
</body>
</html>

Hitting User Quota Limits

I'm currently using this Script to grab all my contacts into a Google Sheet. Ideally I'd like to have it run as often as possible. With a trigger set to every 1hr, I receive the following quota limit.
Temporary problem - please try again later and consider using batch operations. The user is over quota.
Is there a more efficient way to batch the following script so that it can run more often? Or maybe only when a contact has been updated/created?
function onOpen()
{
var spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
var menuEntries = [];
menuEntries.push( {name: "Read Contacts", functionName: "readContacts"} );
spreadsheet.addMenu("Contacts", menuEntries);
};
function readContacts() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var sheet = ss.getSheetByName("Contacts");
sheet.clear();
var group = ContactsApp.getContactGroup('Apptivo Contacts');
var contacts = ContactsApp.getContactsByGroup(group);
//var contacts = ContactsApp.getContacts();
var ContactArray = new Array();
var ContactArrays = [];
ContactArray = [];
ContactArray.push("");
ContactArray.push("FullName");
ContactArray.push("Emails");
ContactArray.push("PhoneNumbers");
//ContactArray.push("HomePhone");
//ContactArray.push("WorkPhone");
ContactArray.push("Company");
ContactArray.push("Job Title");
ContactArray.push("Notes");
ContactArray.push("HomeAddress");
ContactArray.push("WorkAddress");
ContactArray.push("URL");
ContactArray.push("Groups");
//ContactArray.push("Group1");
//ContactArray.push("Group2");
ContactArrays.push(ContactArray);
for (var i=0;i<contacts.length;i++)
{
ContactArray = [];
ContactArray.push("");
ContactArray.push(contacts[i].getFullName());
//Emails
var Emails = "";
for ( var g=0;g<contacts[i].getEmails().length;g++)
{
Emails += contacts[i].getEmails()[g].getAddress();
if (g + 1 == contacts[i].getEmails().length) break
Emails += "\n";
}
try{ContactArray.push(Emails);}
catch(e){ContactArray.push("N/A")}
//Phone Numbers
var Phones = "";
for ( var g=0;g<contacts[i].getPhones().length;g++)
{
if (contacts[i].getPhones()[g].getLabel() == "MOBILE_PHONE") {
Phones += "C: "
} else if (contacts[i].getPhones()[g].getLabel() == "WORK_PHONE") {
Phones += "W: "
} else if (contacts[i].getPhones()[g].getLabel() == "HOME_PHONE") {
Phones += "H: "
} else if (contacts[i].getPhones()[g].getLabel() == "HOME_FAX") {
Phones += "F: "
} else if (contacts[i].getPhones()[g].getLabel() == "WORK_FAX") {
Phones += "F: "
} else {
Phones += "O: "
}
Phones += contacts[i].getPhones()[g].getPhoneNumber();
if (g + 1 == contacts[i].getPhones().length) break
Phones += "\n" ;
}
try{ContactArray.push(Phones);}
catch(e){ContactArray.push("N/A")}
try{ContactArray.push(contacts[i].getCompanies()[0].getCompanyName());}
catch(e){ContactArray.push("N/A")}
try{ContactArray.push(contacts[i].getCompanies()[0].getJobTitle());}
catch(e){ContactArray.push("N/A")}
ContactArray.push(contacts[i].getNotes());
//Addresses
var homeAddress = "" , workAddress = "";
for ( var g=0;g<contacts[i].getAddresses().length;g++)
{
if (contacts[i].getAddresses()[g].getLabel() == "HOME_ADDRESS") {
homeAddress += contacts[i].getAddresses()[g].getAddress();
} else if (contacts[i].getAddresses()[g].getLabel() == "WORK_ADDRESS") {
workAddress += contacts[i].getAddresses()[g].getAddress();
}
}
try{ContactArray.push(homeAddress);}
catch(e){ContactArray.push("N/A")}
try{ContactArray.push(workAddress);}
catch(e){ContactArray.push("N/A")}
//ContactArray.push(contacts[i].getAddresses().getAddress());
try{ContactArray.push(contacts[i].getUrls()[0].getAddress());}
catch(e){ContactArray.push("N/A")}
var ListofGroups = "";
for ( var g=0;g<contacts[i].getContactGroups().length;g++)
{
ListofGroups += contacts[i].getContactGroups()[g].getName();
ListofGroups += " | ";
}
try{ContactArray.push(ListofGroups);}
catch(e){ContactArray.push("N/A")}
//try{ContactArray.push(contacts[i].getContactGroups()[1].getName());}
//catch(e){ContactArray.push("N/A")}
//try{ContactArray.push(contacts[i].getContactGroups()[2].getName());}
//catch(e){ContactArray.push("N/A")}
ContactArrays.push(ContactArray);
}
sheet.getRange(1,1,ContactArrays.length,ContactArrays[0].length).setValues(ContactArrays);
};
Thanks to Zaq, I reduced the number of get* calls in my script -- these calls are what drained the Google Services quota.
The script now takes a fraction of the time to run. (from 2mins to under 20sec)
Although they don't affect the quotas, I used map and join methods of JavaScript arrays to shorten some code.
My end result...
function readContacts() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var sheet = ss.getSheetByName("Contacts");
var group = ContactsApp.getContactGroup('Apptivo Contacts');
var contacts = ContactsApp.getContactsByGroup(group);
var ContactArray = new Array();
var ContactArrays = [];
ContactArray = [];
ContactArray.push("");
ContactArray.push("FullName");
ContactArray.push("Emails");
ContactArray.push("PhoneNumbers");
ContactArray.push("Company");
ContactArray.push("Job Title");
ContactArray.push("Notes");
ContactArray.push("HomeAddress");
ContactArray.push("WorkAddress");
ContactArray.push("URL");
ContactArray.push("Groups");
ContactArrays.push(ContactArray);
for (var i=0;i<contacts.length;i++)
{
ContactArray = [];
ContactArray.push("");
//FullName
ContactArray.push(contacts[i].getFullName());
//Emails
var Emails = contacts[i].getEmails().map(function(email) {
return email.getAddress();
}).join("\n");
try{ContactArray.push(Emails);}
catch(e){ContactArray.push("N/A")}
//Phone Numbers
var Phones = "";
var contactPhones = contacts[i].getPhones();
for ( var g=0;g<contactPhones.length;g++)
{
if (contactPhones[g].getLabel() == "MOBILE_PHONE") {
Phones += "C: "
} else if (contactPhones[g].getLabel() == "WORK_PHONE") {
Phones += "W: "
} else if (contactPhones[g].getLabel() == "HOME_PHONE") {
Phones += "H: "
} else if (contactPhones[g].getLabel() == "HOME_FAX") {
Phones += "F: "
} else if (contactPhones[g].getLabel() == "WORK_FAX") {
Phones += "F: "
} else {
Phones += "O: "
}
Phones += contactPhones[g].getPhoneNumber();
if (g + 1 == contactPhones.length) break
Phones += "\n" ;
}
try{ContactArray.push(Phones);}
catch(e){ContactArray.push("N/A")}
//Company
var contactCompany = contacts[i].getCompanies();
try{ContactArray.push(contactCompany[0].getCompanyName());}
catch(e){ContactArray.push("N/A")}
//JobTitle
try{ContactArray.push(contactCompany[0].getJobTitle());}
catch(e){ContactArray.push("N/A")}
//Notes
ContactArray.push(contacts[i].getNotes());
//Addresses
var homeAddress = "" , workAddress = "";
var contactAddresses = contacts[i].getAddresses();
for ( var g=0;g<contactAddresses.length;g++)
{
if (contactAddresses[g].getLabel() == "HOME_ADDRESS") {
homeAddress += contactAddresses[g].getAddress();
} else if (contactAddresses[g].getLabel() == "WORK_ADDRESS") {
workAddress += contactAddresses[g].getAddress();
}
}
//Home
try{ContactArray.push(homeAddress);}
catch(e){ContactArray.push("N/A")}
//Work
try{ContactArray.push(workAddress);}
catch(e){ContactArray.push("N/A")}
//URLs
try{ContactArray.push(contacts[i].getUrls()[0].getAddress());}
catch(e){ContactArray.push("N/A")}
//Groups
var Groups = contacts[i].getContactGroups().map(function(group) {
return group.getName();
}).join(" | ");
try{ContactArray.push(Groups);}
catch(e){ContactArray.push("N/A")}
ContactArrays.push(ContactArray);
}
//If Array is not blank(to avoid quota issues)
if (12 < ContactArrays.length) {
// Re-populate sheet
sheet.clear();
sheet.getRange(1,1,ContactArrays.length,ContactArrays[0].length).setValues(ContactArrays);
}
};

Get total rows filtered by if() statement in google apps scripts

I've got this fn().
Is there any simple way to return the number of filtered rows by this conditional statement in Google app scripts?
function getGlobers(globers, project){
var body = "";
var data = globers.getValues();
for( i = 0; i < data.length; i++ ){
if( data[i][2] == project ){
body += "<tr><td style=" + STYLE.TD + ">" + data[i].join("</td><td style=" + STYLE.TD + ">") + "</td></tr>";
}
}
return body;
}
Thanks.
for example (see comments in code)
function getGlobers(globers, project){
var body = "";
var n = 0; // use a variable to count
var data = globers.getValues();
for( i = 0; i < data.length; i++ ){
if( data[i][2] == project ){
n++;// increment each time condition is true
body += "<tr><td style=" + STYLE.TD + ">" + data[i].join("</td><td style=" + STYLE.TD + ">") + "</td></tr>";
}
}
return [body,n];// return an array of 2 values
}
Usage :
var result = getGlobers(range,project);
Logger.log('array result = '+result);
Logger.log('body (string) = '+result[0]);
Logger.log('length (integer) = '+result[1]);
note : instead of an array you could also return an object with 2 properties... a matter of choice.
EDIT : an example using object properties :
function getGlobers(globers, project){
var body = "";
var n = 0;
var result = {};
var data = globers.getValues();
for( i = 0; i < data.length; i++ ){
if( data[i][2] == project ){
n++;
body += "<tr><td style=" + STYLE.TD + ">" + data[i].join("</td><td style=" + STYLE.TD + ">") + "</td></tr>";
}
}
result['body'] = body;
result['length'] = n;
return result;
}
Usage :
var result = getGlobers(range,project);
Logger.log('body = '+result.body);
Logger.log('length = '+result.length);

Need help with setTextFormat (AS3)

I'm trying to make an rss reader with Flash CS5.5. It's almost finished but i couldn't style news titles. The problem is some parts of a textfield needs to be bold and colored. Here's my code:
var num:int = 0;
var tempText:String;
var titleStr:String;
var timeStr:String;
var descriptionStr: String;
function rssLoaded(evt:Event):void {
rssXML = XML(rssLoader.data);
// trace(rssXML);
num = 0;
for (var rssTitle:String in rssXML.channel.item) {
// Set title
tempText = rssXML.channel.item[rssTitle].title;
tempText = tempText.slice(6);
titleStr = tempText + "\r\n";
// Set description
tempText = rssXML.channel.item[num].description;
// Detect if beginning with tags
if ((tempText.charCodeAt(0) == 60) && (tempText.charCodeAt(1) == 73)) {
tempText = tempText.slice(tempText.search("/>") + 2, tempText.search("<img"));
} else {
tempText = tempText.slice(0, 140);
}
// Detect if still contains tags
if ((tempText.indexOf("<") != -1) || (tempText.indexOf(">") != -1)) {
num++;
continue;
}
// Detect if beginning with space
for (var num2:int=0; tempText.charCodeAt(0) == 32 || tempText.charCodeAt(0) == 160; num2++) {
tempText = tempText.slice(1);
}
descriptionStr = tempText + "...\r\n\r\n";
main_txt.appendText(titleStr);
main_txt.setTextFormat(title_tf, main_txt.text.length - titleStr.length, titleStr.length-2);
main_txt.appendText(descriptionStr);
num++;
}
}
var title_tf:TextFormat=new TextFormat();
title_tf.bold=true;
When I test the code, I'm seeing that only the first line is bold, while all titles needs to be bold. Sorry for my English.
Sincerely
It would be much simpler to style the text using the TextField.htmlText property:
title_tf.htmlText = "<b>" + titleTextString + "</b><br/>" + bodyTextString;
This approach would also allow you to use CSS like this:
title_tf.styleSheet = myImportedStyleSheet;
title_tf.htmlText = "<span class='titleClass'>" + titleTextString + "</span><br/><span class='bodyClass'>" + bodyTextString + "</span>";

Nine-patch images for web development [closed]

Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
We don’t allow questions seeking recommendations for books, tools, software libraries, and more. You can edit the question so it can be answered with facts and citations.
Closed 2 years ago.
Improve this question
I'm wondering if there is something like 9-patch in Android, but for web development?
Disclosure: I have no idea about web development at all, but I was curious to know if it exists. And a simple web search with the term 9-patch didn't bring up any related results, so I figured it has either another term or it doesn't exist or is not used widely enough.
Anyone knows?
Yes. It is used for border-image in CSS 3:
http://www.css3.info/preview/border-image/
http://www.w3.org/TR/css3-background/#border-images
If you're still interested I created a Javascript file that uses canvas to create real nine patch image support for the web. The open source project can be found here:
https://github.com/chrislondon/9-Patch-Image-for-Websites
Well, I took the trouble to correct deserts errors I found in the link above.
Knowing NinePath android is a useful tool adding dynamic painting and recognition of padding (which was missing in the previous pluying). I could add one few scripts for complete functionality.
Replace the following code in the library path9.js!
function NinePatchGetStyle(element, style)
{
if (window.getComputedStyle)
{
var computedStyle = window.getComputedStyle(element, "");
if (computedStyle === null)
return "";
return computedStyle.getPropertyValue(style);
}
else if (element.currentStyle)
{
return element.currentStyle[style];
}
else
{
return "";
}
}
// Cross browser function to find valid property
function NinePatchGetSupportedProp(propArray)
{
var root = document.documentElement; //reference root element of document
for (var i = 0; i < propArray.length; i++)
{
// loop through possible properties
if (typeof root.style[propArray[i]] === "string")
{
//if the property value is a string (versus undefined)
return propArray[i]; // return that string
}
}
return false;
}
/**
* 9patch constructer. Sets up cached data and runs initial draw.
* #param {Dom Element} div El Elemento dom en donde se pinta el ninepath
* #param {function} callback La funcion que se llamara cuando se termina
* la carga de la imagen y el pintado del elemento div.
* #returns {NinePatch} Un objeto nine path
*/
function NinePatch(div,callback)
{
this.div = div;
this.callback =callback;
this.padding = {top:0,left:0,right:0,bottom:0};
// Load 9patch from background-image
this.bgImage = new Image();
this.bgImage.src = NinePatchGetStyle(this.div, 'background-image').replace(/"/g, "").replace(/url\(|\)$/ig, "");
var este = this;
this.bgImage.onload = function()
{
este.originalBgColor = NinePatchGetStyle(este.div, 'background-color');
este.div.style.background = 'none';
// Create a temporary canvas to get the 9Patch index data.
var tempCtx, tempCanvas;
tempCanvas = document.createElement('canvas');
tempCanvas.width = este.bgImage.width;
tempCanvas.height = este.bgImage.height;
tempCtx = tempCanvas.getContext('2d');
tempCtx.drawImage(este.bgImage, 0, 0);
// Obteniendo el padding lateral derecho
var dataPad = tempCtx.getImageData(este.bgImage.width-1,0,1,este.bgImage.height).data;
var padRight = este.getPadBorder(dataPad,este.bgImage.width,este.bgImage.height);
este.padding.top = padRight.top;
este.padding.bottom = padRight.bottom;
dataPad = tempCtx.getImageData(0,este.bgImage.height-1,este.bgImage.width,1).data;
var padBottom = este.getPadBorder(dataPad,este.bgImage.width,este.bgImage.height);
este.padding.left = padBottom.top;
este.padding.right = padBottom.bottom;
// Loop over each horizontal pixel and get piece
var data = tempCtx.getImageData(0, 0, este.bgImage.width, 1).data;
// Use the upper-left corner to get staticColor, use the upper-right corner
// to get the repeatColor.
var tempLength = data.length - 4;
var staticColor = data[0] + ',' + data[1] + ',' + data[2] + ',' + data[3];
var repeatColor = data[tempLength] + ',' + data[tempLength + 1] + ',' +
data[tempLength + 2] + ',' + data[tempLength + 3];
este.horizontalPieces = este.getPieces(data, staticColor, repeatColor);
// Loop over each horizontal pixel and get piece
data = tempCtx.getImageData(0, 0, 1, este.bgImage.height).data;
este.verticalPieces = este.getPieces(data, staticColor, repeatColor);
// use this.horizontalPieces and this.verticalPieces to generate image
este.draw();
este.div.onresize = function()
{
este.draw();
};
if(callback !== undefined)
{
if (typeof(callback) === "function")
callback();
}
};
}
// Stores the HTMLDivElement that's using the 9patch image
NinePatch.prototype.div = null;
// Padding
NinePatch.prototype.padding = null;
// Get padding
NinePatch.prototype.callback = null;
// Stores the original background css color to use later
NinePatch.prototype.originalBG = null;
// Stores the pieces used to generate the horizontal layout
NinePatch.prototype.horizontalPieces = null;
// Stores the pieces used to generate the vertical layout
NinePatch.prototype.verticalPieces = null;
// Stores the 9patch image
NinePatch.prototype.bgImage = null;
// Gets the horizontal|vertical pieces based on image data
NinePatch.prototype.getPieces = function(data, staticColor, repeatColor)
{
var tempDS, tempPosition, tempWidth, tempColor, tempType;
var tempArray = new Array();
tempColor = data[4] + ',' + data[5] + ',' + data[6] + ',' + data[7];
tempDS = (tempColor === staticColor ? 's' : (tempColor === repeatColor ? 'r' : 'd'));
tempPosition = 1;
for (var i = 4, n = data.length - 4; i < n; i += 4)
{
tempColor = data[i] + ',' + data[i + 1] + ',' + data[i + 2] + ',' + data[i + 3];
tempType = (tempColor === staticColor ? 's' : (tempColor === repeatColor ? 'r' : 'd'));
if (tempDS !== tempType)
{
// box changed colors
tempWidth = (i / 4) - tempPosition;
tempArray.push(new Array(tempDS, tempPosition, tempWidth));
tempDS = tempType;
tempPosition = i / 4;
tempWidth = 1;
}
}
// push end
tempWidth = (i / 4) - tempPosition;
tempArray.push(new Array(tempDS, tempPosition, tempWidth));
return tempArray;
};
NinePatch.prototype.getPadBorder = function(dataPad,width,height)
{
var staticRight = dataPad[0] + ',' + dataPad[1] + ',' + dataPad[2] + ',' + dataPad[3];
var pad={top:0,bottom:0};
// Padding para la parte superior
for (var i=0;i<dataPad.length;i+=4)
{
var tempColor = dataPad[i] + ',' + dataPad[i + 1] + ',' + dataPad[i + 2] + ',' + dataPad[i + 3];
if(tempColor !==staticRight)
break;
pad.top++;
}
// padding inferior
for (var i=dataPad.length-4;i>=0;i-=4)
{
var tempColor = dataPad[i] + ',' + dataPad[i + 1] + ',' + dataPad[i + 2] + ',' + dataPad[i + 3];
if(tempColor !==staticRight)
break;
pad.bottom++;
}
return pad;
};
// Function to draw the background for the given element size.
NinePatch.prototype.draw = function()
{
var dCtx, dCanvas, dWidth, dHeight;
if(this.horizontalPieces === null)
return;
dWidth = this.div.offsetWidth;
dHeight = this.div.offsetHeight;
dCanvas = document.createElement('canvas');
dCtx = dCanvas.getContext('2d');
dCanvas.width = dWidth;
dCanvas.height = dHeight;
var fillWidth, fillHeight;
// Determine the width for the static and dynamic pieces
var tempStaticWidth = 0;
var tempDynamicCount = 0;
for (var i = 0, n = this.horizontalPieces.length; i < n; i++)
{
if (this.horizontalPieces[i][0] === 's')
tempStaticWidth += this.horizontalPieces[i][2];
else
tempDynamicCount++;
}
fillWidth = (dWidth - tempStaticWidth) / tempDynamicCount;
// Determine the height for the static and dynamic pieces
var tempStaticHeight = 0;
tempDynamicCount = 0;
for (var i = 0, n = this.verticalPieces.length; i < n; i++)
{
if (this.verticalPieces[i][0] === 's')
tempStaticHeight += this.verticalPieces[i][2];
else
tempDynamicCount++;
}
fillHeight = (dHeight - tempStaticHeight) / tempDynamicCount;
// Loop through each of the vertical/horizontal pieces and draw on
// the canvas
for (var i = 0, m = this.verticalPieces.length; i < m; i++)
{
for (var j = 0, n = this.horizontalPieces.length; j < n; j++)
{
var tempFillWidth, tempFillHeight;
tempFillWidth = (this.horizontalPieces[j][0] === 'd') ?
fillWidth : this.horizontalPieces[j][2];
tempFillHeight = (this.verticalPieces[i][0] === 'd') ?
fillHeight : this.verticalPieces[i][2];
// Stretching :
if (this.verticalPieces[i][0] !== 'r') {
// Stretching is the same function for the static squares
// the only difference is the widths/heights are the same.
dCtx.drawImage(
this.bgImage,
this.horizontalPieces[j][1], this.verticalPieces[i][1],
this.horizontalPieces[j][2], this.verticalPieces[i][2],
0, 0,
tempFillWidth, tempFillHeight);
} else {
var tempCanvas = document.createElement('canvas');
tempCanvas.width = this.horizontalPieces[j][2];
tempCanvas.height = this.verticalPieces[i][2];
var tempCtx = tempCanvas.getContext('2d');
tempCtx.drawImage(this.bgImage,
this.horizontalPieces[j][1], this.verticalPieces[i][1],
this.horizontalPieces[j][2], this.verticalPieces[i][2],
0, 0,
this.horizontalPieces[j][2], this.verticalPieces[i][2]);
var tempPattern = dCtx.createPattern(tempCanvas, 'repeat');
dCtx.fillStyle = tempPattern;
dCtx.fillRect(
0, 0,
tempFillWidth, tempFillHeight);
}
// Shift to next x position
dCtx.translate(tempFillWidth, 0);
}
// shift back to 0 x and down to the next line
dCtx.translate(-dWidth, (this.verticalPieces[i][0] === 's' ? this.verticalPieces[i][2] : fillHeight));
}
// store the canvas as the div's background
var url = dCanvas.toDataURL("image/png");
var tempIMG = new Image();
var _this = this;
tempIMG.onload = function(event)
{
_this.div.style.background = _this.originalBgColor + " url(" + url + ") no-repeat";
};
tempIMG.src = url;
};
The usage is the following:
var elemDom = document.getElementById("idDiv");
var background = "border.9.png";
if (background.match(/\.9\.(png|gif)/i)) // Es nine path?
{
elemDom.style.backgroundRepeat = "no-repeat";
elemDom.style.backgroundPosition = "-1000px -1000px";
elemDom.style.backgroundImage = "url('"+background+"')";
var ninePatch = new NinePatch(elemDom,function()
{
elemDom.style.paddingLeft = ninePatch.padding.left;
elemDom.style.paddingTop = ninePatch.padding.top;
elemDom.style.paddingRight = ninePatch.padding.right;
elemDom.style.paddingBottom = ninePatch.padding.bottom;
});
}
I forked https://github.com/chrislondon/9-Patch-Image-for-Websites and fixed the bugs based on the above comments. Now the 9-Patch javascript works well. Please check out https://github.com/blackmonkey/jQuery-9-Patch