Thursday 7 January 2010
A new blog about Iphone development
Par Vincent DEMAY, Thursday 7 January 2010 :: Wicket
- all Iphone API I find
- Some tips about Iphone
- Some development I make
I'll continue to populate this blog with other topics Cheers
Thursday 7 January 2010
Par Vincent DEMAY, Thursday 7 January 2010 :: Wicket
Thursday 31 July 2008
Par Vincent DEMAY, Thursday 31 July 2008 :: Wicket
[code java]
package net.demay.fr.wicket;
/**
* A link asking a javascript confirmation before acting
*
* @author Vincent Demay
*
*/
public abstract class ConfirmLink extends Link {
public ConfirmLink(String id) {
super(id);
add(new JsConfirm("onclick", "are you sure?"));
}
@Override
public abstract void onClick();
/**
* an attribute modifier adding confirmation on an event.
*
* @author Vincent Demay
*
*/
public class JsConfirm extends AttributeModifier {
public JsConfirm(String event, String msg) {
super(event, true, new Model(msg));
}
protected String newValue(final String currentValue, final String replacementValue) {
String result = "if (confirm('" + replacementValue + "'))";
if (currentValue != null) {
result = result + "{" + currentValue + "}; return false;";
}
return result;
}
}
}
Friday 7 December 2007
Par Vincent DEMAY, Friday 7 December 2007 :: Wicket
package net.demay.fr.component.ajax.upload;
import org.apache.wicket.Page;
import org.apache.wicket.ajax.AbstractDefaultAjaxBehavior;
import org.apache.wicket.ajax.AjaxRequestTarget;
import org.apache.wicket.markup.ComponentTag;
import org.apache.wicket.markup.MarkupStream;
import org.apache.wicket.markup.html.WebComponent;
import org.apache.wicket.markup.html.WebPage;
import org.apache.wicket.markup.html.form.upload.FileUpload;
import org.apache.wicket.markup.html.link.IPageLink;
import org.apache.wicket.markup.html.link.InlineFrame;
import org.apache.wicket.markup.html.panel.Panel;
/**
* A panel allowing to upload file in an iframe. This panel can be used to
* upload file in a "Ajax way" : page does not need to be reloaded. Only the iframe is reloaded
*
* @author Vincent Demay
*
*/
@SuppressWarnings("serial")
public abstract class UploadPanel extends Panel {
private InlineFrame uploadIFrame = null;
public UploadPanel(String id) {
super(id);
addOnUploadedCallback();
setOutputMarkupId(true);
}
/**
* Called when the upload load is uploaded and ready to be used
* Return the url of the new uploaded resource
* @param upload {@link FileUpload}
*/
public abstract String onFileUploaded(FileUpload upload);
/**
* Called once the upload is finished and the traitment of the
* {@link FileUpload} has been done in {@link UploadPanel#onFileUploaded}
* @param target an {@link AjaxRequestTarget}
* @param fileName name of the file on the client side
* @param newFileUrl Url of the uploaded file
*/
public abstract void onUploadFinished(AjaxRequestTarget target, String filename, String newFileUrl);
protected void onBeforeRender() {
super.onBeforeRender();
if (uploadIFrame == null) {
// the iframe should be attached to a page to be able to get its pagemap,
// that's why i'm adding it in onBeforRender
addUploadIFrame();
}
}
/**
* Create the iframe containing the upload widget
*
*/
private void addUploadIFrame() {
IPageLink iFrameLink = new IPageLink() {
public Page getPage() {
return new UploadIFrame() {
@Override
protected String getOnUploadedCallback() {
return "onUpload_" + UploadPanel.this.getMarkupId();
}
@Override
protected String manageInputSream(FileUpload upload) {
return UploadPanel.this.onFileUploaded(upload);
}
};
}
public Class extends WebPage> getPageIdentity() {
return UploadIFrame.class;
}
};
uploadIFrame = new InlineFrame("upload", getPage().getPageMap(), iFrameLink);
add(uploadIFrame);
}
/**
* Hackie method allowing to add a javascript in the page defining the
* callback called by the innerIframe
*
*/
private void addOnUploadedCallback() {
final OnUploadedBehavior onUploadBehavior = new OnUploadedBehavior();
add(onUploadBehavior);
add(new WebComponent("onUploaded") {
protected void onComponentTagBody(MarkupStream markupStream, ComponentTag openTag) {
// calling it through setTimeout we ensure that the callback is called
// in the proper execution context, that is the parent frame
replaceComponentTagBody(markupStream, openTag,
"function onUpload_" + UploadPanel.this.getMarkupId() +
"(clientFileName, newFileUrl) {window.setTimeout(function() { " +
onUploadBehavior.getCallback() + " }, 0 )}");
}
});
}
private class OnUploadedBehavior extends AbstractDefaultAjaxBehavior {
public String getCallback() {
return generateCallbackScript(
"wicketAjaxGet('" + getCallbackUrl(false) +
"&newFileUrl=' + encodeURIComponent(newFileUrl)" +
" + '&clientFileName=' + encodeURIComponent(clientFileName)").toString();
}
protected void respond(AjaxRequestTarget target) {
UploadPanel.this.onUploadFinished(target, getRequest().getParameter("clientFileName"), getRequest().getParameter("newFileUrl"));
}
};
}
UploadPanel.html
<html xmlns:wicket> <wicket:panel> <!-- I put the callback snippet at the body so that is rendered for each panel instead of once --> <script wicket:id="onUploaded" type="text/javascript"></script> <iframe wicket:id="upload" frameborder="0" height="55" width="450" style="overflow:hidden"></iframe> </wicket:panel> </html>UploadIFrame.java
package net.demay.fr.component.ajax.upload;
import org.apache.wicket.ajax.AjaxRequestTarget;
import org.apache.wicket.markup.ComponentTag;
import org.apache.wicket.markup.MarkupStream;
import org.apache.wicket.markup.html.WebComponent;
import org.apache.wicket.markup.html.WebPage;
import org.apache.wicket.markup.html.form.Form;
import org.apache.wicket.markup.html.form.upload.FileUpload;
import org.apache.wicket.markup.html.form.upload.FileUploadField;
import org.apache.wicket.model.ResourceModel;
/**
* A webPage to be used in an iframe in order to simulate
* an ajax file upload
* @author doume
*
*/
@SuppressWarnings("serial")
public abstract class UploadIFrame extends WebPage {
private boolean uploaded = false;
private FileUploadField uploadField;
private String newFileUrl;
public UploadIFrame() {
add(new UploadForm("form"));
addOnUploadedCallback();
}
/**
* return the callback url when upload is finished
* @return callback url when upload is finished
*/
protected abstract String getOnUploadedCallback();
/**
* Called when the input stream has been uploaded and when it is available
* on server side
* return the url of the uploaded file
* @param upload fileUpload
*/
protected abstract String manageInputSream(FileUpload upload);
private class UploadForm extends Form {
public UploadForm(String id) {
super(id);
uploadField = new FileUploadField("file");
add(uploadField);
add(new AjaxLink("submit"){
@Override
protected void onClick(AjaxRequestTarget target) {
target.appendJavascript("showProgressWheel()");
}
});
}
public void onSubmit() {
FileUpload upload = uploadField.getFileUpload();
newFileUrl = manageInputSream(upload);
//file is now uploaded, and the IFrame will be reloaded, during
//reload we need to run the callback
uploaded = true;
}
}
private void addOnUploadedCallback() {
//a hacked component to run the callback on the parent
add(new WebComponent("onUploaded") {
protected void onComponentTagBody(MarkupStream markupStream, ComponentTag openTag) {
if (uploaded) {
if (uploadField.getFileUpload() != null){
replaceComponentTagBody(markupStream, openTag,
"window.parent." + getOnUploadedCallback() + "('" +
uploadField.getFileUpload().getClientFileName() + "','" +
newFileUrl +"')");
}
uploaded = false;
}
}
});
}
}
UploadIframe.html
<html xmlns:wicket>
<head>
<script type="text/javascript">
function showProgressWheel() {
document.images[0].style.display = 'block';
// delay the wheel a bit so it can locally shine
setTimeout(function() { document.forms[0].submit() }, 800);
return false;
}
</script>
</head>
<body>
<form wicket:id="form">
<table>
<tr>
<td>
<input wicket:id="file" type="file"/>
</td>
<td>
<table wicket:id="submit"></table>
</td>
<td>
<img src="indicator.gif" style="display:none"/>
</td>
</tr>
</table>
</form>
<script wicket:id="onUploaded" type="text/javascript">
</body>
</html>
Usage
final UploadPanel upload = new UploadPanel("myUpload"){
@Override
public String onFileUploaded(FileUpload upload) {
if (upload != null){
try {
//save on server side here
//and return the url of the saved file
return savedFile.getUrl()
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
return "";
}
@Override
public void onUploadFinished(AjaxRequestTarget target, String filename, String newFileUrl) {
//when upload is finished, will be called
}
};
Monday 22 October 2007
Par Vincent DEMAY, Monday 22 October 2007 :: Wicket

<html>
<head>
<style type="text/css">
div.tableContainer {
width: 500px; /* table width will be 99% of this*/
height: 290px; /* must be greater than tbody*/
overflow: auto;
margin: 0 auto;
}
table {
width: 99%; /*100% of container produces horiz. scroll in Mozilla*/
border: none;
background-color: #f7f7f7;
}
/*
* Specific Firefox. Only Modern browser are able to interpret > . IE is not a modern browser
*/
table>tbody {
overflow: auto;
height: 250px;
overflow-x: hidden;
}
/*
* Traget is IE5+ only. Only IE is able to interpret this kind of horrible expression Script
* ----------
* FOR HEADER
*/
thead tr {
position:relative;
top: expression(offsetParent.scrollTop);
}
/*
* Traget is IE5+ only. Only IE is able to interpret this kind of horrible expression Script
* ----------
* FOR FOOTER
* ----------
* Some explaination :
* with pseudo code :
* if (scroll_is_needed){
* top = container_height + table_scrollTop - table_Height
* } else {
* //tfoot should be at the same place if there is a scroll or not
* top = container_height - table_height;
* }
*/
table tfoot tr {
position: relative;
overflow-x: hidden;
top: expression(parentNode.parentNode.offsetHeight >= offsetParent.offsetHeight ?
offsetParent.offsetHeight + offsetParent.scrollTop - parentNode.parentNode.offsetHeight :
offsetParent.offsetHeight - parentNode.parentNode.offsetHeight);
}
/*
* Classical Css
*/
thead td, thead th, tfoot td {
text-align: center;
background-color: #C3C3C3;
font-size : 12px;
color: white;
font-weight: bold;
border-top: solid 1px gray;
}
td {
color: #666666;
padding-right: 2px;
text-align: center;
font-size : 12px;
border-bottom: solid 1px #C3C3C3; /* Do not mark double boder */
border-left: solid 1px #C3C3C3;
}
/*
* FF scroll hide last column.
* prevent this case
*/
td:last-child {
padding-right: 20px;
}
</style>
</head>
<body>
<div class="tableContainer">
<table cellspacing="0">
<thead>
<tr>
<td width="30%">Header cell1</td>
<td width="30%">Header cell2</td>
<td width="20%">Header cell3</td>
<td width="20%">Header cell 4</td>
</tr>
</thead>
<tbody>
<tr>
<td>a</td>
<td>a</td>
<td>a</td>
<td>a</td>
</tr>
...
<tr>
<td>z</td>
<td>z</td>
<td>z</td>
<td>z</td>
</tr>
</tbody>
<tfoot>
<tr>
<td colspan="5">Table footer repeats on print</td>
</tr>
</tfoot>
</table>
</div>
</div>
</body>
</html>
Monday 3 September 2007
Par Vincent DEMAY, Monday 3 September 2007 :: Wicket
[java]
package com.theveniceproject.cow.editors.ui.widgets;
import java.util.List;
import org.apache.wicket.ResourceReference;
import org.apache.wicket.behavior.AttributeAppender;
import org.apache.wicket.behavior.HeaderContributor;
import org.apache.wicket.extensions.markup.html.tabs.AbstractTab;
import org.apache.wicket.extensions.markup.html.tabs.ITab;
import org.apache.wicket.markup.ComponentTag;
import org.apache.wicket.markup.MarkupStream;
import org.apache.wicket.markup.html.WebMarkupContainer;
import org.apache.wicket.markup.html.basic.Label;
import org.apache.wicket.markup.html.list.Loop;
import org.apache.wicket.markup.html.panel.Panel;
import org.apache.wicket.model.AbstractReadOnlyModel;
import org.apache.wicket.model.IModel;
import org.apache.wicket.model.Model;
public class TabPanel extends Panel {
private List tabs;
private IModel tabCount;
private static final ResourceReference DEFAULT_CSS = new ResourceReference(LeftTabPanel.class, "css/TabPanel.css");
public TabPanel(String id, List<AbstractTab> tabs) {
super(id, new Model());
setOutputMarkupId(true);
checkTabs(tabs);
add(HeaderContributor.forCss(getCss()));
add(HeaderContributor.forJavaScript(LeftTabPanel.class, "TabPanel.js"));
//create a model for the tabs size
this.tabs = tabs;
tabCount = new AbstractReadOnlyModel()
{
private static final long serialVersionUID = 1L;
public Object getObject()
{
return new Integer(LeftTabPanel.this.tabs.size());
}
};
createTabs();
createContents();
}
/**
* Return the css to use to layout tabs
* @return the css to use to layout tabs
*/
public ResourceReference getCss() {
return DEFAULT_CSS;
}
@Override
protected void onComponentTagBody(MarkupStream markupStream, ComponentTag openTag) {
// TODO Auto-generated method stub
super.onComponentTagBody(markupStream, openTag);
getResponse().write("<script type=\"text/javascript\">var " + getMarkupId() + "Tabs = new TabManager('" + getMarkupId() + "'); ");
}
/**
* Method to check if tabs is all rightd
* @param tabs tabs list
*/
private void checkTabs(List<AbstractTab> tabs){
if (tabs == null)
{
throw new IllegalArgumentException("argument [tabs] cannot be null");
}
if (tabs.size() < 1)
{
throw new IllegalArgumentException(
"argument [tabs] must contain a list of at least one tab");
}
}
/**
* Create tabs on the left of the component
* @param tabsContainer
*/
protected void createTabs(){
add(new Loop("tabs", tabCount)
{
private static final long serialVersionUID = 1L;
protected void populateItem(LoopItem item)
{
final int index = item.getIteration();
final ITab tab = ((ITab)LeftTabPanel.this.tabs.get(index));
final boolean selected = index == 0;
WebMarkupContainer tabContent = new WebMarkupContainer("tab"){
@Override
protected void onComponentTag(ComponentTag tag) {
super.onComponentTag(tag);
tag.put("class", "tabs");
//connect onClick event
tag.put("onClick", LeftTabPanel.this.getMarkupId() + "Tabs.selectTab(this)");
}
@Override
protected void onBeforeRender() {
super.onBeforeRender();
if (selected){
add(new AttributeAppender("class", new Model("selected"), " "));
}
}
};
tabContent.add(new Label("title", tab.getTitle()));
item.add(tabContent);
}
});
}
/**
* Create the tab content using {@link AbstractTab} Panel
*/
private void createContents(){
add(new Loop("contents", tabCount)
{
private static final long serialVersionUID = 1L;
protected void populateItem(LoopItem item)
{
final int index = item.getIteration();
final ITab tab = ((ITab)LeftTabPanel.this.tabs.get(index));
final boolean selected = index == 0;
item.add(tab.getPanel("innerPanel"));
if (!selected){
item.add(new AttributeAppender("style", true, new Model("display:none"), ";"));
}
}
});
}
}
<wicket:panel> <table width="100%" class="leftTab" cellpadding="0" cellspacing="0"> <tr valign="top"> <td width="120px"> <div wicket:id="tabs"> <div wicket:id="tab"> <span wicket:id="title"></span> </div> </div> </td> <td> <div class="content"> <div wicket:id="contents"> <div wicket:id="innerPanel"> content </div> </div> </div> </td> </tr> </table> </wicket:panel>
function TabManager(/**String*/ id){
this.id = id;
this.table = document.getElementById(id).getElementsByTagName("table")[0];
/**
* Select the given tab and show its content
*/
this.selectTab = function(/** div */ tab){
this._clearSelected();
addClass(tab, "selected");
this.setContentSelected(tab);
}
/**
* Return the list of domNode representing tabs
*/
this._getTabs /** Node[] */ = function(){
return this.table.rows.item(0).cells.item(0).childNodes;
}
/**
* return the list of domNode Representing Content
*/
this._getContents /** Node[] */ = function(){
return this.table.rows.item(0).cells.item(1).getElementsByTagName("div")[0].childNodes;
}
/**
* Clear Selection
*/
this._clearSelected = function(){
var tabs = this._getTabs();
for (var i=0; i<tabs.length; i++){
if (tabs[i].nodeName == "DIV"){
removeClass(tabs[i].getElementsByTagName('div')[0], "selected");
}
}
}
/**
* Select the right Content making it visible block
*/
this.setContentSelected = function(/** div */ tab){
var tabs = this._getTabs();
var pos = 0;
for (var i=0; i<tabs.length; i++){
if (tabs[i].nodeName == "DIV"){
if (tab == tabs[i].getElementsByTagName('div')[0]){
break;
}
pos ++;
}
}
var contents = this._getContents();
var contentPos = 0;
for (var i=0; i<contents.length; i++){
if (contents[i].nodeName == "DIV"){
if (contentPos == pos){
contents[i].style.display="block";
}else{
contents[i].style.display="none";
}
contentPos ++;
}
}
}
}
function addClass(/**DomNode*/ node, /** String */ cssclass){
if (!new RegExp('\\b'+cssclass+'\\b').test(node.className)){
node.className+=node.className?' '+cssclass:cssclass;
}
}
function removeClass(/**DomNode*/ node, /** String */ cssclass){
var rep=node.className.match(' '+cssclass)?' '+cssclass:cssclass;
node.className=node.className.replace(rep,'');
}
table.leftTab {
border-spacing: 0px;
}
table.leftTab * div.tabs{
padding:4px 15px 4px 6px;
color:white;
cursor:pointer;
font-size:12px;
font-weight:bold;
white-space:nowrap;
background-image: url('sidetabsDefault.gif');
background-repeat: no-repeat;
}
table.leftTab * div.selected{
color:blue;
cursor: default;
background-image: url('sidetabsSelected.gif');
}
table.leftTab * .content {
border:2px solid blue;
min-height: 300px;
padding: 10px 25px 10px 25px;
font-family:'Arial',sans-serif;
font-size:12px;
}
table.leftTab * .content * table{
font-family:'Arial',sans-serif;
font-size:12px;
}
table.leftTab * .content * label{
font-weight:bold;
margin-right:50px;
}
Wednesday 8 August 2007
Par Vincent DEMAY, Wednesday 8 August 2007 :: Wicket
Thursday 2 August 2007
Par Vincent DEMAY, Thursday 2 August 2007 :: Wicket
myDomNode.onkeypress = function(event) { alert(event.keyCode)}
myDomNode.onkeypress = function() { alert(window.event.keyCode)}
Actually IE propage key event on window.
myDomNode.onkeypress = function(event) {if (!event){event = window.event;} alert(event.keyCode);} Thursday 12 July 2007
Par Vincent DEMAY, Thursday 12 July 2007 :: Wicket
[Java]
public abstract class AbstractComponentAwareModel implements IWrapModel,
IComponentAssignedModel
{
private Component component;
public abstract Object getObject();
public abstract void setObject(Object object);
public void detach() {}
/**
* @see org.apache.wicket.model.IWrapModel#getWrappedModel()
*/
public IModel getWrappedModel()
{
return this;
}
/**
* @see org.apache.wicket.model.IComponentAssignedModel#wrapOnAssignment
(org.apache.wicket.Component)
*/
public IWrapModel wrapOnAssignment(Component component)
{
this.component = component;
return this;
}
protected Component getComponent()
{
return this.component;
}
}
Thx to Johan Compagner for the tip Monday 11 June 2007
Par Vincent DEMAY, Monday 11 June 2007 :: Wicket
Thursday 7 June 2007
Par Vincent DEMAY, Thursday 7 June 2007 :: Wicket

Saturday 10 February 2007
Par Vincent DEMAY, Saturday 10 February 2007 :: Wicket
Par Vincent DEMAY, Saturday 10 February 2007 :: Wicket
Saturday 20 January 2007
Par Vincent DEMAY, Saturday 20 January 2007 :: Wicket
Thursday 4 January 2007
Par Vincent DEMAY, Thursday 4 January 2007 :: Wicket
mvn -U -cpu -Dmaven.test.skip=true installHope tests will soon fixed ;)
Thursday 30 November 2006
Par Vincent DEMAY, Thursday 30 November 2006 :: Wicket
|
For more than a week I've a lot of time to work on Wicket-Dojo-Contrib, so now there are a lot of cool new features such as Calendar or lot of new container. Take a look at it on my web live demo. No distrib is avalaible for the moment because I work on trunk (future wicket 2.0) some features are backported on 1.3 branch wich will be compatible with future wicket 1.3. So be patient, I will try to make a new distribution as soon as wicket 1.3 will come out. |
![]() |