* Initial support for displaying multiple screenshots for packages
which have more than one. Still rough and unfinished.
Screenshot window now has a toolbar with prev/next buttons and
a busy loading indicator. Switching through the screenshots works.
There's currently a server-side bug which makes all data turn up
15 times in the JSON file, so please don't report a bug about
HaikuDepot showing 15 or 30 screenshots available when it's really
just 1 or 2 :)
Still to be done: toolbar icons instead of text labels; better
handling of screenshot window resizing; maybe thumbnails of
screenshots and preloading other screenshots in the background.
Main window also needs a way to indicate that there are more
screenshots than the one thumbnail, needs some more thought about
how that might look.
This concludes my HaikuDepot commits from the coding sprint at
KDC 2017 Toulouse!
* The UI became unresponsive while the PackageListView was filled
with all the packages. This was especially apparent when using
the search function, which clears and refills the view with every
typed character.
* Add a new worker thread with the task of asynchronously filling the
PackageListView. When a new data model is adopted, we hand the
thread a copy of the visible package list. The worker thread then
goes through the list and sends the package infos via BMessage back
to the MainWindow, in batches of 20 infos per message. When the 20
entries were added, it acknowledges this to the worker thread which
will send the next 20 infos (so UI messages can get in between,
keeping it responsive). The lists also get a unique ID so that
model changes while the list is populating will invalidate
previously sent messages (and cause the worker thread to cancel
processing the outdated list).
* Search is much nicer to use this way, staying responsive and
listing packages while typing. Still not perfect since the
PackageListView is still cleared and refilled each time a character
is typed, instead of just narrowing down the already displayed
package set. But that's to be improved on another day...
* Same applies to filling FeaturedPackagesView btw
* Use a hash table to find PackageRows by package name in
PackageListView, instead of doing linear search over all rows.
Improves performance of populating the list, since every
AddPackage() checks if a row for the package already exists.
* Add new WorkStatusView which keeps the user informed about what's
happening. It's a status bar at the bottom of the window which
shows on the left side either a spinning barber pole (for
operations without a progress), or a progress bar (for download
progress). Next to that is a text view showing a descriptive
status text.
* Currently, it will notify of the following operations:
- Repository refresh (barber pole)
- Background packet actions, like preparation of install or uninstall
(barber pole)
- Package downloads, including downloads of dependencies (progress
bar). Status text indicates the name of the package currently
being downloaded (if any), and how many more packages are queued
for download after it (if any).
* Hooks into PackageListView to be notified of package status changes
(such as becoming pending or download progress)
* When the package currently being downloaded is also selected in the
list view, the user sees the progress bar in WorkStatusView
as well as the one in the PackageInfoView, which is redundant. This
still needs a good solution...
* Add a new event "ConfirmedChanges" to PackageProgressListener. It
triggers when a package action was confirmed by the user and is
about to be run. This can be used to e.g. get a full list of
packages about to be installed (i.e. including dependencies)
right before the process of fetching/installing them is started.
* Add a handler for it which looks at PackagesToActivate and sets
all their PackageInfo states to pending (so now, when installing
a package, its dependencies immediately become pending as well).
* When a view is used with the layout system, its initial frame rect
was set to (0, 0, 0, 0), which is a BRect covering 1 pixel in the
top left corner of the window.
Since this a valid rect, it can cause "badly behaved" views to
trigger redraws of themselves and other views during the layout
process, which is ultimately the reason for the HaikuDepot UI
freezing while populating with packages.
The misbehaving view in this case is BTextView. When in read-only
mode, since commit e27a53b2, its GetHeightForWidth() implementation
causes the view to resize (really resizing, not just simulating a
resize) and thus it invalidates itself. This is broken behaviour,
and needs to be fixed in BTextView. Since GetHeightForWidth() is
called during the layout process, all the not-yet-layouted views
have a frame of (0, 0, 0, 0). The invalidation of just the one
BTextView in the layout then hits *all* new views that are being
layouted (because they all occupy the same one pixel in the
corner), and they all get redrawn.
Many view Draw() implementations ignore the update rect, so work
is being done. And even if not, this can cause a lot of traffic
on the app_server link. In a test case with HaikuDepot's
FeaturedPackagesView, adding 300 rows (each containing a BTextView,
among other views) in quick succession caused over 6 million
commands to travel over the app_server link, completely freezing
the UI for a long time.
* The actual problem here is in BTextView::GetHeightForWidth() and
must be fixed there.
However we also put in an extra-fix here because it never makes
sense anyway to try and draw a view that has not yet been layouted.
So we set the initial BView frame to an invalid rect
(0, 0, -1, -1), which will suppress any actual updating, even
when the view actively invalidates itself, as long it doesn't
have a size yet. (The dirty region will always end up empty
then).
* Fixes HaikuDepot UI freezing during package population (caused by
above described behaviour from BTextViews in FeaturedPackagesView).
Might improve performance in other applications using BTextView
with layouting as well.
* Fix use-after-free in the auto-generated JSON listener code (was
calling method of instance after 'delete this')
Will also submit a patch for the code generation script in the
haikudepotserver repo so it won't get lost -- this is just a
temporary fix-up until then.
* Fixes some random occasional crashes
* BarberPole view for indicating that the application is busy while
the amount of work is not known
* Flat looks with scrolling color stripes. Number of stripes and their
colors are freely configurable, so you could add a whole rainbow of
colors to endlessly scroll through if you like.
* When SystemProfiler::_MaybeNotifyProfilerThreadLocked() is called
and the conditions are right, it will lock the thread's scheduler
spinlock and unblock it. Internally, the unblock will enqueue the
thread into the run queue, which causes a ThreadEnqueuedInRunQueue
event for SystemProfiler. Since the conditions haven't changed, it
now went into _MaybeNotifyProfilerThreadLocked again (this time
from the profiler thread context). In there, it will try to lock
the profiler thread's scheduling spinlock, which is already locked
by the other thread (which is firmly sleeping). Deadlock, KDL.
* Before unblocking the profiler thread, unset fWaitingProfilerThread
so that further events will not try to unblock it again.
* Performance: on incoming package update messages, don't setup
all data in the PackageView from scratch again; instead, only
update the parts which were actually changed
* Change the background color in the screenshot enlarge window
from black to the blue, specifically the "Haiku blue", the
default desktop background color. Makes it look much friendlier.
* Setting the low color later so it's not overriden also makes
transparency in the screenshot work, i.e. it blends onto the
blue background (many screenshots are thankfully already using
transparency to mask out the unused rectangle left by the window
tab)
* As requested in #12538
* Hidden by default to not clutter up the view with information that
isn't important in the default setup. Like the state of other
columns, the visibility is remembered.
* Fix bug reported by humdinger: when the volume which is
currently shown in the file panel is unmounted, the file
panel's window was closed and even deleted. This is not only
inconvenient but also a use-after-free bug waiting to happen:
an application which keeps the BFilePanel around to show it
again later (as recommended in the BeBook) cannot know that
it has become invalid while it was hidden (the destruction of
the window happens even when it's not shown).
* When receiving an unmount event for the currently shown volume,
we now reset the view to the home directory.
* FuseSMB provides access to shared files and folders over SMB.
It features automatic discovery of servers and shares and
displays them as a folder hierarchy in a virtual volume on the
desktop
* Supports interactive authentication to access shares which require
login. Just open it, and a dialog pops up. Login data is stored in
BKeyStore.
* Comes with a network preferences add-on to easily enable and
configure it. No barbaric manual typing of mount commands required!
* Makes use of Haiku FUSE extensions to give custom MIME types with
icons for workgroup/share/server folders. Thanks again to humdinger
for designing the workgroup and share icons!
* Although the used libsmbclient only supports SMB protocol
version 1, performance is decent enough. Getting around ~75MiB/s
reading over a GbE link here
* Commit 0bec83a8 added const to the signatures of
pthread_mutex*_get*() functions. The declarations in
posix_error_mapper now didn't match that anymore, so the
extern C was lost, adding C++ mangling to the functions
from posix_error_mapper. This made linking applications with
posix_error_mapper fail.
* Last commit put the file-extension-to-MIME-type table and associated
code into a shared location. So now we can remove it from the FAT
and NTFS FS add-ons (they both had their own copy) and use the shared
one there as well, removing the code duplication.
* Add special handling for reading the BEOS:TYPE attribute to supply
on-the-fly fake MIME types for FUSE module filesystems, the same
way it's done in our FAT and NTFS FS modules
* Reuse the mime_ext_table which we already have and put it into a
shared location so we don't get further extra copies of it
* Implement reading extended file attributes in FUSE modules,
using getxattr()
getxattr() is a quite limited API, not allowing to specify a read
offset. So we read in the entire attribute value into a buffer and
store in the cookie. This shouldn't be a problem memory-wise, since
xattr implementions usually have limitations regarding attribute size
anyway, so it'll rarely be more than a few kilobytes.
* Writing, renaming, and removing attributes is not yet implemented
* Add a way for a FUSE module to supply Haiku-specific extensions.
This allows it to integrate better with Haiku while only requiring
minimal changes on the FUSE module itself.
* For now, there is only one extension: another function pointer for
"get_fs_info", which lets the FUSE module fill in an fs_info struct.
FUSE provides no good way to otherwise communicate extra information,
such as the volume flags (e.g. B_FS_IS_SHARED).
* A FUSE module can signal that it supports the Haiku extensions by
a) defining HAS_HAIKU_FUSE_EXTENSIONS before including the fuse
headers
b) setting the global variable gHasHaikuFuseExtensions to 1 in
its initialization
Otherwise, the Haiku extensions are completely invisible to the
FUSE module.
* Commit 337c4ccf introduced usage of plain memcpy in
get_next_frame_no_debugger(), when the frame is already
known to be on the kernel stack. However, it also needs
to check that the end of the frame is still within the
stack bounds. Otherwise this can cause a KDL if bp does
not point to a valid complete frame anymore and is
near a page boundary. Although with commit e477b10c such
cases should already be avoided, it's still safer to
check this here in case of e.g. analyzing broken stacks.
* No need to continue walking the stack when a zero return
address is found, only bogus frames will follow
* Fixes KDLs seen when using the system profiler, due to
a bug that will be fixed in the next commit...
* "ht" and "-ht" enable or disable the use of HT mode
(high throughput, 802.11n) for the wireless network device
* Analogous to the option with the same name in FreeBSD's ifconfig
* Disabling HT before associating with an AP is a workaround for
connection instability issues encountered with iprowifi4965
driver
* Painter::StrokeLine() has an optimization for lines which are
single pixel dots, i.e. identical start and end point and pen
size 1: it sets the pixel directly in the buffer, completely
bypassing the AGG base renderer.
This is a problem when inside a layer since this also bypasses
the low-level offset in the base renderer (which moves drawing
coordinates into the layer bitmap), causing an out-of-bounds
access.
* Fixes#12587
* When cloning a cached mask, we have to attach the
AGG rendering buffer of the new instance to the AGG clipped
mask object. Before, it was using the buffer description from
the clone source.. which can later disappear at any time.
* Fixes bug #12478
* Make getaddrinfo() and friends thread-safe by using the thread-safe
versions of the res functions.
* NetBSD offers two versions of the res functions: one in res_state.c
from the netresolv directory, defined as weak symbols. It is the
legacy version and only for single-threaded applications.
A thread-safe version of the functions is in res_state.c inside
their libpthread directory. An application that uses pthreads on
NetBSD will then use the non-weak symbols from the pthreads
library.
* On Haiku, the thread-safe version is now always used. The
res_state.c is taken from NetBSD's libpthread directory, and then
only struct _nres from the other file is added to it.
Please keep this in mind for future updates of netresolv, do not
accidentally replace it with the single-threaded version.
* This e.g. fixes WebPositive just hanging when opening websites
(even in situations where no IPv6-related problems apply), waiting
forever to resolve names.
* Fix wrong nesting of loops which are supposed to skip the first
(*cookie) number of elements and those with the wrong address
family
* With a start value of first = 0 (the usual case), the old code
would always just return the first element of the addrinfo list, no
matter which address family was actually requested
* The pointer mdt should point to the start of the contents of the
master data table. As defined in struct ATOM_MASTER_DATA_TABLE,
the content begins 4 bytes after the beginning of the table
(which in turn is ctx->data_table bytes from the start of the
AtomBIOS). The wrong parantheses in the cast moved the pointer
somewhere else completely.
* That this apparently worked on many cards is because the mdt
pointer in this function is used just to make sure that the
following dereference is not a NULL-pointer access.
The actual dereference is then done using the CU16() and CU8()
macros which do the casts correctly. However, it only worked when
the wrong pointer plus index lead to some byte which was, by
chance, not zero. For many chips, this was the case.
* For the AtomBIOS of a Radeon HD7850M (Heathrow Pro) it didn't work
out though and the driver couldn't parse tables. With this fix, it
now works on such chips as well.
* Also, fix the same problem in code for master command table.
* At least some nVidia HDA controllers do not acknowledge the CORB
read pointer reset, which is required by the spec (cf. HDA 1.0a
ch. 3.3.21). For these controllers, do not fail when acknowledge
is missing.
* Makes hda driver work for nVidia HDA controllers again, thus fixing
the regression pointed out in #10212.
* Some chipsets do not support bus-snooping for the HDA data
transfers. So, when trying to enable snooping, verify that the
setting was accepted.
* When snooping is not possible, set memory areas for audio buffers,
buffer descriptor lists and command ring-buffers as uncached to
ensure memory coherency with the HDA controller.
* This fixes KDLs during booting on some systems where snooping
is not supported (seen on two systems with AMD chipsets, maybe
applies to others as well).
After setting up the buffer descriptor list for a stream, it was a
gamble whether these writes would be visible to the HDA controller
when subsequently enabling the stream. On some boots it was unlucky
and then the HDA controller's DMA engine would go haywire and start
overwriting random kernel memory with audio input data. The
scheduler was usually the first victim and caused page fault KDLs
due to corrupted data structures.
* Do read-modify-write cycle to preserve bits marked as RsvdP in the
following registers: WAKEEN, CORBWP, CORBCTL, CORBSIZE, RIRBWP,
RINTCNT, RIRBCTL, RIRBSIZE.
* Spec requires software to wait for hardware to acknowledge the
reset by waiting for the bit to become set and then manually
unset it and again wait for it to become unset.
(cf. HDA spec 1.0a ch. 3.3.21)
* Also, do read-modify-write to protect preserved bits
* Radeon chips since Bonaire use a different PCI register base
address. Select the correct one depending on chipset generation
(values from Linux driver).
* Makes radeon_hd work for newer APUs/GPUs (tested with Kabini APU).
* Prefix lock functions with __ to mark them as private. Add
forwarding macros to keep existing code working.
* Avoids symbol name clashes with kernel lock APIs, occuring when
using kernellandemu-lib in userlandfs. Thanks to Ingo for the
suggestion.
* Base class needs to check this as well because the subclass might
not override it (e.g. InitParametersPanel).
* Fixes crash when trying to initialize partition map. Thanks to
jessicah for pointing this out.
* When the add-on provides no parameter editor, still add the set of
of default controls instead of just bailing out of the Init()
method.
* Before, DriveSetup never added the default controls in such cases
and simply showed an empty window. This happened when e.g. trying
to create a new partition inside an extended partition (because
ExtendedPartitionAddOn provides no parameter editor).
* Fixes#10569
* When determining the output link, look at the internal encoder in
the transmitter setup.
* Fixes getting no picture on digital output of certain systems.
* The rounding algorithm here expects to start with the 2 digits
after the decimal point in pll->feedbackDivFrac. Multiplying with
1000 instead of 100 filled it with 3 digits.
The last step then set the fractional part to zero because it was
still too large.
* The AMD-part of the add-on is supposed to reject some very old
models. However, a bug in the selection code caused it to reject
anything with model-number smaller 9 regardless of model-family.
This caused MTRR setup to not happen on many AMD CPUs and Haiku
being very slow on these machines.
* Fixes#10571
* BSecureSocket::CertificateVerificationFailed() took a BCertificate
instance by value as parameter.
BCertificate deletes internal data in its destructor. Passing an
object by value creates a copy, so the copy attempted to delete
the internal data again during its destruction.
This caused mail_daemon to crash here when it came across a failed
certificate.
* Fix: pass BCertificate object as reference.
* BWindow used to generate the B_MOUSE_IDLE events by sending a
delayed message with a one-shot BMessageRunner to itself.
Every creation and deletion of BMessageRunners causes synchronous
messaging between the application under the mouse cursor and the
registrar. This creates large amounts of calls to set_port_owner()
in the kernel whenever moving the mouse.
* Now, B_MOUSE_IDLE is sent by the cursor loop inside the app_server
instead. When the mouse wasn't moved for the tooltip delay time,
it inserts a B_MOUSE_IDLE message into the event stream.
* The tooltip delay thus becomes a system-wide constant and is not
configurable per-application anymore (no code currently in the
Haiku repo makes use of that anyhow).
* Replace ports list mutex with R/W-lock.
* Move team port list protection to separate array of mutexes.
Relieve contention on sPortsLock by removing Team::port_list from its
protected items. With this, set_port_owner() only needs to acquire the
sPortsLock for reading.
* Add another hash table holding the ports by name. Used by find_port()
so it doesn't have to iterate over the list anymore.
* Use slab-based memory allocator for port messages. sPortQuotaLock was
acquired on every message send or receive and was thus another point
of contention. The lock is not necessary anymore.
* Lock for port hashes and Port::lock are no longer locked in a nested
fashion to reduce chances of blocking other threads.
* Make operations concurrency-safe by adding an atomically accessed
Port::state which provides linearization points to port creation and
deletion. Both operations are now divided into logical and physical
parts, the logical part just updating the state and the physical part
adding/remove it to/from the port hash and team port list.
* set_port_owner() is the only remaining function which still locks
Port::lock and one or two of sTeamListLock[] in a nested fashion.
Since it needs to move the port from one team list to another and
change Port::owner, there's no way around.
* Ports are now reference counted to make accesses to already-deleted
ports safe.
* Should fix#8007.
* Optimized code path for bitmap drawing with bilinear interpolation
scaling was assuming that source bitmap is always at least 2 rows
in size.
* Fixes#12469: in webkit, scaled 1-pixel-high bitmaps often occur.
If the bitmap allocation is by chance aligned to a page end, access
to the non-existant second row crashes app_server.
* Add a lock which is acquired when reattaching/regenerating masks,
and also acquired for a cached mask before making a clone of it,
to prevent the clone from having an inconsistent state in
concurrent edge cases.
* Maybe fixes#12469
* If the same shape alpha mask is set again and again, we now keep
the rendered masks in a cache. On certain websites, WebKit sets
the same shape for clipping hundreds of times, which uses a lot
of time to render the masks.
* When a shape mask was generated, we put it into AlphaMaskCache.
The constructor for ShapeAlphaMask is made private and a factory
method is used for instantiation instead, which transparently
looks up in the cache whether a suitable mask was already generated
before (so the entire caching is encapsulated inside the AlphaMask
class).
* When taking a mask out of the cache, we still create a new
AlphaMask instance. However, the new instance will share the
mask bitmap with the previously generated instance (aside from
the rendering of their bitmap, AlphaMask instances are pretty
lightweight). Shape masks are only seen as identical when
their shape is the same, the inverse flag, and they have the
same parent mask.
* Cache is limited to a fixed size of currently 8 MiB, using a
simple random replacement scheme. An LRU scheme can be added in
the future if necessary. Counting of bytes for the cache size
includes parent masks of masks in the cache, even if the parent
itself is not cached. A reference counter for "indirect" cache
references keeps track of which masks are not part of the cache,
but still need to be added to the cache byte size.
* For now, only for ShapeAlphaMasks, other mask types can be added
as necessary.
* If there is an empty clipping region (invalid clipping) for the
current view, a new layer could still be started, but not ended
anymore. That's because unlike begin layer, end layer is handled in
_DispatchViewDrawingMessage (because it can do actual drawing)
and this method checks whether the clipping is valid and bails out
if it isn't.
* Add an exception for the AS_VIEW_END_LAYER command code to still
process it even when the clipping is invalid. The layer itself
can after all set a valid clipping later on when its command list
is played back. And even if it doesn't, we still have to play it
to make sure nested layers are cleaned up.
* Fixes the memory leak in #12460 where webkit creates
said situation: it had a layer open and then the closing was
ignored due to empty clipping. All subsequent layer calls created
nested layers in that one, hundreds of them, and their BPictures
contained bitmaps, quickly eating up and leaking hundreds of MiB
in app_server.
* When a layer has opacity 0, we can't just ignore it, we still
have to play back its picture, even if the drawing will never
appear on screen. This is because there might be nested layers
and if they don't get blended, their references are not released.
Also, it can be argued that state changes in the layer should be
applied even if the layer is invisible (if we ignore it there,
it would be inconsistent with other layers).
This edge case of invisible layers could be optimized further, but
it is rare enough anyway, so this should do.
* OffscreenCanvas was not deleting its DrawState. Found thanks to
the allocation tracking feature in libroot_debug (thanks mmlr!)
* Also a missing nothrow and a missing ref release in an error case
* Making the alpha masks independent of view size is a good thing,
however it turns out that I was too optimistic about the
consequences: webkit sometimes sets masks for the whole page, not
just the currently visible area. E.g. on Github diff views, it
was seen to set a clipping path which is about 1,000 x 10,000
pixels in size. Generating these huge masks eats up lots of memory
and time.
* We now clip the alpha masks to the current view size. This
introduces a dependency between mask and view again, however a
weaker one than it used to be before the mask rework. When the
view is enlarged, and the alpha mask was previously clipped during
rendering, we regenerate it at the new size. When the view is
shrunk however, we don't do anything and just keep the
now larger than necessary mask around (so we don't have to
regenerate again when the view is subsequently enlarged again --
except if it then becomes even larger than it used to be).
Changing the view origin is unaffected and still doesn't cause a
regenerate.
* BView::TranslateBy(), BView::ScaleBy() and BView::RotateBy()
allow to conveniently modify the current affine transformation.
This makes it unnecessary to first read the current transform,
modify it, and then set it again.
Uses the new Pre...() methods of BAffineTransform.
* Also, remove setting the transform "through" to the BView even
while recording a BPicture, as this now results in transforms
being applied more than once.
* The existing methods TranslateBy(), ScaleBy() and RotateBy()
transform the transformation. For a transform A, a point p,
and the temporary transform B (being applied by the methods),
this results in p' = B*(A*p) = (B*A)*p
This is not necessarily the desired result. Suppose A is a
translation and B a rotation, added by RotateBy(). Then B*A
means that the translation itself is rotated, so B moves the
coordinate origin itself, by rotating it around the original
origin of the coordinate system (top left view corner).
If we want to translate and then rotate around that *new* origin,
we need to multiply the transforms the other way around: A*B.
Three new methods PreTranslateBy(), PreScaleBy() and PreRotateBy()
implement this. They are later used as a base to add translatation/
scaling/rotation methods to BView which behave in the expected
ordering, similar to other graphic APIs.
* Add new clipping API for rectangles (ClipToRect, ClipToInverseRect)
and shapes (ClipToShape, ClipToInverseShape)
* Works with affine transforms and automatically switches from fast
region-based clipping to alpha-mask based clipping as necessary.
* Always self-intersecting, i.e. no state push required to further
narrow down the clipping region. All of the 4 new methods can be
mixed in any order.
* Add IsDilation() to BAffineTransform and Transformable which check
whether the transform is a dilation, i.e. consists of only
translation and/or scaling
Conflicts:
src/kits/interface/PicturePlayer.cpp
src/servers/app/ServerPicture.cpp
In addition, the following files were also adapted to master branch
BPicture changes during the merge:
src/kits/interface/PicturePlayer.h
src/servers/app/PictureBoundingBoxPlayer.cpp
* Refactor AlphaMask class to separate the mask from its source. This
allows use to not just a BPicture as source for a pixel alpha mask,
but also e.g. a BShape in the future (not yet implemented).
* For BPicture-based masks, use the PictureBoundingBoxPlayer to
determine the size of the resulting mask bitmap. The masks are now
drawn into bitmaps of this size (instead of the whole view size).
When alpha masks are stacked, their bounding rectangles intersect
(i.e. masks further up in the stack can never be larger than masks
lower in the stack). The bitmap of a mask always contains the state
of itself blended with all masks in the stack below it.
This also avoids frequent rerendering of the masks. They are now
independent of view size. When the view origin (in screen
coordinates) changes we only have to reattach the mask buffer,
without having to redraw it.
* The class UniformAlphaMask is used for simple masks with the same
alpha value in all pixels, it uses no mask bitmap at all.
Currently, it can only be used on its own and not be stacked
together with other mask types.
* Make test-app_server work again in a launch_daemon environment
* test_registrar gets a separate signature and port name again so the
host system can distinguish it from the system registrar
* AppServer is normally a BServer now, however, there can't be two
BApplications in one team. A class TestServerLoopAdapter is added,
which becomes the base class of AppServer instead of BServer when
compiling for libbe_test. It's an adapter class which looks towards
AppServer as it if was a BServer, but internally it is derived from
MessageLooper (like the old AppServer before the transition to
BServer).
This way, AppServer can stay a BServer in normal builds and it also
avoids having to use too many #ifdefs to distinguish the two
versions.
* Same concept as the previously exisiting drawing mode
implementations for e.g. pixel alpha overlay mode: when pattern
is solid, provide a separate mode implementation which does no
unnecessary pattern pixel lookups. This provides a considerable
speedup in composite mode when no stipple pattern is used.
* Add support for pixel alpha overlay mode in the optimized bilinear-
scaled bitmap drawing code of BitmapPainter.
For now, only BilinearDefault supports this. DrawBitmapBilinear
gets the colour type and draw mode as template parameters to
minimize code duplication and allow simple extension with further
pixel formats and modes.
Avoids, for this mode, fallback to the slower generic
AGG-pipeline-based version.
* Add another mode to DrawBitmapNoScale for drawing bitmaps using
B_OP_COPY with alpha masks. It behaves like the definition for
ClipToPicture from the BeBook: pixels with alpha = 0 are ignored,
pixels with any alpha > 0 are copied.
Before, this fell back to the slower generic AGG-pipeline-based
version.
* Some light refactoring