3-Dimensional Text

In the previous post, I mentioned font embedding as a way to increase the variety of a web page. Another way to do this is to use three dimensional text. Below are several different ways to do this using css or svg or combinations of the two:

click image for larger view

extrude

The first sample is created with the css text-shadow:

H1{position: absolute;  top: 345px; left: 252px; border-shadow: 5px 5px 5px #000000 color: #000000; font: italic normal 800 162px Times New Roman;}

 

The others all use extrusion:

<script type='text/javascript'>
function text() {
for (var i = 1; i <=10; i++) {
var layr = "text" + i;
var xpos = 250 + 2*i;
var ypos = 200 + i;
document.getElementById(layr).setAttributeNS(null, "x", xpos);
document.getElementById(layr).setAttributeNS(null, "y", ypos);
layr = "text2" + i;
var ypos = 360 + i;
document.getElementById(layr).setAttributeNS(null, "x", xpos);
document.getElementById(layr).setAttributeNS(null, "y", ypos);
layr = "text3" + i;
var ypos = 520 + i;
document.getElementById(layr).setAttributeNS(null, "x", xpos);
document.getElementById(layr).setAttributeNS(null, "y", ypos);
}
}function position() {
for (var i=1; i<=10; i++) {
var layr = "h1" + i;
var lft = (240 + 2* i).toString() + "px";
var tp = (610 + i).toString() + "px";
document.getElementById(layr).style.left=lft;
document.getElementById(layr).style.top=tp;
}
}
</script>
</head>
<body onload='text(); position();'>

 

The second sample is just an svg extrusion:

<text id="text1">Test</text><text id="text2">Test</text><text id="text3">Test</text><text id="text4">Test</text><text id="text5">Test</text><text id="text6">Test</text><text id="text7">Test</text><text id="text8">Test</text><text id="text9">Test</text><text id="text10">Test</text>

 

The third is an svg extrusion with blur to simulate a shadow:

<defs>
<filter id="shadow">
<feGaussianBlur stdDeviation="1.5"/>
</filter>
</defs>
<text id="text21" style="stroke: #000000; filter:url(#shadow);">Test</text><text id="text22">Test</text><text id="text23">Test</text><text id="text24">Test</text><text id="text25">Test</text><text id="text26">Test</text><text id="text27">Test</text><text id="text28">Test</text><text id="text29">Test</text><text id="text210">Test</text>

 

The fourth is an svg extrusion in combination with a css text-shadow:

body {margin-left:0;margin-right:0;font:italic normal 800 160px Times New Roman; text-shadow: -3px -2px 3px #666666; color:#EEEEEE}

<text id=”text31″>Test</text><text id=”text32″>Test</text><text id=”text33″>Test</text><text id=”text34″>Test</text><text id=”text35″>Test</text><text id=”text36″>Test</text><text id=”text37″>Test</text><text id=”text38″>Test</text><text id=”text39″>Test</text><text id=”text310″>Test</text>

&nbsp&nbsp&nbsp&nbsp&nbsp&nbsp&nbspTest

 

 

The fifth is a combination of css extrusion and css text-shadow:

#h11{position: absolute;  color: #000000; font:italic normal 800 160px Times new Roman; text-shadow: -2px -2px 2px #000000}

<div id=”h11″>Test</div><div id=”h12″>Test</div><div id=”h13″>Test</div><div id=”h14″>Test</div><div id=”h15″>Test</div><div id=”h16″>Test</div><div id=”h17″>Test</div><div id=”h18″>Test</div><div id=”h19″>Test</div><div id=”h110″>Test</div>

 

Any one of these methods can be used with an ordinary or embedded font to add a special effect to the web page.

Embedding Fonts

You have the perfect font to accentuate the theme of your site. There is a problem, however. If the reader does not have that font installed, all that will be seen on the page is a plain generic font.

You could use a graphic application to create an image with text from that font, but that would mean creating and loading a new image any time there is a text change. You could also upload the font and hope the reader downloads and installs it, but I would not want to depend on that. There is another choice: you could embed the font.

There are two ways of embedding fonts: with css and with svg.

Embedding Fonts with CSS:

The following code embeds a font with css:


<style type='text/css'>
@font-face { font-family: 'peterfontregular';
src: url('peter-webfont.eot');
src: url('peter-webfont.eot?#iefix') format('embedded-opentype'),
url('peter-webfont.woff') format('woff'),
url('peter-webfont.ttf') format('truetype'),
url('peter-webfont.svg#peterfontregular') format('svg');
font-weight: normal;
font-style: normal;
}
body {margin-left:0;margin-right:0;font:oblique normal 900 48px peterfontregular; }
a{ text-decoration: }
:link { color: rgb(0, 0, 255) }
:visited {color :rgb(100, 0,100) }
:hover { }
:active { }
div.text{position:absolute;width:60%;height:80%;left:20%;top:10%;border-width:0; padding: 20px;}
</style>
</head>
<body>
<div class=’text’>&nbsp&nbsp&nbsp&nbsp&nbsp&nbspThis is a font embedded in the html document (If you can see the unique font, it is truly embedded. I can guarantee no one else originally had this font.)
</div>

 

Here is how it appears  (I am unable to upload the html file and font file to show the actual embedding, so this is an image made from the screen of an an embedded font)

Click image for larger view

embeddedfont

The font definition goes within the style tags and once defined, the font can be used the same as any other font.

One thing to be noticed is several font formats must be uploaded and defined, since there is not universal browser support for any font extension. In particular, IE does not support ttf fonts.

SVG Font Embedding:

The SVG Text element can support font embedding by means of the <defs> tag:


<defs >
<font-face font-family="Cancun">
<font-face-src>
<font-face-uri xlink:href="cancunn.svg#CancunPlain">
<font-face-format string="svg"/>
</font-face-uri>
</font-face-src>
</font-face>
</defs>

 

The defined font face can then be used inside the <text> element.

The embedded fonts must of course be uploaded to the server, but once on the server, can be referred to repeatedly.

Also, the web fonts must be created. I use the online site Font Squirrel, which produces fonts for all browsers, as well as the required css.

Automating SVG Text with Scripting

I have previously used embedded html elements to wrap text inside an svg graphic here  and here. However, there are times when you might want to use svg text, as it has special effects not available otherwise, such as putting a border on the text.

See this example:

click image for larger view

bordertext

This still suffers from the inability to create more than one line at a time and if the line width exceeds the limit of the container, it is simply truncated.

It is possible, however, to automate some of the procedure as with the following code:


<style type='text/css'>
body {margin-left:0;margin-right:0;font:normal normal normal 12px Arial;}
a{ text-decoration: }
:link { color: rgb(0, 0, 255) }
:visited {color :rgb(100, 0,100) }
:hover { }
:active { }
.d1{position:absolute;width:800px;height:600px; left: 400px; border-style:ridge;border-width:2;font:normal normal normal 12px Arial;}
#svg1{position: absolute; width: 100%; height: 100%;  top: 0; background: #EEFFFF;}
text{fill: #EE0077; font: italic normal 900 76px Times new Roman; stroke: #000000; stroke-width: 3}
</style>
<script type='text/javascript' >
function display() {
var inc = 76;
var xpos = 15;
for (var i = 1; i <=4; i++) {
var layr = “text” + i;
var ypos =  inc * i;
document.getElementById(layr).setAttributeNS(null, “x”, xpos);
document.getElementById(layr ).setAttributeNS(null, “y”, ypos);
}
var t = document.getElementById(“text1”).firstChild;
t.nodeValue = “Hello!! This is a sample”;
t = document.getElementById(“text2″).firstChild;
t.nodeValue = ” of dynamically changing”;
t = document.getElementById(“text3”).firstChild;
t.nodeValue = “the text by means of”;
t = document.getElementById(“text4”).firstChild;
t.nodeValue = “javascript”;
}
</script>
</head>
<body  onload=’display();’>
<div class=’d1′>
<svg id=”svg1″ xmlns=”http://www.w3.org/2000/svg&#8221; version=”1.1″ width=”” height= “”>
<text id=”text1″> </text>
<text id=”text2″> </text>
<text id=”text3″> </text>
<text id=”text4″> </text>
</svg>
</div>
</body>

 

Creating css text allows the font to be set once for all the text lines;

text{fill: #EE0077; font: italic normal 900 76px Times new Roman; stroke: #000000; stroke-width: 3}

Additionally, the horizontal and vertical position for each line can be set once, rather than for each line individually;

for (var i = 1; i <=4; i++) {
var layr = “text” + i;
var ypos =  inc * i;
document.getElementById(layr).setAttributeNS(null, “x”, xpos);
document.getElementById(layr ).setAttributeNS(null, “y”, ypos);
}

Simply set the var inc to the pixel value of the font.

With only four lines of text, this is not much of a saving, but with a very large number of lines, could save a lot of data entry.

Unfortunately, it is still necessary to adjust the length of the text string for each line so that it does not exceed the container width.

Create a Container to Place Your Open Windows in Tabs

In several past posts I have ported applications originally written in c to python. This post will describe an application that remains in c.

Everyone knows the inconvenience of switching between multiple running windows. Wouldn’t it be nice if they were contained within tabs, just like web browsers? Although there are containers such as that already available, the simplicity and ease of this application (only 10 kb) make it very attractive for the DYIer.

The application has 10 tabs, each of which can be filled with a different window. The examples below have three windows in tabs, a web browser, the application that I use as my html editor and a spreadsheet.

The first shows the browser as the active tab:

click image for larger view

tab1

The second has my editor as the active tab:

click for larger view

tab2

The third has the spreadsheet as the active tab:

click for larger view

tab3

To place a window into a tab, start the tab application, which I call Tabber.exe, choose the tab, open the file or folder to be inserted and hit Ctrl + WinKey + Alt. The window will then be inserted into that tab.

I use an application called  BCX to write my c applications. It is a cross between basic and c. The syntex is basic, although it accepts straight c code if placed inside tags so indicating. Although the syntax is basic, the structure is more c like, as it has pointers, all variables must be declared and variables are c variables that must be cast to convert. It can be used with a number of c compilers; I use the lcc32 compiler, which is free for personal use and produces very compact applications. The self-written html editor I use, shown inside the second tab,  is also used to write c application source code and as a front end for the compiler.  I can therefore create c applications directly within the editor. This editor was written in BCX.

Below is the BCX code for creating Tabber.exe:


CONST sx = GetSystemMetrics(SM_CXSCREEN)
CONST sy = GetSystemMetrics(SM_CYSCREEN)
OPTION BASE 0
GUI "Form1", PIXELS
DIM Form1 AS CONTROL
DIM  tab1 as control, changetext as tabitem, iPage as integer, tab[10] as HWND
dim winAct[10] as HWND, str1$[10], tit$[10], cntr%
type tabitem
mask as integer
lpReserved1 as integer
lpReserved2 as integer
tabtext as LPSTR
maxtext as integer
iImage as integer
end type
SUB FORMLOAD
Form1 = BCX_FORM(“Tabber”,-0.001*sx,-0.006*sy, 1.002*sx, 1.013*sy)
str1$[0] = “Tab 1”
str1$[1] = “Tab 2”
str1$[2] = “Tab 3”
str1$[3] = “Tab 4”
str1$[4] = “Tab 5”
str1$[5] = “Tab 6”
str1$[6] = “Tab 7”
str1$[7] = “Tab 8”
str1$[8] = “Tab 9”
str1$[9] = “Tab 10”
tab1 = bcx_tab(Form1, 201, 10, tab, str1$, 0, 0,GetSystemMetrics(SM_CXSCREEN) – 1, GetSystemMetrics(SM_CYSCREEN) – 1)CENTER(Form1)
SHOW(Form1)
SetTimer(Form1,3000,100,(TIMERPROC) NULL)
tit$[0] = str1$[0]
changetext.tabtext = tit$[0]
changetext.maxtext = 200
changetext.mask = TCIF_TEXT
TabCtrl_SetItem(tab1 , 0, &changetext)
END SUB

BEGIN EVENTS
SELECT CASE CBMSG
case WM_TIMER
if GetAsyncKeyState(VK_MENU) <> 0 and GetAsyncKeyState(VK_LWIN) <> 0 and GetAsyncKeyState(VK_CONTROL) <> 0 then
winAct[iPage] = GetForegroundWindow()
if winAct[iPage] != 0 then
SetParent(winAct[iPage], tab[iPage])
end if
end if

case WM_NOTIFY

cntr% = 0
if wParam =  201  then
cntr% ++
if cntr% = 1 then
iPage = TabCtrl_GetCurSel(tab1)
cntr% = 0

changetext.tabtext = str1$[iPage]
GetWindowText(winAct[iPage], &tit$[iPage], 200)
changetext.tabtext = tit$[iPage]

changetext.maxtext = 200
changetext.mask = TCIF_TEXT

if len(changetext.tabtext) < 3 then
changetext.tabtext = str1$[iPage]
end if

TabCtrl_SetItem(tab1 , iPage, &changetext)
end if
end if

case WM_CLOSE
KillTimer(Form1,3000)
END SELECT
END EVENTS

A Scrolling 360° Panoramic Image

A scrolling panorama adds an interesting effect to a webpage and is quite easy to do.

Here is the code:


<!DOCTYPE html PUBLIC '-//W3C//DTD XHTML 1.0 Transitional//EN' 'http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd'>
<html xmlns='http://www.w3.org/1999/xhtml'>
<head profile='http://gmpg.org/xfn/11'>
<title>Enter Title Here</title>
<style type='text/css'>
body {margin-left:0;margin-right:0;font:normal normal normal 12px Arial; background: black}
a{ text-decoration: }
:link { color: rgb(255, 255, 255) }
:visited {color :rgb(255, 255,255) }
:hover { }
:active { }
#layer1{position:absolute;width:200%;left:0%;top:5%;border-width:0;font:normal normal normal 12px Arial;}
#layer2{position:absolute;width:200%;left:200%;top:5%;border-width:0;font:normal normal normal 12px Arial;}
</style>
<script type='text/javascript' src='JavaScripts.js'></script>
<script type='text/javascript'>
var pos1 =0; var pos2 =200; var s;
function direct1() {s= setInterval("move1()", 3);}
function move1() {
document.getElementById('layer1').style.width='100%';
document.getElementById('layer1').style.borderWidth="0";
hideLayer("layer1");
pos1 -= .01;
str1 = pos1.toString().concat("%");
document.getElementById('layer1').style.left=str1;
document.getElementById('layer2').style.width='100%';
document.getElementById('layer2').style.borderWidth="0";
hideLayer("layer2");
pos2 -= .01;
str2 = pos2.toString().concat("%");
document.getElementById('layer2').style.left=str2;
if (pos1 < -200 ){pos1 = pos2 + 200;}if (pos1 > 100 | pos1 < -200) {hideLayer("layer1");}
if (pos1<100 & pos1> -200) {showLayer("layer1");}
if (pos2 < -200 ){pos2 = pos1 + 200;}if (pos2 > 100 | pos2 < -200) {hideLayer("layer2");}
if (pos2<100 & pos2> -200) {showLayer("layer2");}
}
</script>
</head>
<body onload='direct1();'>
<div id='layer1'>
<Img SRC="Panoramas/MS-Enc-W2012.jpg" width="200%" name='image1' alt=' ' />
</div>
<div id='layer2'>
<Img SRC="Panoramas/MS-Enc-W2012.jpg" width="200%" name='image1' alt=' ' />
</div>
</body></html>

 

Two layers with the same image are created such that the left position of the second corresponds to the end of the first. Then the left position of each layer is moved to the left.When the second layer reaches the viewport, the second layer is made visible while the first layer is hidden and moved to the back of the second layer. When the first layer reaches the viewport, it is made visible while the second layer is hidden and moved again to the back of the first layer. This procedure is repeated  so long as the page is kept open.

Use this link to view an example of a scrolling Panoramic Image

Below is the image that was used for the panorama:

click image for larger view

MS-Enc-W2012

I found the best way to created the image is by conversion of a video. I used the free Microsoft Image Composite Editor (ICE) to do the conversion.