public ConstraintSystem addConstraint(Constraint c) {
        if (c == null) {
            throw new IllegalArgumentException("Constraint cannot be null");
        }
        ConstraintVariable t = c.getTarget();
        List<ConstraintVariable> src = c.getSources();
        if (t == null) {
            throw new RuntimeException("No target");
        }
        if (src.isEmpty()) {
            throw new RuntimeException("No source(s)");
        }
        
        int index = variables.indexOf(t), i, size = src.size();
        if (index == -1) {
            variables.add(t);
        } else {
            t = variables.get(index);
            c.setTarget(t);
        }
        
        for (i = 0; i < size; i++) {
            ConstraintVariable s = src.get(i);
            index = variables.indexOf(s);
            if (index == -1) {
                variables.add(s);
            } else {
                s = variables.get(index);
                src.set(i, s);
                s.setSource(true);
            }
            s.addNext(t);
            t.addConstraint(s.hashCode(), c);
        }
        
        constraints.add(c);
        
        return this;
    }