Rad Cor: Во-первых, в конце не надо использовать wp_reset_query, с WP_Query / get_posts используется функция wp_reset_postdata(). Во-вторых, ошибка говорит, что где-то вы пытаетесь обращаться к объекту типа WP_Query как к массиву. Ищите где. Где-то в вашей теме.
Прямые запросы в БД в рамках CMS / фреймворка свидетельствуют о незнании возможностей ядра платформы. Данный запрос формируется с помощью родного API. В вашем примере ничего не сработает, потому что колонки 'category' в таблице wp_posts нету, там идет JOIN. Не пишите ерунды, если не понимаете о чем речь.
Иван Козлов: Для вас делает более читабельным - возможно. Начнете работать с другими разработчиками над одним и тем же проектом хотя бы среднего размера - и вас все будут проклинать, потому что есть стандартное API, а вы его переопределяете в свою переменную, которая всем остальным будет непривычна (и ее использование будем им непонятно). Управлять из одного места? Так get_template_directory_uri тоже одно место. И ее значение всегда одинаковое.
xxy: Все, что можно сверстать в статику, можно натянуть и на WordPress. Как и на любой другой движок. Что и как делать - тут вопрос не только к кодеру, как я подозреваю, но и к бекендеру, разработчику. Потому что то, что вы называете "фичи с разных тем" может быть не просто интересным выводом стандартной фичи WP, а полностью кастомный функционал, который кто-то должен для начала написать. А это время и бюджет. В общем, если говорить абстрактно "можно ли" - да, можно, но в процессе всегда консультируйтесь с фронтенд и бекенд разработчиком, а под рукой всегда держите ТЗ проекта. На практике же лучше отталкиваться именно от ТЗ и бекенда / функционала. И это касается любой платформы, не только WP.
Простой пример - делаем магазин на WP / WooCommerce. У Woo есть своя стандартная страница входа / регистрации с двумя формами. Натянуть на нее наши стили - час работы фронтендера, бекендер не участвует вообще. Дизайнер силой характера решил, что там должна быть одна форма, кнопка для открытия второй формы, добавил/убрал поля в форме регистрации. И теперь бекендеру надо подключаться на час-два, фронтендеру +1 час минимум добавился, плюс он не может доверстать страницу по ка не получит от бека готовую страницу. Думаю, легко понять, кто в итоге получил по шапке за свое творчество. И если таких моментов в дизайне много, вы можете запросто увеличить сложность, сроки и стоимость там, где это совершенно не нужно.
zerofx: Основной цикл / основной WP_Query строится из разобранного URL и глобальных данных. Он есть всегда, на любой странице / записи / архиве и тд, это как скелет. Многие, если им надо например изменить сортировку или количество постов на странице, забывают о главном цикле и делают свой вторичный, а потом начинают мучаться с пагинацией (потому что она завязана как раз на глобальных данных и основном цикле). А меняется такое через хук pre_get_posts, который и модифицирует главный WP_Query непосредственно перед его выполнением. Это как пример.
zerofx: а wp_reset_postdata() соответственно потом возвращает все обратно - заново запихивает в глобальную $post то, что там было до вашего произвольного цикла - контент страницы, полученной через Main Query.
zerofx: setup_postdata($post); - вот чего не хватает в вашем коде. Эта функция в вашем цикле (лупе) запихивает полученный пост (страницу) в глобальную переменную $post, из которой и забирают данные почти все template tags, такие как the_title и the_content. Без вызова этой функции в глобальной $post продолжает находиться та страница, которая прилетела в Main Query.