Nine-patch images for web development [closed] - html
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
Related
Problem with executing google app script (google slides) after renaming presentation and script
I'm quite new to programming and using google apps scripts. I wrote script that splits selected text in text box (google slides) in different text boxes (each line of initial textbox is a separated textbox). Code was just a modification of examples from developers.google.com. function SelectedTextGrabber() { var selection = SlidesApp.getActivePresentation().getSelection(); var selectionType = selection.getSelectionType(); var currentPage; switch (selectionType) { case SlidesApp.SelectionType.NONE: Logger.log('Nothing selected'); break; ... case SlidesApp.SelectionType.TEXT: var tableCellRange = selection.getTableCellRange(); if (tableCellRange != null) { var tableCell = tableCellRange.getTableCells()[0]; Logger.log('Selected text is in a table at row ' + tableCell.getRowIndex() + ', column ' + tableCell.getColumnIndex()); } var textRange = selection.getTextRange(); if (textRange.getStartIndex() == textRange.getEndIndex()) { Logger.log('Text cursor position: ' + textRange.getStartIndex()); } else { Logger.log('Selection is a text range from: ' + textRange.getStartIndex() + ' to: ' + textRange.getEndIndex() + ' is selected'); var s1 = textRange.asString(); var s2 = ''; var s3 = []; for (var i = 0; i < s1.length; i++){ if (s1[i] === '\n' || i === s1.length -1) { s3.push(s2); s2=''; } else { s2 += s1[i]; } } // textbox parameteres var h4 = 0; var left = 10; var top = 10; var textsize = 12; var standnum = 37; var width = 2 * textsize + (textsize - textsize % 2) / 2 * standnum; Logger.log(width); var slide = SlidesApp.getActivePresentation().getSlides()[1]; for (var i = 0; i < s3.length; i++){ //анализ размера текстового блока var s4 = s3[i].length; if (s4 <= standnum) { h4 = textsize * 2; } else { h4 = textsize * 2 + (s4 - s4 % standnum) / standnum * textsize; } var shape = slide.insertShape(SlidesApp.ShapeType.TEXT_BOX, left, top, width, h4); var textRange = shape.getText(); textRange.setText(s3[i]); textRange.getTextStyle().setFontSize(textsize); top += h4; if (top > 370) { top = 10; left += width; } } } break; case SlidesApp.SelectionType.TABLE_CELL: var tableCells = selection.getTableCellRange().getTableCells(); var table = tableCells[0].getParentTable(); Logger.log('There are ' + tableCells.length + ' table cells selected.'); break; case SlidesApp.SelectionType.PAGE: var pages = selection.getPageRange().getPages(); Logger.log('There are ' + pages.length + ' pages selected.'); break; default: break; } } It worked just fine, but when I renamed script and presentation, I get the TypeError: Cannot call method "getSelectionType" of null. (line 4, file "Code"). After 30 minutes of waiting this script started working again without errors. I thought it may happen because it takes time to make some changes in google servers. But when I modified initial text in text box to be splitted the script gave me the same result as I didn't change initial text (the result is separated lines in textboxes but for initial text). Do u have any idea what should I do to fix it?
How to change the order in which elements load on homepage?
For some reason my blog homepage starts loading half way down the page, and then slides to the top when the featured images above it have loaded. I'm not sure why it's doing this. Does anyone know how I can change the order so it loads from the first element at the top of the page? Link to blog is: https://futuremag-demo.blogspot.com
The featured post section requires JavaScript to render but currently that Javascript is executed only after all the HTML is loaded on the page (likely to prevent render blocking issues). Currently <span data-type="recent"></span> is the only HTML present in the HTML/Javascript widget which renders the featured post section. Behind the scenes, when JavaScript detects the above HTML, it makes an Ajax call to the specific Blogger feed (/feeds/posts/default?alt=json-in-script&max-results=4) to get the posts to be shown in that section. One way to resolve this problem is by moving the JS snippet responsible for rendering this featured section just after the HTML <span data-type="recent"></span> present in the widget. The specific JS snippet responsible for this section is - <script> $('.featured .HTML .widget-content').each(function() { var v = $(this).find("span").attr("data-label"), box = $(this).find("span").attr("data-type"); if (box.match('recent')) { $.ajax({ url: "/feeds/posts/default?alt=json-in-script&max-results=4", type: 'get', dataType: "jsonp", success: function(e) { var u = ""; var h = '<ul>'; for (var i = 0; i < e.feed.entry.length; i++) { for (var j = 0; j < e.feed.entry[i].link.length; j++) { if (e.feed.entry[i].link[j].rel == "alternate") { u = e.feed.entry[i].link[j].href; break } } var g = e.feed.entry[i].title.$t; var s = e.feed.entry[i].category[0].term; var y = e.feed.entry[i].author[0].name.$t; var d = e.feed.entry[i].published.$t, t = d.substring(0, 4), w = d.substring(5, 7), f = d.substring(8, 10), r = month_format[parseInt(w, 10)] + ' ' + f + ', ' + t; var c = e.feed.entry[i].content.$t; var $c = $('<div>').html(c); if (c.indexOf("//www.youtube.com/embed/") > -1) { var p = e.feed.entry[i].media$thumbnail.url; var k = p } else if (c.indexOf("<img") > -1) { var q = $c.find('img:first').attr('src'); var k = q } else { var k = no_image } h += '<li><div class="featured-inner">' + s + '<a class="rcp-thumb" href="' + u + '" style="background:url(' + k + ') no-repeat center center;background-size: cover"><span class="featured-overlay"/></a><div class="post-panel"><h3 class="rcp-title">' + g + '</h3><div class="featured-meta"><span class="featured-author idel">' + y + '</span><span class="featured-date">' + r + '</span></div></div></div></li>' } h += '</ul>'; $(".featured .HTML .widget-content").each(function() { $(this).html(h); $(this).find('.rcp-thumb').each(function() { $(this).attr('style', function(i, src) { return src.replace('/default.jpg', '/mqdefault.jpg') }).attr('style', function(i, src) { return src.replace('s72-c', 's1600') }) }) }) } }) } else if (box.match('label')) { $.ajax({ url: "/feeds/posts/default/-/" + v + "?alt=json-in-script&max-results=4", type: 'get', dataType: "jsonp", success: function(e) { var u = ""; var h = '<ul>'; for (var i = 0; i < e.feed.entry.length; i++) { for (var j = 0; j < e.feed.entry[i].link.length; j++) { if (e.feed.entry[i].link[j].rel == "alternate") { u = e.feed.entry[i].link[j].href; break } } var g = e.feed.entry[i].title.$t; var s = e.feed.entry[i].category[0].term; var y = e.feed.entry[i].author[0].name.$t; var d = e.feed.entry[i].published.$t, t = d.substring(0, 4), w = d.substring(5, 7), f = d.substring(8, 10), r = month_format[parseInt(w, 10)] + ' ' + f + ', ' + t; var c = e.feed.entry[i].content.$t; var $c = $('<div>').html(c); if (c.indexOf("//www.youtube.com/embed/") > -1) { var p = e.feed.entry[i].media$thumbnail.url; var k = p } else if (c.indexOf("<img") > -1) { var q = $c.find('img:first').attr('src'); var k = q } else { var k = no_image } h += '<li><div class="featured-inner">' + s + '<a class="rcp-thumb" href="' + u + '" style="background:url(' + k + ') no-repeat center center;background-size: cover"><span class="featured-overlay"/></a><div class="post-panel"><h3 class="rcp-title">' + g + '</h3><div class="featured-meta"><span class="featured-author idel">' + y + '</span><span class="featured-date">' + r + '</span></div></div></div></li>' } h += '</ul>'; $(".featured .HTML .widget-content").each(function() { $(this).html(h); $(this).find('.rcp-thumb').each(function() { $(this).attr('style', function(i, src) { return src.replace('/default.jpg', '/mqdefault.jpg') }).attr('style', function(i, src) { return src.replace('s72-c', 's1600') }) }) }) } }) } });
After analyzing the website, it's found that the said images have big sizes which makes them load slowly. They can be compressed using a technique called lossless compression to minimize the size without distorting the resolution of the image. Compress your images using (for example): https://compressjpeg.com/ and test again.
Execute Code as Fast as Possible
I am using node.js with my WebStorm IDE to parse a large JSON file (~500 megabytes). Here is my code: fs = require("fs"); fs.readFile('C:/Users/.../Documents/AAPL.json', 'utf8', function (err,data) { for (i = 0; i < 1000; i++) { var hex = JSON.parse(data)[i]._source.layers.data["data.data"]; var askPrice = parseInt(hex.substring(215, 239).split(":").reverse().join(""),16); var bidPrice = parseInt(hex.substring(192, 215).split(":").reverse().join(""),16); var symbol = hex.substring(156, 179); var timestamp = hex.substring(132, 155); var askSize = hex.substring(240, 251); var bidSize = hex.substring(180, 191); var price = String((+bidPrice+askPrice)/2); var realprice = price.slice(0, price.length - 4) + "." + price.slice(price.length - 4); function hex2a(hexx) { var hex = hexx.toString(); var str = ''; for (var i = 0; i < hex.length; i += 2) str += String.fromCharCode(parseInt(hex.substr(i, 2), 16)); return str; } if(JSON.parse(data)[i]._source.layers.data["data.len"] == 84 && realprice.length == 8 && +realprice <154 && +realprice >145) { console.log(i + " " + hex2a(symbol.replace(/:/g, "")) + " sold for " + realprice + " at " + parseInt(timestamp.split(":").reverse().join(""), 16)); } } }); The problem I am running into however is that my IDE is parsing this file at an extremely slow speed, roughly 1 iteration a second. I do not think this is because I have a slow computer, for I have a high end rig with a core i7 7700k and a gtx 1070. I tried executing the code in the console with the same result. I tried trimming down the code and again I achieved the same speed: fs = require("fs"); fs.readFile('C:/Users/Brandt Winkler Prins/Documents/AAPL.json', 'utf8', function (err,data) { for (i = 0; i < 12000; i++) { var hex = JSON.parse(data)[i]._source.layers.data["data.data"]; var askPrice = parseInt(hex.substring(215, 239).split(":").reverse().join(""),16); var bidPrice = parseInt(hex.substring(192, 215).split(":").reverse().join(""),16); var price = String((+bidPrice+askPrice)/2); var realprice = price.slice(0, price.length - 4) + "." + price.slice(price.length - 4); if(+realprice <154 && +realprice >145) { console.log(realprice); } } }); How should I execute my code to get my data as fast as possible?
You're running JSON.parse(data) every iteration, that might take quite some time for a 500MB json file. The solution would be to move it out of the loop and reuse the parsed object: var obj = JSON.parse(data); for (...
Esri map with flex show name on navigator instead of coordinates
I am using com.esri.ags.components.directions on esri map and I added the stops by coordinates. So how can I assign a name to the stop so it will be showing on screen and when printing instead of coordinates? This is the code I added the stops into var stop:DirectionsStop = mainUIComponent.myDirections.stopProvider[0]; stop.editable = false; stop.searchTerm = UserSession.getCurrentUserDTO().dealerCoordinatesDTO.AddressLongitude + "," + UserSession.getCurrentUserDTO().dealerCoordinatesDTO.AddressLatitude; var stopCount:int=1; for( var i:int=0; i < customersToVisitsList.length; i++) { var point:DealerQuestMapPoint=new DealerQuestMapPoint( customersToVisitsList[i].addressLongitude,customersToVisitsList[i].addressLatitude); point.pointType="CUSTOMER"; point.targetObject=customersToVisitsList[i]; point.address = customersToVisitsList[i].address; var imageTooltip:String//="Test"; customersToVisitsList[i].customerName.toString() +"\n"+customersToVisitsList[i].address.toString() +", "+customersToVisitsList[i].city.toString() +"\n"+customersToVisitsList[i].state.toString() +", "+customersToVisitsList[i].zip.toString(); renderMapPoint(mainUIComponent.customersLayer, point, customersToVisitsList[i].customer_id, imageTooltip, customersToVisitsList[i], mainUIComponent.blueSymbol); if(i==0) { var stop1:DirectionsStop = mainUIComponent.myDirections.stopProvider[1]; stop1.editable = true; stop1.searchTerm = point.lon.toString() + "," + point.lat.toString(); stop1.name = customersToVisitsList[i].customerName.toString(); } else { stopCount+=1; var st:DirectionsStop = new DirectionsStop(); st.editable = true; st.searchTerm = point.lon.toString() + "," + point.lat.toString(); st.name = customersToVisitsList[i].customerName.toString(); mainUIComponent.myDirections.stopProvider.addItem(st); } } mainUIComponent.myDirections.getDirections(); I checked the documentation and I found nothing to do this because usually they deal with address but dealing with coordinates makes it a must to rename it to another name. Screenshot of the map with coordinates written
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>";