changeset 327:f979673f7d47

merge branches
author John Reimer <terminal.node@gmail.com>
date Sat, 11 Oct 2008 22:16:54 -0700
parents 5073c0da393a (current diff) 68adc3a367d9 (diff)
children 602a4fd8538f
files
diffstat 41 files changed, 593 insertions(+), 148 deletions(-) [+]
line wrap: on
line diff
--- a/dwt/accessibility/Accessible.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/accessibility/Accessible.d	Sat Oct 11 22:16:54 2008 -0700
@@ -239,7 +239,7 @@
     public void removeAccessibleControlListener (AccessibleControlListener listener) {
         checkWidget ();
         if (listener is null) DWT.error (DWT.ERROR_NULL_ARGUMENT);
-        remove( controlListeners, listener, delegate bool(AccessibleControlListener a1, AccessibleControlListener a2 ){ return a1 is a2; });
+        controlListeners.length = remove( controlListeners, listener, delegate bool(AccessibleControlListener a1, AccessibleControlListener a2 ){ return a1 is a2; });
     }
 
     /**
@@ -264,7 +264,7 @@
     public void removeAccessibleListener (AccessibleListener listener) {
         checkWidget ();
         if (listener is null) DWT.error (DWT.ERROR_NULL_ARGUMENT);
-        remove( accessibleListeners, listener, delegate bool( AccessibleListener a1, AccessibleListener a2 ){ return a1 is a2; });
+        accessibleListeners.length = remove( accessibleListeners, listener, delegate bool( AccessibleListener a1, AccessibleListener a2 ){ return a1 is a2; });
     }
 
     /**
@@ -291,7 +291,7 @@
     public void removeAccessibleTextListener (AccessibleTextListener listener) {
         checkWidget ();
         if (listener is null) DWT.error (DWT.ERROR_NULL_ARGUMENT);
-        remove( textListeners, listener, delegate bool(AccessibleTextListener a1, AccessibleTextListener a2 ){ return a1 is a2; });
+        textListeners.length = remove( textListeners, listener, delegate bool(AccessibleTextListener a1, AccessibleTextListener a2 ){ return a1 is a2; });
     }
 
     /**
--- a/dwt/accessibility/AccessibleObject.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/accessibility/AccessibleObject.d	Sat Oct 11 22:16:54 2008 -0700
@@ -1224,7 +1224,7 @@
         return result !is null ? result : new AccessibleTextListener [0];
     }
 
-    private static extern(C) void gObjectClass_finalize (GObject* atkObject) {
+    package static extern(C) void gObjectClass_finalize (GObject* atkObject) {
         auto superType = ATK.g_type_class_peek_parent (ATK.G_OBJECT_GET_CLASS (cast(GTypeInstance*)atkObject));
         auto objectClassStruct = cast(GObjectClass*)ATK.G_OBJECT_CLASS (cast(GTypeClass*)superType);
         objectClassStruct.finalize(atkObject);
--- a/dwt/custom/CTabFolder2Listener.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/CTabFolder2Listener.d	Sat Oct 11 22:16:54 2008 -0700
@@ -15,6 +15,9 @@
 import dwt.internal.DWTEventListener;
 import dwt.custom.CTabFolderEvent;
 
+import tango.core.Traits;
+import tango.core.Tuple;
+
 /**
  * Classes which implement this interface provide methods
  * that deal with the events that are generated by the CTabFolder
@@ -34,6 +37,13 @@
  * @since 3.0
  */
 public interface CTabFolder2Listener : DWTEventListener {
+    public enum {
+        MINIMIZE,
+        MAXIMIZE,
+        SHOWLIST,
+        RESTORE,
+        CLOSE
+    }
 
 /**
  * Sent when the user clicks on the close button of an item in the CTabFolder.
@@ -113,3 +123,73 @@
  */
 public void showList(CTabFolderEvent event);
 }
+
+
+
+/// Helper class for the dgListener template function
+private class _DgCTabFolder2ListenerT(Dg,T...) : CTabFolder2Listener {
+
+    alias ParameterTupleOf!(Dg) DgArgs;
+    static assert( is(DgArgs == Tuple!(CTabFolderEvent,T)),
+                "Delegate args not correct: "~DgArgs.stringof~" vs. (Event,"~T.stringof~")" );
+
+    Dg dg;
+    T  t;
+    int type;
+
+    private this( int type, Dg dg, T t ){
+        this.type = type;
+        this.dg = dg;
+        static if( T.length > 0 ){
+            this.t = t;
+        }
+    }
+
+    void itemClosed( CTabFolderEvent e ){
+        dg(e,t);
+    }
+    public void close(CTabFolderEvent e){
+        if( type is CTabFolder2Listener.CLOSE ){
+            dg(e,t);
+        }
+    }
+    public void minimize(CTabFolderEvent e){
+        if( type is CTabFolder2Listener.MINIMIZE ){
+            dg(e,t);
+        }
+    }
+    public void maximize(CTabFolderEvent e){
+        if( type is CTabFolder2Listener.MAXIMIZE ){
+            dg(e,t);
+        }
+    }
+    public void restore(CTabFolderEvent e){
+        if( type is CTabFolder2Listener.RESTORE ){
+            dg(e,t);
+        }
+    }
+    public void showList(CTabFolderEvent e){
+        if( type is CTabFolder2Listener.SHOWLIST ){
+            dg(e,t);
+        }
+    }
+}
+
+/++
+ + dgListener creates a class implementing the Listener interface and delegating the call to
+ + handleEvent to the users delegate. This template function will store also additional parameters.
+ +
+ + Examle of usage:
+ + ---
+ + void handleTextEvent ( Event e, int inset ) {
+ +     // ...
+ + }
+ + text.addListener (DWT.FocusOut, dgListener( &handleTextEvent, inset ));
+ + ---
+ +/
+CTabFolder2Listener dgCTabFolder2Listener( Dg, T... )( int type, Dg dg, T args ){
+    return new _DgCTabFolder2ListenerT!( Dg, T )( type, dg, args );
+}
+
+
+
--- a/dwt/custom/CTabFolderLayout.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/CTabFolderLayout.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,6 +12,7 @@
  *******************************************************************************/
 module dwt.custom.CTabFolderLayout;
 
+import dwt.dwthelper.utils;
 
 import dwt.DWT;
 import dwt.graphics.GC;
--- a/dwt/custom/CTabFolderListener.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/CTabFolderListener.d	Sat Oct 11 22:16:54 2008 -0700
@@ -15,6 +15,9 @@
 import dwt.internal.DWTEventListener;
 import dwt.custom.CTabFolderEvent;
 
+import tango.core.Traits;
+import tango.core.Tuple;
+
 /**
  * Classes which implement this interface provide a method
  * that deals with events generated in the CTabFolder.
@@ -42,3 +45,46 @@
  */
 public void itemClosed(CTabFolderEvent event);
 }
+
+
+
+/// Helper class for the dgListener template function
+private class _DgCTabFolderListenerT(Dg,T...) : CTabFolderListener {
+
+    alias ParameterTupleOf!(Dg) DgArgs;
+    static assert( is(DgArgs == Tuple!(CTabFolderEvent,T)),
+                "Delegate args not correct" );
+
+    Dg dg;
+    T  t;
+
+    private this( Dg dg, T t ){
+        this.dg = dg;
+        static if( T.length > 0 ){
+            this.t = t;
+        }
+    }
+
+    void itemClosed( CTabFolderEvent e ){
+        dg(e,t);
+    }
+}
+
+/++
+ + dgListener creates a class implementing the Listener interface and delegating the call to
+ + handleEvent to the users delegate. This template function will store also additional parameters.
+ +
+ + Examle of usage:
+ + ---
+ + void handleTextEvent (Event e, int inset ) {
+ +     // ...
+ + }
+ + text.addListener (DWT.FocusOut, dgListener( &handleTextEvent, inset ));
+ + ---
+ +/
+CTabFolderListener dgCTabFolderListener( Dg, T... )( Dg dg, T args ){
+    return new _DgCTabFolderListenerT!( Dg, T )( dg, args );
+}
+
+
+
--- a/dwt/custom/ControlEditor.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/ControlEditor.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,7 +12,7 @@
  *******************************************************************************/
 module dwt.custom.ControlEditor;
 
-
+import dwt.dwthelper.utils;
 
 import dwt.DWT;
 import dwt.graphics.Rectangle;
--- a/dwt/custom/TableTree.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/TableTree.d	Sat Oct 11 22:16:54 2008 -0700
@@ -764,7 +764,6 @@
  * @param items the array of items
  *
  * @exception IllegalArgumentException <ul>
- *    <li>ERROR_NULL_ARGUMENT - if one of the items is null</li>
  *    <li>ERROR_INVALID_ARGUMENT - if one of the item has been disposed</li>
  * </ul>
  * @exception DWTException <ul>
--- a/dwt/custom/TableTreeEditor.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/TableTreeEditor.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,6 +12,7 @@
  *******************************************************************************/
 module dwt.custom.TableTreeEditor;
 
+import dwt.dwthelper.utils;
 
 
 import dwt.DWT;
--- a/dwt/custom/TreeEditor.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/TreeEditor.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,6 +12,7 @@
  *******************************************************************************/
 module dwt.custom.TreeEditor;
 
+import dwt.dwthelper.utils;
 
 
 import dwt.DWT;
--- a/dwt/custom/ViewFormLayout.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/custom/ViewFormLayout.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,6 +12,7 @@
  *******************************************************************************/
 module dwt.custom.ViewFormLayout;
 
+import dwt.dwthelper.utils;
 
 import dwt.DWT;
 import dwt.graphics.Point;
@@ -196,7 +197,7 @@
     int oldSeperator = form.separator;
     form.separator = -1;
     if (content !is null && !content.isDisposed()) {
-        if (left !is null || right!is null || center !is null){
+        if (left !is null || right !is null || center !is null){
             form.separator = y;
             y++;
         }
--- a/dwt/dwthelper/FileInputStream.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/dwthelper/FileInputStream.d	Sat Oct 11 22:16:54 2008 -0700
@@ -7,7 +7,11 @@
 import dwt.dwthelper.File;
 import dwt.dwthelper.InputStream;
 
+version(TANGOSVN){
+import tango.io.device.FileConduit;
+} else {
 import tango.io.FileConduit;
+}
 import tango.io.protocol.Reader;
 import tango.core.Exception;
 import tango.text.convert.Format;
--- a/dwt/dwthelper/FileOutputStream.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/dwthelper/FileOutputStream.d	Sat Oct 11 22:16:54 2008 -0700
@@ -8,7 +8,11 @@
 
 import dwt.dwthelper.utils;
 
+version(TANGOSVN){
+import tango.io.device.FileConduit;
+} else {
 import tango.io.FileConduit;
+}
 
 public class FileOutputStream : dwt.dwthelper.OutputStream.OutputStream {
 
--- a/dwt/dwthelper/InflaterInputStream.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/dwthelper/InflaterInputStream.d	Sat Oct 11 22:16:54 2008 -0700
@@ -7,7 +7,16 @@
 import dwt.dwthelper.utils;
 import tango.io.Stdout;
 import tango.io.compress.ZlibStream;
-import tango.io.Conduit;
+version(Windows){
+    version(build){
+        pragma(link,"zlib");
+    }
+}
+version(TANGOSVN){
+    import tango.io.device.Conduit;
+} else {
+    import tango.io.Conduit;
+}
 
 class InputStreamWrapper : tango.io.model.IConduit.InputStream {
 
@@ -21,7 +30,6 @@
         int res = istr.read( cast(byte[])dst );
         return res;
     }
-
     void[] load (void[] dst = null) {
             return Conduit.load (this, dst);
     }
--- a/dwt/dwthelper/Runnable.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/dwthelper/Runnable.d	Sat Oct 11 22:16:54 2008 -0700
@@ -17,7 +17,7 @@
 
     alias ParameterTupleOf!(Dg) DgArgs;
     static assert( is(DgArgs == Tuple!(T)),
-                "Delegate args not correct" );
+                "Delegate args not correct: "~DgArgs.stringof~" vs "~T.stringof );
 
     Dg dg;
     T t;
@@ -36,4 +36,4 @@
 
 _DgRunnableT!(Dg,T) dgRunnable(Dg,T...)( Dg dg, T args ){
     return new _DgRunnableT!(Dg,T)(dg,args);
-}
\ No newline at end of file
+}
--- a/dwt/dwthelper/System.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/dwthelper/System.d	Sat Oct 11 22:16:54 2008 -0700
@@ -146,6 +146,13 @@
         return (*cast(Object *)&x).toHash();
     }
 
+    public static String getProperty( String key, String defval ){
+        String res = getProperty(key);
+        if( res ){
+            return res;
+        }
+        return defval;
+    }
     public static String getProperty( String key ){
         /* Get values for local dwt specific keys */
         String* p;
@@ -167,15 +174,36 @@
     public static void setProperty ( String key, String value ) {
         /* set property for local dwt keys */
         if (key[0..3] == "dwt") {
-            if (key !is null && value !is null) 
+            if (key !is null && value !is null)
                 localProperties[ key ] = value;
         /* else set properties for global system keys (environment) */
         } else {
-        
+
         }
 
     }
 
+    static class Output {
+        public void println( String str ){
+            implMissing( __FILE__, __LINE__ );
+        }
+    }
+
+    private static Output err__;
+    public static Output err(){
+        if( err__ is null ){
+            err__ = new Output();
+        }
+        return err__;
+    }
+    private static Output out__;
+    public static Output out_(){
+        if( out__ is null ){
+            out__ = new Output();
+        }
+        return out__;
+    }
+
     private static String[String] localProperties;
 }
 
--- a/dwt/dwthelper/utils.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/dwthelper/utils.d	Sat Oct 11 22:16:54 2008 -0700
@@ -4,6 +4,7 @@
 module dwt.dwthelper.utils;
 
 public import dwt.dwthelper.System;
+public import dwt.dwthelper.Runnable;
 public import Math = tango.math.Math;
 
 public import tango.core.Exception : IllegalArgumentException, IOException;
@@ -13,6 +14,7 @@
 static import tango.stdc.stringz;
 static import tango.text.Util;
 static import tango.text.Text;
+static import tango.text.Ascii;
 import tango.text.Unicode;
 import tango.text.convert.Utf;
 import tango.core.Exception;
@@ -20,11 +22,12 @@
 
 import tango.util.log.Trace;
 import tango.text.UnicodeData;
-static import tango.util.collection.model.Seq;
 
 alias char[] String;
 alias tango.text.Text.Text!(char) StringBuffer;
 
+alias ArrayBoundsException ArrayIndexOutOfBoundsException;
+
 void implMissing( String file, uint line ){
     Stderr.formatln( "implementation missing in file {} line {}", file, line );
     Stderr.formatln( "exiting ..." );
@@ -124,6 +127,9 @@
     public static Boolean valueOf( bool b ){
         return b ? TRUE : FALSE;
     }
+    public static bool getBoolean(String name){
+        return tango.text.Ascii.icompare(System.getProperty(name, "false"), "true" ) is 0;
+    }
 }
 
 alias Boolean    ValueWrapperBool;
@@ -145,6 +151,11 @@
     this( byte value ){
         super( value );
     }
+
+    public static String toString( byte i ){
+        return tango.text.convert.Integer.toString(i);
+    }
+
 }
 alias Byte ValueWrapperByte;
 
@@ -197,7 +208,7 @@
 
     public static int parseInt( String s, int radix ){
         try{
-            return tango.text.convert.Integer.parse( s, cast(uint)radix );
+            return tango.text.convert.Integer.toLong( s, radix );
         }
         catch( IllegalArgumentException e ){
             throw new NumberFormatException( e );
@@ -206,7 +217,7 @@
 
     public static int parseInt( String s ){
         try{
-            return tango.text.convert.Integer.parse( s );
+            return tango.text.convert.Integer.toLong( s );
         }
         catch( IllegalArgumentException e ){
             throw new NumberFormatException( e );
@@ -277,6 +288,10 @@
         implMissing( __FILE__, __LINE__ );
         return null;
     }
+    public static double parseDouble(String s){
+        implMissing( __FILE__, __LINE__ );
+        return 0.0;
+    }
 }
 
 class Float : ValueWrapperT!(float) {
@@ -372,6 +387,10 @@
     }
     return res;
 }
+
+/++
+ +
+ +/
 int indexToCodepointIndex( String str, int index ){
     if( index < 0 ) return index;
     int i = 0;
@@ -397,6 +416,9 @@
     return res;
 }
 
+/++
+ + Get that String, that contains the next codepoint of a String.
+ +/
 String firstCodePointStr( String str, out int consumed ){
     dchar[1] buf;
     uint ate;
@@ -405,6 +427,12 @@
     return str[ 0 .. ate ];
 }
 
+/++
+ + Get first codepoint of a String. If an offset is needed, simply use a slice:
+ + ---
+ + dchar res = str[ offset .. $ ].firstCodePoint();
+ + ---
+ +/
 dchar firstCodePoint( String str ){
     int dummy;
     return firstCodePoint( str, dummy );
@@ -421,6 +449,18 @@
     assert( res.length is 1 );
     return res[0];
 }
+dchar firstCodePoint( wchar[] str, out int consumed ){
+    dchar[1] buf;
+    uint ate;
+    dchar[] res = str.toString32( buf, &ate );
+    consumed = ate;
+    if( ate is 0 || res.length is 0 ){
+        Trace.formatln( "dwthelper.utils {}: str.length={} str={:X2}", __LINE__, str.length, cast(ubyte[])str );
+    }
+    assert( ate > 0 );
+    assert( res.length is 1 );
+    return res[0];
+}
 
 String dcharToString( dchar key ){
     dchar[1] buf;
@@ -440,6 +480,9 @@
 alias tango.text.convert.Utf.toString toString;
 
 int getRelativeCodePointOffset( String str, int startIndex, int searchRelCp ){
+    return getAbsoluteCodePointOffset( str, startIndex, searchRelCp ) - startIndex;
+}
+int getAbsoluteCodePointOffset( String str, int startIndex, int searchRelCp ){
     int ignore;
     int i = startIndex;
     if( searchRelCp > 0 ){
@@ -483,7 +526,7 @@
             do{
                 i--;
                 if( i < 0 ){
-                    return -1;
+                    return startIndex-1;
                     //Trace.formatln( "dwthelper.utils getRelativeCodePointOffset {}: str={}, startIndex={}, searchRelCp={}", __LINE__, str, startIndex, searchRelCp );
                     //tango.text.convert.Utf.onUnicodeError( "invalid utf8 input", i );
                 }
@@ -491,7 +534,50 @@
             searchRelCp++;
         }
     }
-    return i - startIndex;
+    return i;
+}
+int getAbsoluteCodePointOffset( wchar[] str, int startIndex, int searchRelCp ){
+    int ignore;
+    int i = startIndex;
+    if( searchRelCp > 0 ){
+        while( searchRelCp !is 0 ){
+
+            if( ( i < str.length )
+                && ( str[i] & 0xD800 ) !is 0xD800 )
+            {
+                i+=1;
+            }
+            else if( ( i+1 < str.length )
+                && (( str[i+1] & 0xDC00 ) is 0xDC00 )
+                && (( str[i  ] & 0xDC00 ) is 0xD800 ))
+            {
+                i+=2;
+            }
+            else{
+                Trace.formatln( "invalid utf8 characters:  {:X2}", cast(ubyte[]) str );
+                tango.text.convert.Utf.onUnicodeError( "invalid utf8 input", i );
+            }
+            searchRelCp--;
+        }
+    }
+    else if( searchRelCp < 0 ){
+        while( searchRelCp !is 0 ){
+            do{
+                i--;
+                if( i < 0 ){
+                    return startIndex-1;
+                    //Trace.formatln( "dwthelper.utils getRelativeCodePointOffset {}: str={}, startIndex={}, searchRelCp={}", __LINE__, str, startIndex, searchRelCp );
+                    //tango.text.convert.Utf.onUnicodeError( "invalid utf8 input", i );
+                }
+            } while(( str[i] & 0xDC00 ) is 0xDC00 );
+            searchRelCp++;
+        }
+    }
+    return i;
+}
+dchar getRelativeCodePoint( String str, int startIndex, int searchRelCp ){
+    int dummy;
+    return getRelativeCodePoint( str, startIndex, dummy );
 }
 dchar getRelativeCodePoint( String str, int startIndex, int searchRelCp, out int relIndex ){
     relIndex = getRelativeCodePointOffset( str, startIndex, searchRelCp );
@@ -535,6 +621,84 @@
     return res;
 }
 
+class Character {
+    public static bool isUpperCase( dchar c ){
+        implMissing( __FILE__, __LINE__);
+        return false;
+    }
+    public static dchar toUpperCase( dchar c ){
+        dchar[] r = tango.text.Unicode.toUpper( [c] );
+        return r[0];
+    }
+    public static dchar toLowerCase( dchar c ){
+        dchar[] r = tango.text.Unicode.toLower( [c] );
+        return r[0];
+    }
+    public static bool isWhitespace( dchar c ){
+        return tango.text.Unicode.isWhitespace( c );
+    }
+    public static bool isDigit( dchar c ){
+        return tango.text.Unicode.isDigit( c );
+    }
+    public static bool isLetterOrDigit( dchar c ){
+        return isDigit(c) || isLetter(c);
+    }
+    public static bool isUnicodeIdentifierPart(char ch){
+        implMissing( __FILE__, __LINE__);
+        return false;
+    }
+    public static bool isUnicodeIdentifierStart(char ch){
+        implMissing( __FILE__, __LINE__);
+        return false;
+    }
+    public static bool isIdentifierIgnorable(char ch){
+        implMissing( __FILE__, __LINE__);
+        return false;
+    }
+    public static bool isJavaIdentifierPart(char ch){
+        implMissing( __FILE__, __LINE__);
+        return false;
+    }
+
+    this( char c ){
+        // must be correct for container storage
+        implMissing( __FILE__, __LINE__);
+    }
+}
+
+String new_String( String cont, int offset, int len ){
+    return cont[ offset .. offset+len ].dup;
+}
+String new_String( String cont ){
+    return cont.dup;
+}
+String String_valueOf( bool v ){
+    return v ? "true" : "false";
+}
+String String_valueOf( int v ){
+    return tango.text.convert.Integer.toString(v);
+}
+String String_valueOf( long v ){
+    return tango.text.convert.Integer.toString(v);
+}
+String String_valueOf( float v ){
+    return tango.text.convert.Float.toString(v);
+}
+String String_valueOf( double v ){
+    return tango.text.convert.Float.toString(v);
+}
+String String_valueOf( dchar v ){
+    return dcharToString(v);
+}
+String String_valueOf( char[] v ){
+    return v.dup;
+}
+String String_valueOf( char[] v, int offset, int len ){
+    return v[ offset .. offset+len ].dup;
+}
+String String_valueOf( Object v ){
+    return v is null ? "null" : v.toString();
+}
 bool CharacterIsDefined( dchar ch ){
     return (ch in tango.text.UnicodeData.unicodeData) !is null;
 }
@@ -548,7 +712,9 @@
     dchar[] r = tango.text.Unicode.toLower( buf );
     return r[0];
 }
-
+int length( String str ){
+    return str.length;
+}
 dchar CharacterToLower( dchar c ){
     dchar[] r = tango.text.Unicode.toLower( [c] );
     return r[0];
@@ -570,6 +736,11 @@
     return tango.text.Unicode.toUpper( str );
 }
 
+public String replaceFirst( String str, String regex, String replacement ){
+    implMissing(__FILE__,__LINE__);
+    return str;
+}
+
 public int indexOf( String str, char searched ){
     int res = tango.text.Util.locate( str, searched );
     if( res is str.length ) res = -1;
@@ -609,6 +780,10 @@
     return res;
 }
 
+public String replaceAll( String str, String regex, String replacement ){
+    implMissing(__FILE__,__LINE__);
+    return null;
+}
 public String replace( String str, char from, char to ){
     return tango.text.Util.replace( str.dup, from, to );
 }
@@ -637,8 +812,12 @@
     dst[ dstBegin .. dstBegin + srcEnd - srcBegin ] = src[ srcBegin .. srcEnd ];
 }
 
-public wchar[] toCharArray( String str ){
-    return toString16( str );
+public wchar[] toWCharArray( String str ){
+    return toString16(str);
+}
+
+public char[] toCharArray( String str ){
+    return str;
 }
 
 public bool endsWith( String src, String pattern ){
@@ -685,6 +864,10 @@
     return str;
 }
 
+/++
+ + This is like tango.stdc.stringz.toStringz, but in case of an empty input string,
+ + this function returns a pointer to a null value instead of a null ptr.
+ +/
 public char* toStringzValidPtr( String src ){
     if( src ){
         return src.toStringz();
@@ -794,6 +977,11 @@
         super(e);
     }
 }
+class ClassCastException : Exception {
+    this( String e = null ){
+        super(e);
+    }
+}
 
 interface Cloneable{
 }
@@ -859,7 +1047,42 @@
     }
 }
 
-interface Reader{
+class Reader{
+    protected Object   lock;
+    protected this(){
+        implMissing(__FILE__,__LINE__);
+    }
+    protected this(Object lock){
+        implMissing(__FILE__,__LINE__);
+    }
+    abstract  void  close();
+    void mark(int readAheadLimit){
+        implMissing(__FILE__,__LINE__);
+    }
+    bool markSupported(){
+        implMissing(__FILE__,__LINE__);
+        return false;
+    }
+    int read(){
+        implMissing(__FILE__,__LINE__);
+        return 0;
+    }
+    int read(char[] cbuf){
+        implMissing(__FILE__,__LINE__);
+        return 0;
+    }
+    abstract int read(char[] cbuf, int off, int len);
+    bool ready(){
+        implMissing(__FILE__,__LINE__);
+        return false;
+    }
+    void reset(){
+        implMissing(__FILE__,__LINE__);
+    }
+    long skip(long n){
+        implMissing(__FILE__,__LINE__);
+        return 0;
+    }
 }
 interface Writer{
 }
@@ -977,7 +1200,7 @@
     return true;
 }
 
-int SeqIndexOf(T)( tango.util.collection.model.Seq.Seq!(T) s, T src ){
+/+int SeqIndexOf(T)( tango.util.collection.model.Seq.Seq!(T) s, T src ){
     int idx;
     foreach( e; s ){
         if( e == src ){
@@ -986,7 +1209,8 @@
         idx++;
     }
     return -1;
-}
+}+/
+
 int arrayIndexOf(T)( T[] arr, T v ){
     int res = -1;
     int idx = 0;
@@ -1000,18 +1224,18 @@
     return res;
 }
 
-int seqIndexOf( tango.util.collection.model.Seq.Seq!(Object) seq, Object v ){
-    int res = -1;
-    int idx = 0;
-    foreach( p; seq ){
-        if( p == v){
-            res = idx;
-            break;
-        }
-        idx++;
-    }
-    return res;
-}
+// int seqIndexOf( tango.util.collection.model.Seq.Seq!(Object) seq, Object v ){
+//     int res = -1;
+//     int idx = 0;
+//     foreach( p; seq ){
+//         if( p == v){
+//             res = idx;
+//             break;
+//         }
+//         idx++;
+//     }
+//     return res;
+// }
 
 void PrintStackTrace( int deepth = 100, String prefix = "trc" ){
     auto e = new Exception( null );
@@ -1041,3 +1265,30 @@
     const ImportData getImportData = ImportData( import(name), name );
 }
 
+interface CharSequence {
+    char           charAt(int index);
+    int             length();
+    CharSequence    subSequence(int start, int end);
+    String          toString();
+}
+
+class StringCharSequence : CharSequence {
+    private String str;
+    this( String str ){
+        this.str = str;
+    }
+    char           charAt(int index){
+        return str[index];
+    }
+    int             length(){
+        return str.length;
+    }
+    CharSequence    subSequence(int start, int end){
+        return new StringCharSequence( str[ start .. end ]);
+    }
+    String          toString(){
+        return str;
+    }
+}
+
+
--- a/dwt/events/KeyEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/KeyEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,13 +12,12 @@
  *******************************************************************************/
 module dwt.events.KeyEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.events.TypedEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
 
 /**
  * Instances of this class are sent as a result of
--- a/dwt/events/MenuDetectEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/MenuDetectEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,13 +12,13 @@
  *******************************************************************************/
 module dwt.events.MenuDetectEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.events.TypedEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
+
 /**
  * Instances of this class are sent whenever the platform-
  * specific trigger for showing a context menu is detected.
--- a/dwt/events/MouseEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/MouseEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,13 +12,12 @@
  *******************************************************************************/
 module dwt.events.MouseEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.events.TypedEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
 
 /**
  * Instances of this class are sent whenever mouse
--- a/dwt/events/PaintEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/PaintEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,8 +12,6 @@
  *******************************************************************************/
 module dwt.events.PaintEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.graphics.GC;
@@ -21,6 +19,7 @@
 import dwt.events.TypedEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
 
 /**
  * Instances of this class are sent as a result of
--- a/dwt/events/SelectionEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/SelectionEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,14 +12,14 @@
  *******************************************************************************/
 module dwt.events.SelectionEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.widgets.Widget;
 import dwt.events.TypedEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
+
 /**
  * Instances of this class are sent as a result of
  * widgets being selected.
--- a/dwt/events/SelectionListener.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/SelectionListener.d	Sat Oct 11 22:16:54 2008 -0700
@@ -16,6 +16,9 @@
 public import dwt.internal.DWTEventListener;
 public import dwt.events.SelectionEvent;
 
+import tango.core.Traits;
+import tango.core.Tuple;
+
 /**
  * Classes which implement this interface provide methods
  * that deal with the events that are generated when selection
@@ -34,6 +37,10 @@
  */
 public interface SelectionListener : DWTEventListener {
 
+    public enum {
+        SELECTION,
+        DEFAULTSELECTION
+    }
 /**
  * Sent when selection occurs in the control.
  * <p>
@@ -63,3 +70,47 @@
  */
 public void widgetDefaultSelected(SelectionEvent e);
 }
+
+
+/// DWT extension
+private class _DgSelectionListenerT(Dg,T...) : SelectionListener {
+
+    alias ParameterTupleOf!(Dg) DgArgs;
+    static assert( is(DgArgs == Tuple!(SelectionEvent,T)),
+                "Delegate args not correct: "~DgArgs.stringof~" vs. (Event,"~T.stringof~")" );
+
+    Dg dg;
+    T  t;
+    int type;
+
+    private this( int type, Dg dg, T t ){
+        this.type = type;
+        this.dg = dg;
+        static if( T.length > 0 ){
+            this.t = t;
+        }
+    }
+
+    public void widgetSelected(SelectionEvent e){
+        if( type is SelectionListener.SELECTION ){
+            dg(e,t);
+        }
+    }
+    public void widgetDefaultSelected(SelectionEvent e){
+        if( type is SelectionListener.DEFAULTSELECTION ){
+            dg(e,t);
+        }
+    }
+}
+
+SelectionListener dgSelectionListener( Dg, T... )( int type, Dg dg, T args ){
+    return new _DgSelectionListenerT!( Dg, T )( type, dg, args );
+}
+
+SelectionListener dgSelectionListenerWidgetSelected( Dg, T... )( Dg dg, T args ){
+    return dgSelectionListener( SelectionListener.SELECTION, dg, args );
+}
+SelectionListener dgSelectionListenerWidgetDefaultSelected( Dg, T... )( Dg dg, T args ){
+    return dgSelectionListener( SelectionListener.DEFAULTSELECTION, dg, args );
+}
+
--- a/dwt/events/ShellEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/ShellEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,13 +12,12 @@
  *******************************************************************************/
 module dwt.events.ShellEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.events.TypedEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
 
 /**
  * Instances of this class are sent as a result of
--- a/dwt/events/TraverseEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/TraverseEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,13 +12,13 @@
  *******************************************************************************/
 module dwt.events.TraverseEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.events.KeyEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
+
 /**
  * Instances of this class are sent as a result of
  * widget traversal actions.
--- a/dwt/events/TypedEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/TypedEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,8 +12,6 @@
  *******************************************************************************/
 module dwt.events.TypedEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.widgets.Display;
@@ -22,6 +20,7 @@
 
 import tango.text.convert.Format;
 import tango.text.Util : split;
+import dwt.dwthelper.utils;
 
 /**
  * This is the super class for all typed event classes provided
--- a/dwt/events/VerifyEvent.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/events/VerifyEvent.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,13 +12,13 @@
  *******************************************************************************/
 module dwt.events.VerifyEvent;
 
-import dwt.dwthelper.utils;
-
 
 import dwt.widgets.Event;
 import dwt.events.KeyEvent;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
+
 /**
  * Instances of this class are sent as a result of
  * widgets handling keyboard events
--- a/dwt/graphics/Device.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/graphics/Device.d	Sat Oct 11 22:16:54 2008 -0700
@@ -698,9 +698,7 @@
     Device dev = cast(Device)user_data;
     if (dev.warningLevel is 0) {
         if (DEBUG || dev.debugging) {
-            foreach( msg; (new Exception ("")).info ){
-                Stderr.formatln( "trc {}", msg );
-            }
+            ExceptionPrintStackTrace(new Exception (""));
         }
         OS.g_log_default_handler (log_domain, log_level, message, user_data);
     }
--- a/dwt/graphics/ImageLoader.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/graphics/ImageLoader.d	Sat Oct 11 22:16:54 2008 -0700
@@ -299,7 +299,7 @@
 public void removeImageLoaderListener(ImageLoaderListener listener) {
     if (listener is null) DWT.error (DWT.ERROR_NULL_ARGUMENT);
     if (imageLoaderListeners.length is 0 ) return;
-    tango.core.Array.remove( imageLoaderListeners, listener, delegate bool(ImageLoaderListener l1, ImageLoaderListener l2 ){ return l1 is l2; });
+    imageLoaderListeners.length = tango.core.Array.remove( imageLoaderListeners, listener, delegate bool(ImageLoaderListener l1, ImageLoaderListener l2 ){ return l1 is l2; });
 }
 
 /**
--- a/dwt/internal/accessibility/gtk/ATK.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/internal/accessibility/gtk/ATK.d	Sat Oct 11 22:16:54 2008 -0700
@@ -1,4 +1,4 @@
-/*******************************************************************************
+/*******************************************************************************
  * Copyright (c) 2000, 2006 IBM Corporation and others. All rights reserved.
  * The contents of this file are made available under the terms
  * of the GNU Lesser General Public License (LGPL) Version 2.1 that
@@ -60,12 +60,17 @@
 }
 
 
-
-
 template NameOfFunc(alias f) {
     // Note: highly dependent on the .stringof formatting
     // the value begins with "& " which is why the first two chars are cut off
-    const String NameOfFunc = (&f).stringof[2 .. $];
+    version( LDC ){
+        // stringof in LLVMDC is "&foobar"
+        const char[] NameOfFunc = (&f).stringof[1 .. $];
+    }
+    else{
+        // stringof in DMD is "& foobar"
+        const char[] NameOfFunc = (&f).stringof[2 .. $];
+    }
 }
 
 template ForwardGtkAtkCFunc( alias cFunc ) {
--- a/dwt/internal/cairo/Cairo.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/internal/cairo/Cairo.d	Sat Oct 11 22:16:54 2008 -0700
@@ -1,4 +1,4 @@
-/* ***** BEGIN LICENSE BLOCK *****
+/* ***** BEGIN LICENSE BLOCK *****
  * Version: MPL 1.1
  *
  * The contents of this file are subject to the Mozilla Public License Version
@@ -63,7 +63,14 @@
 template NameOfFunc(alias f) {
     // Note: highly dependent on the .stringof formatting
     // the value begins with "& " which is why the first two chars are cut off
-    const String NameOfFunc = (&f).stringof[2 .. $];
+    version( LDC ){
+        // stringof in LLVMDC is "&foobar"
+        const char[] NameOfFunc = (&f).stringof[1 .. $];
+    }
+    else{
+        // stringof in DMD is "& foobar"
+        const char[] NameOfFunc = (&f).stringof[2 .. $];
+    }
 }
 
 template ForwardGtkCairoCFunc( alias cFunc ) {
--- a/dwt/internal/gtk/OS.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/internal/gtk/OS.d	Sat Oct 11 22:16:54 2008 -0700
@@ -616,7 +616,20 @@
 template NameOfFunc(alias f) {
     // Note: highly dependent on the .stringof formatting
     // the value begins with "& " which is why the first two chars are cut off
-    const char[] NameOfFunc = (&f).stringof[2 .. $];
+
+    // this is also used in dwt/internal/cairo/Cairo and dwt/internal/accessible/gtk/ATK
+    version( LDC ){
+        // stringof in LDC is "&foobar"
+        static assert( (&f).stringof[0] == '&' );
+        static assert( (&f).stringof[1] != ' ' );
+        const char[] NameOfFunc = (&f).stringof[1 .. $];
+    }
+    else{
+        // stringof in DMD is "& foobar"
+        static assert( (&f).stringof[0] == '&' );
+        static assert( (&f).stringof[1] == ' ' );
+        const char[] NameOfFunc = (&f).stringof[2 .. $];
+    }
 }
 
 template ForwardGtkOsCFunc( alias cFunc ) {
--- a/dwt/widgets/Canvas.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/Canvas.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,7 +12,7 @@
  *******************************************************************************/
 module dwt.widgets.Canvas;
 
-
+import dwt.dwthelper.utils;
 import dwt.graphics.Point;
 import dwt.internal.gtk.OS;
 import dwt.DWT;
--- a/dwt/widgets/CoolItem.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/CoolItem.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,6 +12,7 @@
  *******************************************************************************/
 module dwt.widgets.CoolItem;
 
+import dwt.dwthelper.utils;
 import dwt.DWT;
 import dwt.DWTException;
 import dwt.events.SelectionEvent;
--- a/dwt/widgets/DateTime.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/DateTime.d	Sat Oct 11 22:16:54 2008 -0700
@@ -40,6 +40,7 @@
 static import tango.text.Util;
 //static import tango.text.locale.Core;
 static import tango.text.Text;
+static import tango.time.Time;
 static import tango.time.WallClock;
 static import tango.time.chrono.Gregorian;
 static import tango.time.chrono.Calendar;
@@ -84,6 +85,17 @@
         return instance;
     }
 
+    public this(){
+        tango.time.Time.Time time = tango.time.WallClock.WallClock.now();
+        tango.time.Time.TimeSpan span = time.time.span;
+        this.second = span.seconds % 60;
+        this.minute = span.minutes % 60;
+        this.hour   = span.hours;
+        auto greg = tango.time.chrono.Gregorian.Gregorian.generic;
+        this.dayofmonth = greg.getDayOfMonth( time );
+        this.month      = greg.getMonth( time );
+        this.year       = greg.getYear( time );
+    }
     int getActualMaximum(int field){
         switch( field ){
         case YEAR:
@@ -288,68 +300,6 @@
     }
 }
 
-/+
-private int getCalendarActualMaximum( tango.time.Time.Time time, int field ){
-    int year = cal.getYear( time );
-    int month = cal.getMonth( time );
-    tango.time.Time.TimeOfDay tod = tango.time.Time.TimeOfDay( time.ticks );
-    switch( field ){
-    case YEAR: return tango.time.chrono.Gregorian.Gregorian.MAX_YEAR;
-    case MONTH: return cal.getMonthsInYear( year, tango.time.chrono.Gregorian.Gregorian.AD_ERA ) -1; // Jan is 0, so max is 11
-    case DAY_OF_MONTH:return cal.getDaysInMonth( year, month, tango.time.chrono.Gregorian.Gregorian.AD_ERA ) -1; // 1st is 0
-    case HOUR:return 23;
-    case MINUTE:return 59;
-    case SECOND:return 59;
-    case AM_PM:return PM;
-    default:
-    }
-}
-
-private int getCalendarActualMinimum( tango.time.Time.Time time, int field ){
-    switch( field ){
-    case YEAR: return 1800;
-    case MONTH: return 1;
-    case DAY_OF_MONTH:return 1;
-    case HOUR:return 0;
-    case MINUTE:return 0;
-    case SECOND:return 0;
-    case AM_PM:return AM;
-    default:
-    }
-}
-private int getCalendarField( tango.time.Time.Time time, int field ){
-    switch( field ){
-    case YEAR: return cal.getYear( time );
-    case MONTH: return cal.getMonth( time );
-    case DAY_OF_MONTH:return cal.getDayOfMonth( time );
-    default:
-    }
-    tango.time.Time.TimeOfDay tod = tango.time.Time.TimeOfDay( time.ticks );
-    switch( field ){
-    case HOUR:return tod.hours;
-    case MINUTE:return tod.minutes;
-    case SECOND:return tod.seconds;
-    case AM_PM:return tod.hours > 12;
-    default:
-    }
-    assert(false);
-}
-enum {
-    AM,
-    PM,
-    AM_PM,
-    HOUR,
-    MINUTE,
-    SECOND,
-    MONTH,
-    YEAR,
-    DAY_OF_MONTH,
-    DAY_SELECTED,
-    MONTH_CHANGED,
-    HOUR_OF_DAY
-}
-
-+/
 
 /**
  * Instances of this class are selectable user interface
@@ -371,7 +321,7 @@
  * </p><p>
  * IMPORTANT: This class is <em>not</em> intended to be subclassed.
  * </p>
- * 
+ *
  * @see <a href="http://www.eclipse.org/swt/snippets/#datetime">DateTime snippets</a>
  * @see <a href="http://www.eclipse.org/swt/examples.php">DWT Example: ControlExample</a>
  * @see <a href="http://www.eclipse.org/swt/">Sample code and further information</a>
--- a/dwt/widgets/Display.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/Display.d	Sat Oct 11 22:16:54 2008 -0700
@@ -3649,7 +3649,7 @@
     OS.gtk_container_forall (cast(GtkContainer*)widget, cast(GtkCallback)&setDirectionProcFunc, &setDirectionProcCallbackData);
 }
 
-private static extern(C) int /*long*/ setDirectionProcFunc (GtkWidget* widget, void* data) {
+package static extern(C) int /*long*/ setDirectionProcFunc (GtkWidget* widget, void* data) {
     version(LOG) Stderr.formatln( "Display {}:", __LINE__ ).flush;
     CallbackData* cbdata = cast(CallbackData*)data;
     return cbdata.display.setDirectionProc( widget, cast(int)cbdata.data );
--- a/dwt/widgets/Event.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/Event.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,8 +12,6 @@
  *******************************************************************************/
 module dwt.widgets.Event;
 
-import dwt.dwthelper.utils;
-
 import dwt.graphics.GC;
 import dwt.graphics.Rectangle;
 
@@ -21,6 +19,7 @@
 import dwt.widgets.Display;
 
 import tango.text.convert.Format;
+import dwt.dwthelper.utils;
 
 
 /**
@@ -226,7 +225,7 @@
  *
  * @return a string representation of the event
  */
-public override String toString () {
+override public String toString () {
     return Format( "Event {{type={} {} time={} data={} x={} y={} width={} height={} detail={}}",
         type, widget, time, data, x, y, width, height, detail );  //$NON-NLS-1$//$NON-NLS-2$ //$NON-NLS-3$ //$NON-NLS-4$ //$NON-NLS-5$ //$NON-NLS-6$ //$NON-NLS-7$
 }
--- a/dwt/widgets/Listener.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/Listener.d	Sat Oct 11 22:16:54 2008 -0700
@@ -57,12 +57,13 @@
 void handleEvent (Event event);
 }
 
+
 /// Helper class for the dgListener template function
 private class _DgListenerT(Dg,T...) : Listener {
 
     alias ParameterTupleOf!(Dg) DgArgs;
     static assert( is(DgArgs == Tuple!(Event,T)),
-                "Delegate args not correct" );
+                "Delegate args not correct: delegate args: ("~DgArgs.stringof~") vs. passed args: ("~Tuple!(Event,T).stringof~")" );
 
     Dg dg;
     T  t;
@@ -97,7 +98,3 @@
 
 
 
-
-
-
-
--- a/dwt/widgets/Scrollable.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/Scrollable.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,6 +12,7 @@
  *******************************************************************************/
 module dwt.widgets.Scrollable;
 
+import dwt.dwthelper.utils;
 
 import dwt.DWT;
 import dwt.internal.gtk.OS;
--- a/dwt/widgets/Slider.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/Slider.d	Sat Oct 11 22:16:54 2008 -0700
@@ -12,6 +12,7 @@
  *******************************************************************************/
 module dwt.widgets.Slider;
 
+import dwt.dwthelper.utils;
 
 import dwt.widgets.Control;
 import dwt.widgets.Composite;
--- a/dwt/widgets/TableItem.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/TableItem.d	Sat Oct 11 22:16:54 2008 -0700
@@ -1234,7 +1234,6 @@
  * @param images the array of new images
  *
  * @exception IllegalArgumentException <ul>
- *    <li>ERROR_NULL_ARGUMENT - if the array of images is null</li>
  *    <li>ERROR_INVALID_ARGUMENT - if one of the images has been disposed</li>
  * </ul>
  * @exception DWTException <ul>
@@ -1244,7 +1243,6 @@
  */
 public void setImage (Image [] images) {
     checkWidget ();
-    if (images is null) error (DWT.ERROR_NULL_ARGUMENT);
     for (int i=0; i<images.length; i++) {
         setImage (i, images [i]);
     }
@@ -1276,9 +1274,6 @@
  * @param index the column index
  * @param string the new text
  *
- * @exception IllegalArgumentException <ul>
- *    <li>ERROR_NULL_ARGUMENT - if the text is null</li>
- * </ul>
  * @exception DWTException <ul>
  *    <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li>
  *    <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li>
@@ -1286,7 +1281,6 @@
  */
 public void setText (int index, String string) {
     checkWidget ();
-    if (string is null) error (DWT.ERROR_NULL_ARGUMENT);
     if (_getText (index).equals (string)) return;
     int count = Math.max (1, parent.getColumnCount ());
     if (0 > index || index > count - 1) return;
@@ -1316,9 +1310,6 @@
  *
  * @param strings the array of new strings
  *
- * @exception IllegalArgumentException <ul>
- *    <li>ERROR_NULL_ARGUMENT - if the text is null</li>
- * </ul>
  * @exception DWTException <ul>
  *    <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li>
  *    <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li>
@@ -1326,7 +1317,6 @@
  */
 public void setText (String [] strings) {
     checkWidget ();
-    if (strings is null) error (DWT.ERROR_NULL_ARGUMENT);
     for (int i=0; i<strings.length; i++) {
         String string = strings [i];
         if (string !is null) setText (i, string);
--- a/dwt/widgets/Widget.d	Sun Aug 17 09:04:23 2008 -0700
+++ b/dwt/widgets/Widget.d	Sat Oct 11 22:16:54 2008 -0700
@@ -562,6 +562,10 @@
     checkWidget();
     return (state & KEYED_DATA) !is 0 ? (cast(ArrayWrapperObject)data).array[0] : data;
 }
+public String getDataStr () {
+    return stringcast( getData() );
+}
+
 /**
  * Returns the application defined property of the receiver
  * with the specified name, or null if it has not been set.
@@ -596,6 +600,9 @@
     }
     return null;
 }
+public String getDataStr (String key) {
+    return stringcast( getData(key) );
+}
 
 /**
  * Returns the <code>Display</code> that is associated with
@@ -1409,6 +1416,9 @@
         this.data = data;
     }
 }
+public void setDataStr (String data) {
+    setData( stringcast(data));
+}
 
 /**
  * Sets the application defined property of the receiver
@@ -1478,6 +1488,9 @@
         }
     }
 }
+public void setDataStr (String key, String value) {
+    setData(key, stringcast(value));
+}
 
 void setForegroundColor (GtkWidget* handle, GdkColor* color) {
     auto style = OS.gtk_widget_get_modifier_style (handle);