Generic Makefile handling unit testing and folder structure
I'll assume throughout this answer that you're targeting GNU Make.  It's available on all targets that matter, and it simplifies your world no end if you can avoid pandering to the idiosyncrasies of the manifold implementations of Make supplied with operating systems.
Object files depend on headers
This is the biggest thing that I think could be improved; I think it's probably a whole question in itself.  Your object files naturally depend on the corresponding C++ source files, but they also need rebuilding when their headers change.  Consider including generated makefiles that tell make how the object files depend on the headers; for a suitable recipe, see the Stack Overflow question &quot;Makefile, header dependencies&quot;, and for a longer exposition, read &quot;Auto-Dependency Generation&quot; by Paul D. Smith.  I normally use something like
-include $(OBJS:.o=.d)

%.d: %.c
    $(CC) $(CFLAGS) -MM -MT $@ -MF $@ $&lt;

More warnings
It's good to see that you're using -Wall.  I also recommend
CXXFLAGS += -Wextra -Wwrite-strings -Wno-parentheses
CXXFLAGS += -Wpedantic -Warray-bounds -Weffc++

The first line above always helps; the second does sometimes improve my code (you'll want to make use of -isystem to quieten your library includes, if you want to  make the latter bearable).
Output directory
Rules of makefiles advises that

Life is simplest if the targets are built in the current working directory.
Use VPATH to locate the sources from the objects directory, not to locate the objects from the sources directory.

That's certainly something to consider, though it might already be too painful to change.  I certainly prefer out-of-tree builds, so I can clean up with rm -rf build/ and be left with just my sources.
Hiding commands
I appreciate that you don't want a wall of text, but when you're debugging (or on an automated build host where you want a complete record of the build), then you might want to override this, and actually see which commands were run.  You can make the behaviour adjustable, like this:
QUIET := @
ECHO := @echo
ifneq ($(QUIET),@)
ECHO := @true
endif

Use it for your commands:
clean clear:
    $(ECHO) &quot;[CL]  out/&quot;
    $(QUIET)$(RM) out/*
    $(ECHO) &quot;[CL]  tmp/&quot;
    $(QUIET)$(RM) tmp/*

I changed the order to print first, like Make does, according to the Principle of Least Surprise.  It makes it more obvious what action was in progress when any error occurs.
Now, when you need to see the actual commands, you can make QUIET= to override the value and get the full output again.  IIRC, the Linux kernel uses a similar system (toggled by a KConfig setting), as does Qt's qmake (toggled with CONFIG += silent in the .pro file).
Re-use Make's pre-defined commands
Instead of writing
%.o: %.cpp
    $(CXX) $(CXXFLAGS) -c $&lt; $(INC) -o $@

%: $(OBJ)
    $(LD) $(LDFLAGS_TEST) $^ -o $@

you can make the rules more like the built-in versions (that you can see with make --print-database):
%.o: %.cpp
    $(COMPILE.cpp) $(OUTPUT_OPTION) $&lt;

%: $(OBJ)
    $(LINK.cpp) $(OUTPUT_OPTION) $^ $(LOADLIBES) $(LDLIBS)

Adapted to use QUIET and ECHO, that's
%.o: %.cpp
    $(ECHO) &quot;[OK]  $@&quot;
    $(QUIET)$(COMPILE.cpp) $(OUTPUT_OPTION) $&lt;

%: $(OBJ)
    $(ECHO) &quot;[OK]  $@&quot;
    $(QUIET)$(LINK.cpp) $(OUTPUT_OPTION) $^ $(LOADLIBES) $(LDLIBS)

You'll need to ensure that your include path is in CXXFLAGS, and you might need target-dependent flags:
CXXFLAGS += $(INC)

tmp/%: CXXFLAGS=$(CXXFLAGS_TEST)

All makefiles should have...
.DELETE_ON_ERROR:

Without this, a failed command could leave a part-written output that a subsequent make believes is up-to-date.
Finally
Here's a tyni tyop:
.PHONY: clean, clear

Lose that , - you've said that clean, is a phony target, not clean as you intended.