Custom Brick Models Made to Order: How It Works, What It Costs, and How to Get Yours

Most people who get in touch with us have never had anything like this made before. They’ve got an idea, a building, a product, a place that means something, and they want to know if someone can actually turn that into a real custom brick model. The answer is yes, and this page explains exactly how.

We’ll walk you through what we build, how the process works, what it costs, and what we need from you to get started.

What we build

Buildings are the most common commission. Offices, factories, homes, landmarks. But the range goes well beyond that. We build branded display pieces, miniature product replicas, vehicles, custom award pieces, and bulk sets for corporate gifting programmes.

If you’ve got a reference image and a clear idea of what you want, there’s a strong chance we can build it. If you’re not sure yet, that’s fine too. Most enquiries start with a rough idea rather than a finished brief, and working out the detail is part of the process.

Every commission is designed from scratch around your brief. There’s no catalogue, nothing off the shelf. Whatever we build for you exists nowhere else.

How the commission process works

Here’s exactly what happens from the moment you get in touch to the moment your order arrives.

1. You get in touch

Send us a description of what you want built, what it’s for, and any reference images you have. There’s no commitment at this stage. We’ll review what you’ve sent and get back to you. If we need more detail before we can quote accurately, we’ll suggest a short call to make sure we’ve understood your requirements correctly.

2. We put together your quote

Once we have what we need, we’ll send you a detailed quote covering the full scope of your commission. Model design, parts sourcing, instructions, packaging, and custom box design if that’s something you want included. You’ll know exactly what you’re paying for before you commit. No surprises later.

3. You review and approve the digital render

Before a single brick is sourced, you see a digital render of the finished model. This is the stage that matters most. You can ask for changes and we don’t move forward until you’re satisfied with the design. It’s your commission and you should be confident in what’s being built before we start.

4. We source parts and prepare your packaging

Once the design is signed off, we source all the parts needed. If you’ve chosen custom printed boxes, we start on the box artwork at the same time. Both happen in parallel so everything comes together cleanly at the end of the project, without unnecessary delays.

5. Everything is packed and shipped

Every box, whether you’ve ordered one or a hundred thousand, contains all the parts and your building instructions. Instructions come in two formats. The digital option includes a card in each box with a photo of the finished model and a QR code linking to the instructions online. It’s the more eco-friendly choice and reduces packaging significantly. If you’d prefer a printed booklet instead, we can supply that too. Either way, everything needed to complete the build is in the box when it arrives.

6. Delivered anywhere in the world

We ship worldwide. Europe, North America, Australia, wherever you need it to go. Shipping is included in your quote upfront so what you’re quoted is what you pay.

What does a commission cost?

It varies. Size, complexity, and quantity all affect the price, which is why we quote every commission individually. Here’s a realistic guide to what different types of commission tend to cost.

Smaller personal commissions start from £120 / $150. A desk model, a modest-scale build for a birthday or retirement. These are contained single pieces and a strong option when you want something genuinely unique without a large outlay.

Corporate commissions typically start from £395 / $500. Architectural models, branded display pieces, large-scale builds for business occasions. The final price depends on the detail required, the scale of the model, and the time involved in design and sourcing.

Bulk orders are priced separately. If you need multiple identical models for a team gift or client programme, include the quantity in your initial enquiry and we’ll factor it into the quote from the start.

Whatever the commission, you’ll have a full itemised quote before you commit to anything.

How long does it take?

Typically 4 to 6 weeks from design approval to delivery. More complex builds and bulk orders take longer.

If you have a firm deadline, tell us upfront. We’d rather be straight with you about what’s achievable than overpromise and rush the build. The earlier you get in touch, the more flexibility we have at the design stage.

A commission worth mentioning

One of our most memorable corporate commissions came from a client who wanted to mark a business partner’s birthday with something that he could keep, be proud of and have fun building it too!

They asked us to build a brick model of the Devon Mill factory where their business was located. Working from reference photos and guidance from the team at Hunter Price we designed and produced a detailed scale model of the site.

The feedback we received:
“You pulled off the most epic project EVER” and “INCREDIBLE!!! Most thoughtful gift I’ve ever had!”

Read the case study for this project to learn more about what we did, the challenges we faced and how we delivered a one of a kind custom brick model that will hold memories forever.

Questions people ask before commissioning

Do you use genuine bricks?

We build primarily with genuine, brand-name bricks. For clients who need a more cost-effective option, we also work with a trusted supplier of high-quality compatible bricks. Either way, the quality of the finished model doesn’t change. Just let us know your preference when you get in touch.

What if I only have one or two reference photos?

That’s usually enough to get started. We’ll ask follow-up questions during the design stage if we need more detail to get things right.

Can I make changes after seeing the render?

Yes. The render stage exists for exactly this reason. You review the design before any parts are sourced and can request adjustments until you’re satisfied. We don’t start sourcing until you’ve signed off.

Can you include personalisation, logos, or custom branding?

Yes. Custom stickers, printed elements, company logos, names, and dates are all available as part of a commission. Let us know what you need at the enquiry stage and we’ll include it in the quote.

Can I order more than one?

Yes. Bulk commissions are a significant part of what we do. If you need multiple identical models, include that in your initial enquiry and we’ll provide quantity pricing in the quote.

Do you ship internationally?

Yes, worldwide. Shipping is included in your quote so there are no additional charges at delivery.

What do I need to provide to get started?

A description of what you want built, what it’s for, any reference images you have, and a rough budget. The more detail you can give us upfront, the quicker we can put together an accurate quote. If we need anything else, we’ll follow up or suggest a short call.

Ready to get yours made?

If you’ve got an idea, get in touch. There’s no obligation at the enquiry stage. Tell us what you have in mind and we’ll come back to you with next steps. If we need more detail before we can quote, we’ll suggest a short call to make sure we’ve got everything right.

<div class="badge-base LI-profile-badge" data-locale="en_US" data-size="large" data-theme="dark" data-type="HORIZONTAL" data-vanity="ferdi-vol" data-version="v1"><a class="badge-base__link LI-simple-link" href="https://www.linkedin.com/in/%E2%9C%85-ferdi-vol-corporate-gifts/?trk=profile-badge"></a></div>
/* Auto generated, hash = 5dceu9kevqjdyuy2uw1atqrsu */
//TODO: Break this file down so that we can actually unit test it.
(function(window) {
  /**
  * Renders all unrendred LinkedIn Badges on the page
  */
  window.LIRenderAll = function () {
    var CALLBACK_NAME     = 'LIBadgeCallback', //Must match callback on helpers.js
        BADGE_NAMES       = '.LI-profile-badge, .LI-entity-badge',
        // TODO -- tracking param for other badge types
        TRACKING_PARAM    = 'profile-badge',
        responsesReceived = 0, //Keeps track of number of responses recieved for proper cleanup when finished
        expectedResponses = 0, //Keeps track of number of responses to expect
        scripts           = [ ], //Keeps track of scripts added for proper cleanup when finished
        childScripts      = {}, //Keeps track of child scripts to render
        badges            = Array.prototype.slice.call(document.querySelectorAll(BADGE_NAMES));

    var i, len, badge, rendered;
    for (i = 0, len = badges.length;  i < len; i++) {
      badge    = badges[i];
      rendered =  badge.getAttribute('data-rendered');
      if (!rendered) {
        expectedResponses++;
        badge.setAttribute('data-rendered', true);
        renderBadge(badge);
      }
    }

    function isCNDomain() {
      if (typeof window !== "undefined") {
        var hostName = window.location && window.location.hostname ||  '';
        return (/linkedin(-ei)?.cn$/).test(hostName);
      }

      return false;
    }

    function generateUrl(isEI) {
      var domainPrefix = isEI ? 'https://badges.linkedin-ei' : 'https://badges.linkedin';
      if (isCNDomain()) {
        return domainPrefix + ".cn/";
      }

      return domainPrefix + ".com/";
    }

    function getBadgeKeyQueryParams(badge) {
      return Array.prototype.slice.call(badge.attributes).filter(function (attr) {
        return attr.name.lastIndexOf('data-key-', 0) !== -1;
      }).map(function (attr) {
        // Most browsers automatically lowercase the attribute name when its being read
        // We are calling lowercase on it again to ensure consistency for any browsers that are lagging behind.
        return encodeURIComponent(attr.name.replace('data-', '').toLowerCase()) + '=' + encodeURIComponent(attr.value);
      });
    }

    /*
    * Renders a single badge on the page
    * @param badge: div element of badge to render
    */
    function renderBadge(badge) {
      var size       = badge.getAttribute('data-size'),
          locale     = badge.getAttribute('data-locale'),
          type       = badge.getAttribute('data-type'),
          theme      = badge.getAttribute('data-theme'),
          vanity     = badge.getAttribute('data-vanity'),
          version    = badge.getAttribute('data-version'),
          isEI       = badge.hasAttribute('data-ei'),
          entity     = badge.getAttribute('data-entity'),
          isCreatePage = badge.hasAttribute('data-iscreate'),
          uid        = Math.round(1000000 * Math.random()),
          baseUrl = generateUrl(isEI),
          queryParams = [
            'locale=' + encodeURIComponent(locale),
            'badgetype=' + encodeURIComponent(type),
            'badgetheme=' + encodeURIComponent(theme),
            'uid=' + encodeURIComponent(uid),
            'version=' + encodeURIComponent(version)
          ],
          url;

      if (version === 'v2') {
        baseUrl += 'view';
        queryParams.push('badgesize=' + encodeURIComponent(size));
        queryParams.push('entity=' + encodeURIComponent(entity));
        queryParams = queryParams.concat(getBadgeKeyQueryParams(badge));
      } else {
        baseUrl += 'profile';
        queryParams.push('maxsize=' + encodeURIComponent(size));
        queryParams.push('trk=' + encodeURIComponent(TRACKING_PARAM));
        queryParams.push('vanityname=' + encodeURIComponent(vanity));
      }

      if (isCreatePage) {
        queryParams.push('fromCreate=true');
      }

      url = baseUrl + '?' + queryParams.join('&');
      badge.setAttribute('data-uid' , uid);
      jsonp(url); //Calls responseHandler when done
    }

    /**
    * Handles a response from the server. Finds badge matching badgeUid and inserts badgeHtml there
    * @param badgeHtml: String representing contents of the badge
    * @param badgeUid: UID of the badge to target
    **/
    function responseHandler(badgeHtml, badgeUid) {
      responsesReceived ++;

      var i, badge, uid, isCreate;
      var defaultWidth = 330 // max possible width
      var defaultHeight = 300 // max possible height

      for (i = 0, len = badges.length; i < len; i++) {
        badge = badges[i];
        // isCreate needed to prevent reloading artdeco script tag
        isCreate = badge.getAttribute('data-iscreate');
        uid   = parseInt(badge.getAttribute('data-uid'), 10);
        if (uid === badgeUid) {
          var badgeMarkup = `<body>${badgeHtml}</body>`
          var iframe = document.createElement('iframe');
          iframe.onload = function() {
            var iframeBody = iframe.contentWindow.document.body;
            // 5 px buffer to avoid the badge border being cut off.
            iframe.setAttribute('height', (iframeBody.scrollHeight || defaultHeight) + 5);
            iframe.setAttribute('width', (iframeBody.scrollWidth || defaultWidth) + 5);
          };
          iframe.setAttribute('frameBorder', '0');
          iframe.style.display = 'block';
          badge.appendChild(iframe);
          iframe.contentWindow.document.open();
          iframe.contentWindow.document.write(badgeMarkup);
          iframe.contentWindow.document.close();
          replaceScriptTags(badge, isCreate);
        }
      }
      tryClean();
    }

  // These functions are needed because badge markup is added via innerHtml property which does not run script tags
  function replaceScriptTags(node, isCreate) {
    if (shouldReplaceNode(node, isCreate)) {
      node.parentNode.replaceChild(cloneScriptNode(node), node);
      childScripts[node.src] = true;
    } else {
      var i = 0,
          children = node.childNodes;
      while (i < children.length) {
        replaceScriptTags(children[i++], isCreate);
      }
    }
    return node;
  }

  function shouldReplaceNode(node, isCreate) {
    return isScriptNode(node) && !childScripts[node.src] && (!isCreate || (isCreate && !node.getAttribute('data-isartdeco')));
  }

  function isScriptNode(node) {
    return node.tagName === 'SCRIPT';
  }

  function cloneScriptNode(node){
    var script  = document.createElement("script");
    for( var i = node.attributes.length-1; i >= 0; i-- ) {
      script.setAttribute( node.attributes[i].name, node.attributes[i].value );
    }
    return script;
  }

    // Gets all incoming responses
    window[CALLBACK_NAME] = responseHandler;

    /**
    * Tries to clean added tags
    **/
    function tryClean() {
      //Clean up after all requests are done..
      //Accounts for people including script more than once
      var done = (responsesReceived >= expectedResponses && expectedResponses > 0) || responsesReceived >= badges.length;
      if (done) {
        delete window[CALLBACK_NAME];

        // remove all script tags
        scripts.map(function(script){
          document.body.removeChild(script);
        });

      }
    }

    /*
    * Makes Jsonp request, responses handles by CALLBACK_NAME
    * @param url String: url of server to make request to
    */
    function jsonp(url) {
      var script = document.createElement('script');
      script.src = url;
      scripts.push(script);
      document.body.appendChild(script);
    }
  };

  if (document.readyState === 'complete') {
    window.LIRenderAll();
  } else {
    window.addEventListener('load', window.LIRenderAll, false);
  }

})(window);
Popular Posts